kdc: allow anonymous AS requests with long-term keys

RFC8062 section 4.1 allows clients with long-term KDC keys to set the anonymous
flag; in this case their identity is authenticated but the returned ticket
contains the anonymous principal name as the client name.

kdc: allow authenticated anonymous PKINIT

The KDC PKINIT code conflated the checks for authenticated and unauthenticated
anonymous by only looking at the anonymous KDC request option.
This commit is contained in:
Luke Howard
2019-05-02 17:05:25 +10:00
committed by Jeffrey Altman
parent 5c8f48495e
commit 63557427e0
2 changed files with 11 additions and 19 deletions

View File

@@ -597,12 +597,6 @@ pa_enc_ts_validate(kdc_request_t r, const PA_DATA *pa)
Key *pa_key; Key *pa_key;
char *str; char *str;
if (_kdc_is_anon_request(&r->req.req_body)) {
ret = KRB5KRB_AP_ERR_BAD_INTEGRITY;
_kdc_set_e_text(r, "ENC-TS doesn't support anon");
goto out;
}
ret = decode_EncryptedData(pa->padata_value.data, ret = decode_EncryptedData(pa->padata_value.data,
pa->padata_value.length, pa->padata_value.length,
&enc_data, &enc_data,
@@ -1774,16 +1768,10 @@ _kdc_as_rep(kdc_request_t r,
if (_kdc_is_anonymous(context, r->client_princ)) { if (_kdc_is_anonymous(context, r->client_princ)) {
if (!_kdc_is_anon_request(b)) { if (!_kdc_is_anon_request(b)) {
kdc_log(context, config, 0, "Anonymous ticket w/o anonymous flag"); kdc_log(context, config, 0, "Anonymous client w/o anonymous flag");
ret = KRB5KDC_ERR_BADOPTION; ret = KRB5KDC_ERR_BADOPTION;
goto out; goto out;
} }
} else if (_kdc_is_anon_request(b)) {
kdc_log(context, config, 0,
"Request for a anonymous ticket with non "
"anonymous client name: %s", r->client_name);
ret = KRB5KDC_ERR_C_PRINCIPAL_UNKNOWN;
goto out;
} }
/* /*
@@ -2021,7 +2009,9 @@ _kdc_as_rep(kdc_request_t r,
ret = copy_Realm(&r->client_princ->realm, &rep.crealm); ret = copy_Realm(&r->client_princ->realm, &rep.crealm);
if (ret) if (ret)
goto out; goto out;
if (f.canonicalize || r->client->entry.flags.force_canonicalize) if (_kdc_is_anon_request(b))
ret = _kdc_make_anonymous_principalname(&rep.cname);
else if (f.canonicalize || r->client->entry.flags.force_canonicalize)
ret = _krb5_principal2principalname(&rep.cname, r->client->entry.principal); ret = _krb5_principal2principalname(&rep.cname, r->client->entry.principal);
else else
ret = _krb5_principal2principalname(&rep.cname, r->client_princ); ret = _krb5_principal2principalname(&rep.cname, r->client_princ);

View File

@@ -477,7 +477,7 @@ _kdc_pk_rd_padata(krb5_context context,
type = "PK-INIT-Win2k"; type = "PK-INIT-Win2k";
if (_kdc_is_anon_request(&req->req_body)) { if (_kdc_is_anonymous(context, client->entry.principal)) {
ret = KRB5_KDC_ERR_PUBLIC_KEY_ENCRYPTION_NOT_SUPPORTED; ret = KRB5_KDC_ERR_PUBLIC_KEY_ENCRYPTION_NOT_SUPPORTED;
krb5_set_error_message(context, ret, krb5_set_error_message(context, ret,
"Anon not supported in RSA mode"); "Anon not supported in RSA mode");
@@ -623,7 +623,7 @@ _kdc_pk_rd_padata(krb5_context context,
hx509_certs signer_certs; hx509_certs signer_certs;
int flags = HX509_CMS_VS_ALLOW_DATA_OID_MISMATCH; /* BTMM */ int flags = HX509_CMS_VS_ALLOW_DATA_OID_MISMATCH; /* BTMM */
if (_kdc_is_anon_request(&req->req_body)) if (_kdc_is_anonymous(context, client->entry.principal))
flags |= HX509_CMS_VS_ALLOW_ZERO_SIGNER; flags |= HX509_CMS_VS_ALLOW_ZERO_SIGNER;
ret = hx509_cms_verify_signed(context->hx509ctx, ret = hx509_cms_verify_signed(context->hx509ctx,
@@ -708,7 +708,7 @@ _kdc_pk_rd_padata(krb5_context context,
goto out; goto out;
} }
if (_kdc_is_anon_request(&req->req_body) && if (_kdc_is_anonymous(context, client->entry.principal) &&
ap.clientPublicValue == NULL) { ap.clientPublicValue == NULL) {
free_AuthPack(&ap); free_AuthPack(&ap);
ret = KRB5_KDC_ERR_PUBLIC_KEY_ENCRYPTION_NOT_SUPPORTED; ret = KRB5_KDC_ERR_PUBLIC_KEY_ENCRYPTION_NOT_SUPPORTED;
@@ -1676,8 +1676,10 @@ _kdc_pk_check_client(krb5_context context,
size_t i; size_t i;
if (cp->cert == NULL) { if (cp->cert == NULL) {
if (!_kdc_is_anonymous(context, client->entry.principal))
return KRB5KDC_ERR_BADOPTION;
*subject_name = strdup("anonymous client client"); *subject_name = strdup("<unauthenticated anonymous client>");
if (*subject_name == NULL) if (*subject_name == NULL)
return ENOMEM; return ENOMEM;
return 0; return 0;