From a7781443df5535f28b0770251950cf65ffeee33c Mon Sep 17 00:00:00 2001 From: Greg Hudson Date: Wed, 2 Dec 2009 19:52:54 +0000 Subject: [PATCH] Clean up the AES enc_provider code a bit. Chiefly, work with unsigned char blocks, casting input->data and output->data once each upon entry to the non-IOV encrypt and decrypt functions, rather than casting our working buffers each time we need to work with an outside function. git-svn-id: svn://anonsvn.mit.edu/krb5/trunk@23428 dc483132-0cff-0310-8789-dd5450dbe970 --- src/lib/crypto/builtin/enc_provider/aes.c | 144 ++++++++++------------ 1 file changed, 64 insertions(+), 80 deletions(-) diff --git a/src/lib/crypto/builtin/enc_provider/aes.c b/src/lib/crypto/builtin/enc_provider/aes.c index cde5bb551..cfa364310 100644 --- a/src/lib/crypto/builtin/enc_provider/aes.c +++ b/src/lib/crypto/builtin/enc_provider/aes.c @@ -31,55 +31,24 @@ #include #include -#if 0 -aes_rval aes_blk_len(unsigned int blen, aes_ctx cx[1]); -aes_rval aes_enc_key(const unsigned char in_key[], unsigned int klen, aes_ctx cx[1]); -aes_rval aes_enc_blk(const unsigned char in_blk[], unsigned char out_blk[], const aes_ctx cx[1]); -aes_rval aes_dec_key(const unsigned char in_key[], unsigned int klen, aes_ctx cx[1]); -aes_rval aes_dec_blk(const unsigned char in_blk[], unsigned char out_blk[], const aes_ctx cx[1]); -#endif - #define CHECK_SIZES 0 -#if 0 -static void printd (const char *descr, krb5_data *d) { - int i, j; - const int r = 16; - - printf("%s:", descr); - - for (i = 0; i < d->length; i += r) { - printf("\n %04x: ", i); - for (j = i; j < i + r && j < d->length; j++) - printf(" %02x", 0xff & d->data[j]); -#ifdef SHOW_TEXT - for (; j < i + r; j++) - printf(" "); - printf(" "); - for (j = i; j < i + r && j < d->length; j++) { - int c = 0xff & d->data[j]; - printf("%c", isprint(c) ? c : '.'); - } -#endif - } - printf("\n"); -} -#endif - -static inline void enc(char *out, const char *in, aes_ctx *ctx) +static inline void +enc(unsigned char *out, const unsigned char *in, aes_ctx *ctx) { - if (aes_enc_blk((const unsigned char *)in, (unsigned char *)out, ctx) - != aes_good) + if (aes_enc_blk(in, out, ctx) != aes_good) abort(); } -static inline void dec(char *out, const char *in, aes_ctx *ctx) + +static inline void +dec(unsigned char *out, const unsigned char *in, aes_ctx *ctx) { - if (aes_dec_blk((const unsigned char *)in, (unsigned char *)out, ctx) - != aes_good) + if (aes_dec_blk(in, out, ctx) != aes_good) abort(); } -static void xorblock(char *out, const char *in) +static void +xorblock(unsigned char *out, const unsigned char *in) { int z; for (z = 0; z < BLOCK_SIZE; z++) @@ -91,8 +60,10 @@ krb5int_aes_encrypt(krb5_key key, const krb5_data *ivec, const krb5_data *input, krb5_data *output) { aes_ctx ctx; - char tmp[BLOCK_SIZE], tmp2[BLOCK_SIZE], tmp3[BLOCK_SIZE]; + unsigned char tmp[BLOCK_SIZE], tmp2[BLOCK_SIZE], tmp3[BLOCK_SIZE]; int nblocks = 0, blockno; + const unsigned char *idata = (const unsigned char *) input->data; + unsigned char *odata = (unsigned char *) output->data; /* CHECK_SIZES; */ @@ -109,31 +80,31 @@ krb5int_aes_encrypt(krb5_key key, const krb5_data *ivec, if (nblocks == 1) { /* XXX Used for DK function. */ - enc(output->data, input->data, &ctx); + enc(odata, idata, &ctx); } else { unsigned int nleft; for (blockno = 0; blockno < nblocks - 2; blockno++) { - xorblock(tmp, input->data + blockno * BLOCK_SIZE); + xorblock(tmp, idata + blockno * BLOCK_SIZE); enc(tmp2, tmp, &ctx); - memcpy(output->data + blockno * BLOCK_SIZE, tmp2, BLOCK_SIZE); + memcpy(odata + blockno * BLOCK_SIZE, tmp2, BLOCK_SIZE); /* Set up for next block. */ memcpy(tmp, tmp2, BLOCK_SIZE); } /* Do final CTS step for last two blocks (the second of which may or may not be incomplete). */ - xorblock(tmp, input->data + (nblocks - 2) * BLOCK_SIZE); + xorblock(tmp, idata + (nblocks - 2) * BLOCK_SIZE); enc(tmp2, tmp, &ctx); nleft = input->length - (nblocks - 1) * BLOCK_SIZE; - memcpy(output->data + (nblocks - 1) * BLOCK_SIZE, tmp2, nleft); + memcpy(odata + (nblocks - 1) * BLOCK_SIZE, tmp2, nleft); memcpy(tmp, tmp2, BLOCK_SIZE); memset(tmp3, 0, sizeof(tmp3)); - memcpy(tmp3, input->data + (nblocks - 1) * BLOCK_SIZE, nleft); + memcpy(tmp3, idata + (nblocks - 1) * BLOCK_SIZE, nleft); xorblock(tmp, tmp3); enc(tmp2, tmp, &ctx); - memcpy(output->data + (nblocks - 2) * BLOCK_SIZE, tmp2, BLOCK_SIZE); + memcpy(odata + (nblocks - 2) * BLOCK_SIZE, tmp2, BLOCK_SIZE); if (ivec) memcpy(ivec->data, tmp2, BLOCK_SIZE); } @@ -146,8 +117,10 @@ krb5int_aes_decrypt(krb5_key key, const krb5_data *ivec, const krb5_data *input, krb5_data *output) { aes_ctx ctx; - char tmp[BLOCK_SIZE], tmp2[BLOCK_SIZE], tmp3[BLOCK_SIZE]; + unsigned char tmp[BLOCK_SIZE], tmp2[BLOCK_SIZE], tmp3[BLOCK_SIZE]; int nblocks = 0, blockno; + const unsigned char *idata = (const unsigned char *) input->data; + unsigned char *odata = (unsigned char *) output->data; CHECK_SIZES; @@ -165,26 +138,26 @@ krb5int_aes_decrypt(krb5_key key, const krb5_data *ivec, if (nblocks == 1) { if (input->length < BLOCK_SIZE) abort(); - dec(output->data, input->data, &ctx); + dec(odata, idata, &ctx); } else { for (blockno = 0; blockno < nblocks - 2; blockno++) { - dec(tmp2, input->data + blockno * BLOCK_SIZE, &ctx); + dec(tmp2, idata + blockno * BLOCK_SIZE, &ctx); xorblock(tmp2, tmp); - memcpy(output->data + blockno * BLOCK_SIZE, tmp2, BLOCK_SIZE); - memcpy(tmp, input->data + blockno * BLOCK_SIZE, BLOCK_SIZE); + memcpy(odata + blockno * BLOCK_SIZE, tmp2, BLOCK_SIZE); + memcpy(tmp, idata + blockno * BLOCK_SIZE, BLOCK_SIZE); } /* Do last two blocks, the second of which (next-to-last block of plaintext) may be incomplete. */ - dec(tmp2, input->data + (nblocks - 2) * BLOCK_SIZE, &ctx); + dec(tmp2, idata + (nblocks - 2) * BLOCK_SIZE, &ctx); /* Set tmp3 to last ciphertext block, padded. */ memset(tmp3, 0, sizeof(tmp3)); - memcpy(tmp3, input->data + (nblocks - 1) * BLOCK_SIZE, + memcpy(tmp3, idata + (nblocks - 1) * BLOCK_SIZE, input->length - (nblocks - 1) * BLOCK_SIZE); /* Set tmp2 to last (possibly partial) plaintext block, and save it. */ xorblock(tmp2, tmp3); - memcpy(output->data + (nblocks - 1) * BLOCK_SIZE, tmp2, + memcpy(odata + (nblocks - 1) * BLOCK_SIZE, tmp2, input->length - (nblocks - 1) * BLOCK_SIZE); /* Maybe keep the trailing part, and copy in the last ciphertext block. */ @@ -193,10 +166,9 @@ krb5int_aes_decrypt(krb5_key key, const krb5_data *ivec, ciphertext. */ dec(tmp3, tmp2, &ctx); xorblock(tmp3, tmp); - memcpy(output->data + (nblocks - 2) * BLOCK_SIZE, tmp3, BLOCK_SIZE); + memcpy(odata + (nblocks - 2) * BLOCK_SIZE, tmp3, BLOCK_SIZE); if (ivec) - memcpy(ivec->data, input->data + (nblocks - 2) * BLOCK_SIZE, - BLOCK_SIZE); + memcpy(ivec->data, idata + (nblocks - 2) * BLOCK_SIZE, BLOCK_SIZE); } return 0; @@ -209,7 +181,7 @@ krb5int_aes_encrypt_iov(krb5_key key, size_t num_data) { aes_ctx ctx; - char tmp[BLOCK_SIZE], tmp2[BLOCK_SIZE]; + unsigned char tmp[BLOCK_SIZE], tmp2[BLOCK_SIZE]; int nblocks = 0, blockno; size_t input_length, i; @@ -234,20 +206,22 @@ krb5int_aes_encrypt_iov(krb5_key key, assert(nblocks > 1); { - char blockN2[BLOCK_SIZE]; /* second last */ - char blockN1[BLOCK_SIZE]; /* last block */ + unsigned char blockN2[BLOCK_SIZE]; /* second last */ + unsigned char blockN1[BLOCK_SIZE]; /* last block */ struct iov_block_state input_pos, output_pos; IOV_BLOCK_STATE_INIT(&input_pos); IOV_BLOCK_STATE_INIT(&output_pos); for (blockno = 0; blockno < nblocks - 2; blockno++) { - char blockN[BLOCK_SIZE]; + unsigned char blockN[BLOCK_SIZE]; - krb5int_c_iov_get_block((unsigned char *)blockN, BLOCK_SIZE, data, num_data, &input_pos); + krb5int_c_iov_get_block(blockN, BLOCK_SIZE, data, num_data, + &input_pos); xorblock(tmp, blockN); enc(tmp2, tmp, &ctx); - krb5int_c_iov_put_block(data, num_data, (unsigned char *)tmp2, BLOCK_SIZE, &output_pos); + krb5int_c_iov_put_block(data, num_data, tmp2, BLOCK_SIZE, + &output_pos); /* Set up for next block. */ memcpy(tmp, tmp2, BLOCK_SIZE); @@ -258,8 +232,10 @@ krb5int_aes_encrypt_iov(krb5_key key, /* First, get the last two blocks */ memset(blockN1, 0, sizeof(blockN1)); /* pad last block with zeros */ - krb5int_c_iov_get_block((unsigned char *)blockN2, BLOCK_SIZE, data, num_data, &input_pos); - krb5int_c_iov_get_block((unsigned char *)blockN1, BLOCK_SIZE, data, num_data, &input_pos); + krb5int_c_iov_get_block(blockN2, BLOCK_SIZE, data, num_data, + &input_pos); + krb5int_c_iov_get_block(blockN1, BLOCK_SIZE, data, num_data, + &input_pos); /* Encrypt second last block */ xorblock(tmp, blockN2); @@ -273,8 +249,10 @@ krb5int_aes_encrypt_iov(krb5_key key, memcpy(blockN1, tmp2, BLOCK_SIZE); /* Put the last two blocks back into the iovec (reverse order) */ - krb5int_c_iov_put_block(data, num_data, (unsigned char *)blockN1, BLOCK_SIZE, &output_pos); - krb5int_c_iov_put_block(data, num_data, (unsigned char *)blockN2, BLOCK_SIZE, &output_pos); + krb5int_c_iov_put_block(data, num_data, blockN1, BLOCK_SIZE, + &output_pos); + krb5int_c_iov_put_block(data, num_data, blockN2, BLOCK_SIZE, + &output_pos); if (ivec != NULL) memcpy(ivec->data, blockN1, BLOCK_SIZE); @@ -290,7 +268,7 @@ krb5int_aes_decrypt_iov(krb5_key key, size_t num_data) { aes_ctx ctx; - char tmp[BLOCK_SIZE], tmp2[BLOCK_SIZE], tmp3[BLOCK_SIZE]; + unsigned char tmp[BLOCK_SIZE], tmp2[BLOCK_SIZE], tmp3[BLOCK_SIZE]; int nblocks = 0, blockno; unsigned int i; size_t input_length; @@ -318,20 +296,22 @@ krb5int_aes_decrypt_iov(krb5_key key, assert(nblocks > 1); { - char blockN2[BLOCK_SIZE]; /* second last */ - char blockN1[BLOCK_SIZE]; /* last block */ + unsigned char blockN2[BLOCK_SIZE]; /* second last */ + unsigned char blockN1[BLOCK_SIZE]; /* last block */ struct iov_block_state input_pos, output_pos; IOV_BLOCK_STATE_INIT(&input_pos); IOV_BLOCK_STATE_INIT(&output_pos); for (blockno = 0; blockno < nblocks - 2; blockno++) { - char blockN[BLOCK_SIZE]; + unsigned char blockN[BLOCK_SIZE]; - krb5int_c_iov_get_block((unsigned char *)blockN, BLOCK_SIZE, data, num_data, &input_pos); + krb5int_c_iov_get_block(blockN, BLOCK_SIZE, data, num_data, + &input_pos); dec(tmp2, blockN, &ctx); xorblock(tmp2, tmp); - krb5int_c_iov_put_block(data, num_data, (unsigned char *)tmp2, BLOCK_SIZE, &output_pos); + krb5int_c_iov_put_block(data, num_data, tmp2, BLOCK_SIZE, + &output_pos); memcpy(tmp, blockN, BLOCK_SIZE); } @@ -340,8 +320,10 @@ krb5int_aes_decrypt_iov(krb5_key key, /* First, get the last two encrypted blocks */ memset(blockN1, 0, sizeof(blockN1)); /* pad last block with zeros */ - krb5int_c_iov_get_block((unsigned char *)blockN2, BLOCK_SIZE, data, num_data, &input_pos); - krb5int_c_iov_get_block((unsigned char *)blockN1, BLOCK_SIZE, data, num_data, &input_pos); + krb5int_c_iov_get_block(blockN2, BLOCK_SIZE, data, num_data, + &input_pos); + krb5int_c_iov_get_block(blockN1, BLOCK_SIZE, data, num_data, + &input_pos); if (ivec != NULL) memcpy(ivec->data, blockN2, BLOCK_SIZE); @@ -362,8 +344,10 @@ krb5int_aes_decrypt_iov(krb5_key key, memcpy(blockN1, tmp3, BLOCK_SIZE); /* Put the last two blocks back into the iovec */ - krb5int_c_iov_put_block(data, num_data, (unsigned char *)blockN1, BLOCK_SIZE, &output_pos); - krb5int_c_iov_put_block(data, num_data, (unsigned char *)blockN2, BLOCK_SIZE, &output_pos); + krb5int_c_iov_put_block(data, num_data, blockN1, BLOCK_SIZE, + &output_pos); + krb5int_c_iov_put_block(data, num_data, blockN2, BLOCK_SIZE, + &output_pos); } return 0; @@ -374,7 +358,7 @@ krb5int_aes_init_state (const krb5_keyblock *key, krb5_keyusage usage, krb5_data *state) { state->length = 16; - state->data = (void *) malloc(16); + state->data = malloc(16); if (state->data == NULL) return ENOMEM; memset(state->data, 0, state->length); -- 2.26.2