krb5: Better default KCM cache logic (moar)
Ah, we can't use context->default_cc_name because that will be taken from KRB5CCNAME if it's set, and then we'll think whatever that value is is the default, but we're really looking to special case resolving of the "%{UID}" KCM cache name. So do that.
This commit is contained in:
@@ -151,8 +151,6 @@ kcm_stat(krb5_context context, const char *name)
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
static krb5_error_code kcm_get_default_name_kcm(krb5_context, char **);
|
|
||||||
static krb5_error_code kcm_get_default_name_api(krb5_context, char **);
|
|
||||||
static krb5_error_code kcm_get_default_name(krb5_context,
|
static krb5_error_code kcm_get_default_name(krb5_context,
|
||||||
const krb5_cc_ops *,
|
const krb5_cc_ops *,
|
||||||
const char *, char **);
|
const char *, char **);
|
||||||
@@ -164,30 +162,26 @@ kcm_alloc(krb5_context context,
|
|||||||
const char *sub,
|
const char *sub,
|
||||||
krb5_ccache *id)
|
krb5_ccache *id)
|
||||||
{
|
{
|
||||||
|
krb5_error_code ret;
|
||||||
krb5_kcmcache *k;
|
krb5_kcmcache *k;
|
||||||
size_t ops_prefix_len = strlen(ops->prefix);
|
size_t ops_prefix_len = strlen(ops->prefix);
|
||||||
size_t plen = 0;
|
size_t plen = 0;
|
||||||
size_t local_def_name_len;
|
size_t local_def_name_len;
|
||||||
const char *local_def_name = "";
|
char *local_def_name = NULL; /* Our idea of default KCM cache name */
|
||||||
char *def_name = NULL;
|
char *kcm_def_name = NULL; /* KCM's knowledge of default cache name */
|
||||||
int default_cc_name_is_ours;
|
|
||||||
int aret;
|
int aret;
|
||||||
|
|
||||||
if (!context->default_cc_name)
|
/* Get the KCM:%{UID} default */
|
||||||
(void) krb5_cc_default_name(context);
|
if (ops == &krb5_kcm_ops)
|
||||||
|
ret = _krb5_expand_default_cc_name(context, KRB5_DEFAULT_CCNAME_KCM_KCM, &local_def_name);
|
||||||
default_cc_name_is_ours =
|
else
|
||||||
context->default_cc_name &&
|
ret = _krb5_expand_default_cc_name(context, KRB5_DEFAULT_CCNAME_KCM_API, &local_def_name);
|
||||||
strncmp(context->default_cc_name, ops->prefix, ops_prefix_len) == 0 &&
|
if (ret)
|
||||||
context->default_cc_name[ops_prefix_len] == ':';
|
return ret;
|
||||||
|
local_def_name_len = strlen(local_def_name);
|
||||||
if (default_cc_name_is_ours) {
|
|
||||||
local_def_name = context->default_cc_name + ops_prefix_len + 1;
|
|
||||||
local_def_name_len = strlen(local_def_name);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Get the default ccache name from KCM if possible */
|
/* Get the default ccache name from KCM if possible */
|
||||||
(void) kcm_get_default_name(context, ops, NULL, &def_name);
|
(void) kcm_get_default_name(context, ops, NULL, &kcm_def_name);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* We have a sticky situation in that applications that call
|
* We have a sticky situation in that applications that call
|
||||||
@@ -214,17 +208,18 @@ kcm_alloc(krb5_context context,
|
|||||||
*
|
*
|
||||||
* Only the first two count as "maybe I mean the default KCM cache".
|
* Only the first two count as "maybe I mean the default KCM cache".
|
||||||
*/
|
*/
|
||||||
if (residual && !sub && local_def_name &&
|
if (residual && !sub &&
|
||||||
strncmp(residual, local_def_name, local_def_name_len) == 0) {
|
strncmp(residual, local_def_name + ops_prefix_len + 1,
|
||||||
if (residual[local_def_name_len] == '\0' ||
|
local_def_name_len - (ops_prefix_len + 1)) == 0) {
|
||||||
(residual[local_def_name_len] == ':' &&
|
if (residual[local_def_name_len - (ops_prefix_len + 1)] == '\0' ||
|
||||||
residual[local_def_name_len + 1] == '\0')) {
|
(residual[local_def_name_len - (ops_prefix_len + 1)] == ':' &&
|
||||||
|
residual[local_def_name_len - ops_prefix_len] == '\0')) {
|
||||||
/*
|
/*
|
||||||
* If we got a default cache name from KCM and the requested default
|
* If we got a default cache name from KCM and the requested default
|
||||||
* cache does not exist, use the former.
|
* cache does not exist, use the former.
|
||||||
*/
|
*/
|
||||||
if (def_name && kcm_stat(context, residual))
|
if (kcm_def_name && kcm_stat(context, residual))
|
||||||
residual = def_name + ops_prefix_len + 1;
|
residual = kcm_def_name + ops_prefix_len + 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -235,10 +230,10 @@ kcm_alloc(krb5_context context,
|
|||||||
|
|
||||||
if (residual == NULL && sub == NULL) {
|
if (residual == NULL && sub == NULL) {
|
||||||
/* Use the default cache name, either from KCM or local default */
|
/* Use the default cache name, either from KCM or local default */
|
||||||
if (def_name)
|
if (kcm_def_name)
|
||||||
residual = def_name + ops_prefix_len + 1;
|
residual = kcm_def_name + ops_prefix_len + 1;
|
||||||
else if (default_cc_name_is_ours)
|
else
|
||||||
residual = local_def_name;
|
residual = local_def_name + ops_prefix_len + 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (residual) {
|
if (residual) {
|
||||||
@@ -255,7 +250,8 @@ kcm_alloc(krb5_context context,
|
|||||||
|
|
||||||
k = calloc(1, sizeof(*k));
|
k = calloc(1, sizeof(*k));
|
||||||
if (k == NULL) {
|
if (k == NULL) {
|
||||||
free(def_name);
|
free(local_def_name);
|
||||||
|
free(kcm_def_name);
|
||||||
return krb5_enomem(context);
|
return krb5_enomem(context);
|
||||||
}
|
}
|
||||||
k->name = NULL;
|
k->name = NULL;
|
||||||
@@ -284,12 +280,14 @@ kcm_alloc(krb5_context context,
|
|||||||
residual, sub);
|
residual, sub);
|
||||||
}
|
}
|
||||||
if (aret == -1 || k->name == NULL) {
|
if (aret == -1 || k->name == NULL) {
|
||||||
free(def_name);
|
free(local_def_name);
|
||||||
|
free(kcm_def_name);
|
||||||
free(k);
|
free(k);
|
||||||
return krb5_enomem(context);
|
return krb5_enomem(context);
|
||||||
}
|
}
|
||||||
|
|
||||||
free(def_name);
|
free(local_def_name);
|
||||||
|
free(kcm_def_name);
|
||||||
(*id)->data.data = k;
|
(*id)->data.data = k;
|
||||||
(*id)->data.length = sizeof(*k);
|
(*id)->data.length = sizeof(*k);
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user