Annotation of 43BSDReno/kerberosIV/des/pcbc_encrypt.c, revision 1.1

1.1     ! root        1: /*
        !             2:  * $Source: /afs/athena.mit.edu/astaff/project/kerberos/src/lib/des/RCS/pcbc_encrypt.c,v $
        !             3:  * $Author: jtkohl $
        !             4:  *
        !             5:  * Copyright 1985, 1986, 1987, 1988 by the Massachusetts Institute
        !             6:  * of Technology.
        !             7:  *
        !             8:  * For copying and distribution information, please see the file
        !             9:  * <mit-copyright.h>.
        !            10:  *
        !            11:  * These routines perform encryption and decryption using the DES
        !            12:  * private key algorithm, or else a subset of it-- fewer inner loops.
        !            13:  * ( AUTH_DES_ITER defaults to 16, may be less)
        !            14:  *
        !            15:  * Under U.S. law, this software may not be exported outside the US
        !            16:  * without license from the U.S. Commerce department.
        !            17:  *
        !            18:  * The key schedule is passed as an arg, as well as the cleartext or
        !            19:  * ciphertext.  The cleartext and ciphertext should be in host order.
        !            20:  *
        !            21:  * These routines form the library interface to the des facilities.
        !            22:  *
        !            23:  * spm 8/85    MIT project athena
        !            24:  */
        !            25: 
        !            26: #ifndef        lint
        !            27: static char rcsid_pcbc_encrypt_c[] =
        !            28: "$Id: pcbc_encrypt.c,v 4.11 90/01/02 13:46:30 jtkohl Exp $";
        !            29: #endif lint
        !            30: 
        !            31: #include <mit-copyright.h>
        !            32: #include <stdio.h>
        !            33: #include <des.h>
        !            34: #include "des_internal.h"
        !            35: 
        !            36: extern int des_debug;
        !            37: extern int des_debug_print();
        !            38: 
        !            39: /*
        !            40:  * pcbc_encrypt is an "error propagation chaining" encrypt operation
        !            41:  * for DES, similar to CBC, but that, on encryption, "xor"s the
        !            42:  * plaintext of block N with the ciphertext resulting from block N,
        !            43:  * then "xor"s that result with the plaintext of block N+1 prior to
        !            44:  * encrypting block N+1. (decryption the appropriate inverse.  This
        !            45:  * "pcbc" mode propagates a single bit error anywhere in either the
        !            46:  * cleartext or ciphertext chain all the way through to the end. In
        !            47:  * contrast, CBC mode limits a single bit error in the ciphertext to
        !            48:  * affect only the current (8byte) block and the subsequent block.
        !            49:  *
        !            50:  * performs pcbc error-propagation chaining operation by xor-ing block
        !            51:  * N+1 with both the plaintext (block N) and the ciphertext from block
        !            52:  * N.  Either encrypts from cleartext to ciphertext, if encrypt != 0
        !            53:  * or decrypts from ciphertext to cleartext, if encrypt == 0
        !            54:  *
        !            55:  * NOTE-- the output is ALWAYS an multiple of 8 bytes long.  If not
        !            56:  * enough space was provided, your program will get trashed.
        !            57:  *
        !            58:  * For encryption, the cleartext string is null padded, at the end, to
        !            59:  * an integral multiple of eight bytes.
        !            60:  *
        !            61:  * For decryption, the ciphertext will be used in integral multiples
        !            62:  * of 8 bytes, but only the first "length" bytes returned into the
        !            63:  * cleartext.
        !            64:  *
        !            65:  * This is NOT a standard mode of operation.
        !            66:  *
        !            67:  */
        !            68: 
        !            69: int
        !            70: des_pcbc_encrypt(in,out,length,key,iv,encrypt)
        !            71:     des_cblock *in;            /* >= length bytes of inputtext */
        !            72:     des_cblock *out;           /* >= length bytes of outputtext */
        !            73:     register long length;      /* in bytes */
        !            74:     int encrypt;               /* 0 ==> decrypt, else encrypt */
        !            75:     des_key_schedule key;              /* precomputed key schedule */
        !            76:     des_cblock *iv;            /* 8 bytes of ivec */
        !            77: {
        !            78:     register unsigned long *input = (unsigned long *) in;
        !            79:     register unsigned long *output = (unsigned long *) out;
        !            80:     register unsigned long *ivec = (unsigned long *) iv;
        !            81: 
        !            82:     unsigned long i,j;
        !            83:     static unsigned long t_input[2];
        !            84:     static unsigned long t_output[2];
        !            85:     static unsigned char *t_in_p;
        !            86:     static unsigned long xor_0, xor_1;
        !            87: 
        !            88:     t_in_p = (unsigned char *) t_input;
        !            89:     if (encrypt) {
        !            90: #ifdef MUSTALIGN
        !            91:        if ((long) ivec & 3) {
        !            92:            bcopy((char *)ivec++,(char *)&xor_0,sizeof(xor_0));
        !            93:            bcopy((char *)ivec,(char *)&xor_1,sizeof(xor_1));
        !            94:        }
        !            95:        else
        !            96: #endif
        !            97:        {
        !            98:            xor_0 = *ivec++;
        !            99:            xor_1 = *ivec;
        !           100:        }
        !           101: 
        !           102:        for (i = 0; length > 0; i++, length -= 8) {
        !           103:            /* get input */
        !           104: #ifdef MUSTALIGN
        !           105:            if ((long) input & 3) {
        !           106:                bcopy((char *)input,(char *)&t_input[0],sizeof(t_input[0]));
        !           107:                bcopy((char *)(input+1),(char *)&t_input[1],sizeof(t_input[1]));
        !           108:            }
        !           109:            else
        !           110: #endif
        !           111:            {
        !           112:                t_input[0] = *input;
        !           113:                t_input[1] = *(input+1);
        !           114:            }
        !           115: 
        !           116:            /* zero pad */
        !           117:            if (length < 8) {
        !           118:                for (j = length; j <= 7; j++)
        !           119:                    *(t_in_p+j)= 0;
        !           120:            }
        !           121: 
        !           122: #ifdef DEBUG
        !           123:            if (des_debug)
        !           124:                des_debug_print("clear",length,t_input[0],t_input[1]);
        !           125: #endif
        !           126:            /* do the xor for cbc into the temp */
        !           127:            t_input[0] ^= xor_0 ;
        !           128:            t_input[1] ^= xor_1 ;
        !           129:            /* encrypt */
        !           130:            (void) des_ecb_encrypt(t_input,t_output,key,encrypt);
        !           131: 
        !           132:            /*
        !           133:             * We want to XOR with both the plaintext and ciphertext
        !           134:             * of the previous block, before we write the output, in
        !           135:             * case both input and output are the same space.
        !           136:             */
        !           137: #ifdef MUSTALIGN
        !           138:            if ((long) input & 3) {
        !           139:                bcopy((char *)input++,(char *)&xor_0,sizeof(xor_0));
        !           140:                xor_0 ^= t_output[0];
        !           141:                bcopy((char *)input++,(char *)&xor_1,sizeof(xor_1));
        !           142:                xor_1 ^= t_output[1];
        !           143:            }
        !           144:            else
        !           145: #endif
        !           146:            {
        !           147:                xor_0 = *input++ ^ t_output[0];
        !           148:                xor_1 = *input++ ^ t_output[1];
        !           149:            }
        !           150: 
        !           151: 
        !           152:            /* copy temp output and save it for cbc */
        !           153: #ifdef MUSTALIGN
        !           154:            if ((long) output & 3) {
        !           155:                bcopy((char *)&t_output[0],(char *)output++,
        !           156:                      sizeof(t_output[0]));
        !           157:                bcopy((char *)&t_output[1],(char *)output++,
        !           158:                      sizeof(t_output[1]));
        !           159:            }
        !           160:            else
        !           161: #endif
        !           162:            {
        !           163:                *output++ = t_output[0];
        !           164:                *output++ = t_output[1];
        !           165:            }
        !           166: 
        !           167: #ifdef DEBUG
        !           168:            if (des_debug) {
        !           169:                des_debug_print("xor'ed",i,t_input[0],t_input[1]);
        !           170:                des_debug_print("cipher",i,t_output[0],t_output[1]);
        !           171:            }
        !           172: #endif
        !           173:        }
        !           174:        t_output[0] = 0;
        !           175:        t_output[1] = 0;
        !           176:        xor_0 = 0;
        !           177:        xor_1 = 0;
        !           178:        return 0;
        !           179:     }
        !           180: 
        !           181:     else {
        !           182:        /* decrypt */
        !           183: #ifdef MUSTALIGN
        !           184:        if ((long) ivec & 3) {
        !           185:            bcopy((char *)ivec++,(char *)&xor_0,sizeof(xor_0));
        !           186:            bcopy((char *)ivec,(char *)&xor_1,sizeof(xor_1));
        !           187:        }
        !           188:        else
        !           189: #endif
        !           190:        {
        !           191:            xor_0 = *ivec++;
        !           192:            xor_1 = *ivec;
        !           193:        }
        !           194: 
        !           195:        for (i = 0; length > 0; i++, length -= 8) {
        !           196:            /* get input */
        !           197: #ifdef MUSTALIGN
        !           198:            if ((long) input & 3) {
        !           199:                bcopy((char *)input++,(char *)&t_input[0],sizeof(t_input[0]));
        !           200:                bcopy((char *)input++,(char *)&t_input[1],sizeof(t_input[1]));
        !           201:            }
        !           202:            else
        !           203: #endif
        !           204:            {
        !           205:                t_input[0] = *input++;
        !           206:                t_input[1] = *input++;
        !           207:            }
        !           208: 
        !           209:            /* no padding for decrypt */
        !           210: #ifdef DEBUG
        !           211:            if (des_debug)
        !           212:                des_debug_print("cipher",i,t_input[0],t_input[1]);
        !           213: #else
        !           214: #ifdef lint
        !           215:            i = i;
        !           216: #endif
        !           217: #endif
        !           218:            /* encrypt */
        !           219:            (void) des_ecb_encrypt(t_input,t_output,key,encrypt);
        !           220: #ifdef DEBUG
        !           221:            if (des_debug)
        !           222:                des_debug_print("out pre xor",i,t_output[0],t_output[1]);
        !           223: #endif
        !           224:            /* do the xor for cbc into the output */
        !           225:            t_output[0] ^= xor_0 ;
        !           226:            t_output[1] ^= xor_1 ;
        !           227:            /* copy temp output */
        !           228: #ifdef MUSTALIGN
        !           229:            if ((long) output & 3) {
        !           230:                bcopy((char *)&t_output[0],(char *)output++,
        !           231:                      sizeof(t_output[0]));
        !           232:                bcopy((char *)&t_output[1],(char *)output++,
        !           233:                      sizeof(t_output[1]));
        !           234:            }
        !           235:            else
        !           236: #endif
        !           237:            {
        !           238:                *output++ = t_output[0];
        !           239:                *output++ = t_output[1];
        !           240:            }
        !           241: 
        !           242:            /* save xor value for next round */
        !           243:            xor_0 = t_output[0] ^ t_input[0];
        !           244:            xor_1 = t_output[1] ^ t_input[1];
        !           245: 
        !           246: #ifdef DEBUG
        !           247:            if (des_debug)
        !           248:                des_debug_print("clear",i,t_output[0],t_output[1]);
        !           249: #endif
        !           250:        }
        !           251:        return 0;
        !           252:     }
        !           253: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.