kdc: avoid re-encoding KDC-REQ-BODY

Use --preserve-binary=KDC-REQ-BODY option to ASN.1 compiler to avoid
re-encoding KDC-REQ-BODYs for verification in GSS preauth, TGS and PKINIT.
This commit is contained in:
Luke Howard
2021-09-13 13:50:45 +10:00
parent 908ef18c9f
commit ebfd48e40a
5 changed files with 8 additions and 56 deletions

View File

@@ -357,7 +357,6 @@ fast_unwrap_request(astgs_request_t r)
krb5_keyblock armorkey; krb5_keyblock armorkey;
krb5_error_code ret; krb5_error_code ret;
krb5_ap_req ap_req; krb5_ap_req ap_req;
unsigned char *buf = NULL;
KrbFastReq fastreq; KrbFastReq fastreq;
size_t len, size; size_t len, size;
krb5_data data; krb5_data data;
@@ -476,18 +475,10 @@ fast_unwrap_request(astgs_request_t r)
krb5_free_keyblock_contents(r->context, &armorkey); krb5_free_keyblock_contents(r->context, &armorkey);
/* verify req-checksum of the outer body */ /* verify req-checksum of the outer body */
ASN1_MALLOC_ENCODE(KDC_REQ_BODY, buf, len, &r->req.req_body, &size, ret);
if (ret)
goto out;
if (size != len) {
ret = KRB5KDC_ERR_PREAUTH_FAILED;
goto out;
}
ret = krb5_verify_checksum(r->context, r->armor_crypto, ret = krb5_verify_checksum(r->context, r->armor_crypto,
KRB5_KU_FAST_REQ_CHKSUM, KRB5_KU_FAST_REQ_CHKSUM,
buf, len, r->req.req_body._save.data,
r->req.req_body._save.length,
&fxreq.u.armored_data.req_checksum); &fxreq.u.armored_data.req_checksum);
if (ret) { if (ret) {
kdc_log(r->context, r->config, 2, kdc_log(r->context, r->config, 2,
@@ -548,7 +539,6 @@ fast_unwrap_request(astgs_request_t r)
krb5_free_principal(r->context, armor_server); krb5_free_principal(r->context, armor_server);
if(armor_user) if(armor_user)
_kdc_free_ent(r->context, armor_user); _kdc_free_ent(r->context, armor_user);
free(buf);
return ret; return ret;
} }

View File

@@ -190,7 +190,6 @@ _kdc_gss_rd_padata(astgs_request_t r,
int *open) int *open)
{ {
krb5_error_code ret; krb5_error_code ret;
size_t size;
OM_uint32 minor; OM_uint32 minor;
gss_client_params *gcp = NULL; gss_client_params *gcp = NULL;
@@ -230,12 +229,7 @@ _kdc_gss_rd_padata(astgs_request_t r,
goto out; goto out;
_krb5_gss_data_to_buffer(&pa->padata_value, &input_token); _krb5_gss_data_to_buffer(&pa->padata_value, &input_token);
_krb5_gss_data_to_buffer(&r->req.req_body._save, &cb.application_data);
ASN1_MALLOC_ENCODE(KDC_REQ_BODY, cb.application_data.value,
cb.application_data.length, &r->req.req_body,
&size, ret);
heim_assert(ret || size == cb.application_data.length,
"internal asn1 encoder error");
gcp->major = gss_accept_sec_context(&gcp->minor, gcp->major = gss_accept_sec_context(&gcp->minor,
&gcp->context_handle, &gcp->context_handle,
@@ -263,7 +257,6 @@ _kdc_gss_rd_padata(astgs_request_t r,
out: out:
gss_release_cred(&minor, &cred); gss_release_cred(&minor, &cred);
gss_release_buffer(&minor, &cb.application_data);
if (gcp && gcp->major != GSS_S_NO_CONTEXT) if (gcp && gcp->major != GSS_S_NO_CONTEXT)
*pgcp = gcp; *pgcp = gcp;

View File

@@ -1081,9 +1081,6 @@ tgs_check_authenticator(krb5_context context,
krb5_keyblock *key) krb5_keyblock *key)
{ {
krb5_authenticator auth; krb5_authenticator auth;
size_t len = 0;
unsigned char *buf;
size_t buf_size;
krb5_error_code ret; krb5_error_code ret;
krb5_crypto crypto; krb5_crypto crypto;
@@ -1109,25 +1106,9 @@ tgs_check_authenticator(krb5_context context,
goto out; goto out;
} }
/* XXX should not re-encode this */
ASN1_MALLOC_ENCODE(KDC_REQ_BODY, buf, buf_size, b, &len, ret);
if(ret){
const char *msg = krb5_get_error_message(context, ret);
kdc_log(context, config, 4, "Failed to encode KDC-REQ-BODY: %s", msg);
krb5_free_error_message(context, msg);
goto out;
}
if(buf_size != len) {
free(buf);
kdc_log(context, config, 4, "Internal error in ASN.1 encoder");
*e_text = "KDC internal error";
ret = KRB5KRB_ERR_GENERIC;
goto out;
}
ret = krb5_crypto_init(context, key, 0, &crypto); ret = krb5_crypto_init(context, key, 0, &crypto);
if (ret) { if (ret) {
const char *msg = krb5_get_error_message(context, ret); const char *msg = krb5_get_error_message(context, ret);
free(buf);
kdc_log(context, config, 4, "krb5_crypto_init failed: %s", msg); kdc_log(context, config, 4, "krb5_crypto_init failed: %s", msg);
krb5_free_error_message(context, msg); krb5_free_error_message(context, msg);
goto out; goto out;
@@ -1135,10 +1116,9 @@ tgs_check_authenticator(krb5_context context,
ret = krb5_verify_checksum(context, ret = krb5_verify_checksum(context,
crypto, crypto,
KRB5_KU_TGS_REQ_AUTH_CKSUM, KRB5_KU_TGS_REQ_AUTH_CKSUM,
buf, b->_save.data,
len, b->_save.length,
auth->cksum); auth->cksum);
free(buf);
krb5_crypto_destroy(context, crypto); krb5_crypto_destroy(context, crypto);
if(ret){ if(ret){
const char *msg = krb5_get_error_message(context, ret); const char *msg = krb5_get_error_message(context, ret);

View File

@@ -113,10 +113,7 @@ pk_check_pkauthenticator(krb5_context context,
PKAuthenticator *a, PKAuthenticator *a,
const KDC_REQ *req) const KDC_REQ *req)
{ {
u_char *buf = NULL;
size_t buf_size;
krb5_error_code ret; krb5_error_code ret;
size_t len = 0;
krb5_timestamp now; krb5_timestamp now;
Checksum checksum; Checksum checksum;
@@ -128,22 +125,13 @@ pk_check_pkauthenticator(krb5_context context,
return KRB5KRB_AP_ERR_SKEW; return KRB5KRB_AP_ERR_SKEW;
} }
ASN1_MALLOC_ENCODE(KDC_REQ_BODY, buf, buf_size, &req->req_body, &len, ret);
if (ret) {
krb5_clear_error_message(context);
return ret;
}
if (buf_size != len)
krb5_abortx(context, "Internal error in ASN.1 encoder");
ret = krb5_create_checksum(context, ret = krb5_create_checksum(context,
NULL, NULL,
0, 0,
CKSUMTYPE_SHA1, CKSUMTYPE_SHA1,
buf, req->req_body._save.data,
len, req->req_body._save.length,
&checksum); &checksum);
free(buf);
if (ret) { if (ret) {
krb5_clear_error_message(context); krb5_clear_error_message(context);
return ret; return ret;

View File

@@ -4,3 +4,4 @@
--sequence=METHOD-DATA --sequence=METHOD-DATA
--sequence=ETYPE-INFO --sequence=ETYPE-INFO
--sequence=ETYPE-INFO2 --sequence=ETYPE-INFO2
--preserve-binary=KDC-REQ-BODY