#include "k5-int.h"
#include <CommonCrypto/CommonCryptor.h>
#include "des_int.h"
static krb5_error_code
k5_des_docrypt(const krb5_keyblock *key, const krb5_data *ivec,
const krb5_data *input, krb5_data *output, CCOperation enc)
{
CCCryptorStatus ret;
size_t movedData;
if (key->length != 8)
return(KRB5_BAD_KEYSIZE);
if ((input->length%8) != 0)
return(KRB5_BAD_MSIZE);
if (ivec && (ivec->length != 8))
return(KRB5_BAD_MSIZE);
if (input->length != output->length)
return(KRB5_BAD_MSIZE);
ret = CCCrypt(enc,
kCCAlgorithmDES,
0,
key->contents,
key->length,
ivec != NULL ? ivec->data : (char *)mit_des_zeroblock,
input->data,
input->length,
output->data,
output->length,
&movedData);
if (ret)
return(KRB5_CRYPTO_INTERNAL);
return(0);
}
static krb5_error_code
k5_des_encrypt(const krb5_keyblock *key, const krb5_data *ivec,
const krb5_data *input, krb5_data *output)
{
return(k5_des_docrypt(key, ivec, input, output, kCCEncrypt));
}
static krb5_error_code
k5_des_decrypt(const krb5_keyblock *key, const krb5_data *ivec,
const krb5_data *input, krb5_data *output)
{
return(k5_des_docrypt(key, ivec, input, output, kCCDecrypt));
}
static krb5_error_code
k5_des_make_key(const krb5_data *randombits, krb5_keyblock *key)
{
if (key->length != 8)
return(KRB5_BAD_KEYSIZE);
if (randombits->length != 7)
return(KRB5_CRYPTO_INTERNAL);
key->magic = KV5M_KEYBLOCK;
key->length = 8;
memcpy(key->contents, randombits->data, randombits->length);
key->contents[7] = (((key->contents[0]&1)<<1) | ((key->contents[1]&1)<<2) |
((key->contents[2]&1)<<3) | ((key->contents[3]&1)<<4) |
((key->contents[4]&1)<<5) | ((key->contents[5]&1)<<6) |
((key->contents[6]&1)<<7));
mit_des_fixup_key_parity(key->contents);
return(0);
}
const struct krb5_enc_provider krb5int_enc_des = {
8,
7, 8,
k5_des_encrypt,
k5_des_decrypt,
k5_des_make_key,
krb5int_des_init_state,
krb5int_default_free_state
};
unsigned long
k5_des_cbc_cksum(const krb5_octet *in, krb5_octet *out,
unsigned long length, const krb5_octet *key,
const krb5_octet *ivec)
{
CCCryptorStatus ret;
unsigned char buf[8];
const unsigned char *ip;
size_t i, len, movedData;
memcpy(buf, ivec, sizeof(buf));
ip = (const unsigned char *)in;
len = length;
while (len > 0) {
for (i = 0; i < len && i < 8; i++)
buf[i] ^= (*ip++);
len -= i;
ret = CCCrypt(kCCEncrypt,
kCCAlgorithmDES,
kCCOptionECBMode,
key,
8,
NULL,
buf,
sizeof(buf),
buf,
sizeof(buf),
&movedData);
if (ret)
return(KRB5_CRYPTO_INTERNAL);
}
memcpy(out, buf, sizeof(buf));
#if 0
return right & 0xFFFFFFFFUL;
#endif
return 0;
}