gsskrb5: fix _gssapi_wrap_iov_length_cfx() - there's more than just krb5 overhead...
metze Signed-off-by: Love Hornquist Astrand <lha@h5l.org>
This commit is contained in:

committed by
Love Hornquist Astrand

parent
1a0423fd3d
commit
f286dd5d64
@@ -937,9 +937,16 @@ _gssapi_wrap_iov_length_cfx(OM_uint32 *minor_status,
|
||||
gss_iov_buffer_desc *iov,
|
||||
int iov_count)
|
||||
{
|
||||
OM_uint32 major_status;
|
||||
size_t size;
|
||||
int i;
|
||||
size_t *padding = NULL;
|
||||
gss_iov_buffer_desc *header = NULL;
|
||||
gss_iov_buffer_desc *padding = NULL;
|
||||
gss_iov_buffer_desc *trailer = NULL;
|
||||
size_t gsshsize = 0;
|
||||
size_t gsstsize = 0;
|
||||
size_t k5hsize = 0;
|
||||
size_t k5tsize = 0;
|
||||
|
||||
GSSAPI_KRB5_INIT (&context);
|
||||
*minor_status = 0;
|
||||
@@ -952,21 +959,25 @@ _gssapi_wrap_iov_length_cfx(OM_uint32 *minor_status,
|
||||
size += iov[i].buffer.length;
|
||||
break;
|
||||
case GSS_IOV_BUFFER_TYPE_HEADER:
|
||||
*minor_status = krb5_crypto_length(context, ctx->crypto, KRB5_CRYPTO_TYPE_HEADER, &iov[i].buffer.length);
|
||||
if (*minor_status)
|
||||
if (header != NULL) {
|
||||
*minor_status = 0;
|
||||
return GSS_S_FAILURE;
|
||||
}
|
||||
header = &iov[i];
|
||||
break;
|
||||
case GSS_IOV_BUFFER_TYPE_TRAILER:
|
||||
*minor_status = krb5_crypto_length(context, ctx->crypto, KRB5_CRYPTO_TYPE_TRAILER, &iov[i].buffer.length);
|
||||
if (*minor_status)
|
||||
if (trailer != NULL) {
|
||||
*minor_status = 0;
|
||||
return GSS_S_FAILURE;
|
||||
}
|
||||
trailer = &iov[i];
|
||||
break;
|
||||
case GSS_IOV_BUFFER_TYPE_PADDING:
|
||||
if (padding != NULL) {
|
||||
*minor_status = 0;
|
||||
return GSS_S_FAILURE;
|
||||
}
|
||||
padding = &iov[i].buffer.length;
|
||||
padding = &iov[i];
|
||||
break;
|
||||
case GSS_IOV_BUFFER_TYPE_SIGN_ONLY:
|
||||
break;
|
||||
@@ -975,15 +986,83 @@ _gssapi_wrap_iov_length_cfx(OM_uint32 *minor_status,
|
||||
return GSS_S_FAILURE;
|
||||
}
|
||||
}
|
||||
|
||||
major_status = _gk_verify_buffers(minor_status, ctx, header, padding, trailer);
|
||||
if (major_status != GSS_S_COMPLETE) {
|
||||
return major_status;
|
||||
}
|
||||
|
||||
if (conf_req_flag) {
|
||||
size_t k5psize = 0;
|
||||
size_t k5pbase = 0;
|
||||
size_t k5bsize = 0;
|
||||
size_t ec = 0;
|
||||
|
||||
size += sizeof(gss_cfx_wrap_token_desc);
|
||||
|
||||
*minor_status = krb5_crypto_length(context, ctx->crypto,
|
||||
KRB5_CRYPTO_TYPE_HEADER,
|
||||
&k5hsize);
|
||||
if (*minor_status)
|
||||
return GSS_S_FAILURE;
|
||||
|
||||
*minor_status = krb5_crypto_length(context, ctx->crypto,
|
||||
KRB5_CRYPTO_TYPE_TRAILER,
|
||||
&k5tsize);
|
||||
if (*minor_status)
|
||||
return GSS_S_FAILURE;
|
||||
|
||||
*minor_status = krb5_crypto_length(context, ctx->crypto,
|
||||
KRB5_CRYPTO_TYPE_PADDING,
|
||||
&k5pbase);
|
||||
if (*minor_status)
|
||||
return GSS_S_FAILURE;
|
||||
|
||||
if (k5pbase > 1) {
|
||||
k5psize = k5pbase - (size % k5pbase);
|
||||
} else {
|
||||
k5psize = 0;
|
||||
}
|
||||
|
||||
if (k5psize == 0 && IS_DCE_STYLE(ctx)) {
|
||||
*minor_status = krb5_crypto_getblocksize(context, ctx->crypto,
|
||||
&k5bsize);
|
||||
if (*minor_status)
|
||||
return GSS_S_FAILURE;
|
||||
|
||||
ec = k5bsize;
|
||||
} else {
|
||||
ec = k5psize;
|
||||
}
|
||||
|
||||
gsshsize = sizeof(gss_cfx_wrap_token_desc) + k5hsize;
|
||||
gsstsize = sizeof(gss_cfx_wrap_token_desc) + ec + k5tsize;
|
||||
} else {
|
||||
*minor_status = krb5_crypto_length(context, ctx->crypto,
|
||||
KRB5_CRYPTO_TYPE_CHECKSUM,
|
||||
&k5tsize);
|
||||
if (*minor_status)
|
||||
return GSS_S_FAILURE;
|
||||
|
||||
gsshsize = sizeof(gss_cfx_wrap_token_desc);
|
||||
gsstsize = k5tsize;
|
||||
}
|
||||
|
||||
if (trailer != NULL) {
|
||||
trailer->buffer.length = gsstsize;
|
||||
} else {
|
||||
gsshsize += gsstsize;
|
||||
}
|
||||
|
||||
header->buffer.length = gsshsize;
|
||||
|
||||
if (padding) {
|
||||
size_t pad;
|
||||
krb5_crypto_length(context, ctx->crypto, KRB5_CRYPTO_TYPE_PADDING, &pad);
|
||||
if (pad > 1) {
|
||||
*padding = pad - (size % pad);
|
||||
if (*padding == pad)
|
||||
*padding = 0;
|
||||
} else
|
||||
*padding = 0;
|
||||
/* padding is done via EC and is contained in the header or trailer */
|
||||
padding->buffer.length = 0;
|
||||
}
|
||||
|
||||
if (conf_state) {
|
||||
*conf_state = conf_req_flag;
|
||||
}
|
||||
|
||||
return GSS_S_COMPLETE;
|
||||
|
Reference in New Issue
Block a user