From: CSRG Date: Tue, 2 Jan 1990 03:46:37 +0000 (-0800) Subject: BSD 4_4_Lite2 development X-Git-Tag: BSD-4_4_Lite2~3148 X-Git-Url: https://git.subgeniuskitty.com/unix-history/.git/commitdiff_plain/869f46e0b0e06be57e0b9976655596a931272eab BSD 4_4_Lite2 development Work on file Domestic/src/kerberosIV/des/cbc_encrypt.c Work on file usr/src/kerberosIV/des/cbc_encrypt.c Work on file Domestic/src/kerberosIV/des/cksum.c Work on file usr/src/kerberosIV/des/cksum.c Work on file Domestic/src/kerberosIV/des/pcbc_encrypt.c Work on file usr/src/kerberosIV/des/pcbc_encrypt.c Work on file Domestic/src/kerberosIV/des/quad_cksum.c Work on file usr/src/kerberosIV/des/quad_cksum.c Synthesized-from: CSRG/cd3/4.4BSD-Lite2 --- diff --git a/Domestic/src/kerberosIV/des/cbc_encrypt.c b/Domestic/src/kerberosIV/des/cbc_encrypt.c new file mode 100644 index 0000000000..5d27e9f4d8 --- /dev/null +++ b/Domestic/src/kerberosIV/des/cbc_encrypt.c @@ -0,0 +1,211 @@ +/* + * $Source: /afs/athena.mit.edu/astaff/project/kerberos/src/lib/des/RCS/cbc_encrypt.c,v $ + * $Author: jtkohl $ + * + * Copyright 1985, 1986, 1987, 1988 by the Massachusetts Institute + * of Technology. + * + * For copying and distribution information, please see the file + * . + * + * These routines perform encryption and decryption using the DES + * private key algorithm, or else a subset of it -- fewer inner loops. + * (AUTH_DES_ITER defaults to 16, may be less.) + * + * Under U.S. law, this software may not be exported outside the US + * without license from the U.S. Commerce department. + * + * These routines form the library interface to the DES facilities. + * + * Originally written 8/85 by Steve Miller, MIT Project Athena. + */ + +#ifndef lint +static char rcsid_cbc_encrypt_c[] = +"$Id: cbc_encrypt.c,v 4.10 90/01/02 13:46:14 jtkohl Exp $"; +#endif lint + +#include +#include +#include + +extern int des_debug; +extern int des_debug_print(); + +/* + * This routine performs DES cipher-block-chaining operation, either + * encrypting from cleartext to ciphertext, if encrypt != 0 or + * decrypting from ciphertext to cleartext, if encrypt == 0. + * + * The key schedule is passed as an arg, as well as the cleartext or + * ciphertext. The cleartext and ciphertext should be in host order. + * + * NOTE-- the output is ALWAYS an multiple of 8 bytes long. If not + * enough space was provided, your program will get trashed. + * + * For encryption, the cleartext string is null padded, at the end, to + * an integral multiple of eight bytes. + * + * For decryption, the ciphertext will be used in integral multiples + * of 8 bytes, but only the first "length" bytes returned into the + * cleartext. + */ + +int +des_cbc_encrypt(in,out,length,key,iv,encrypt) + des_cblock *in; /* >= length bytes of input text */ + des_cblock *out; /* >= length bytes of output text */ + register long length; /* in bytes */ + int encrypt; /* 0 ==> decrypt, else encrypt */ + des_key_schedule key; /* precomputed key schedule */ + des_cblock *iv; /* 8 bytes of ivec */ +{ + register unsigned long *input = (unsigned long *) in; + register unsigned long *output = (unsigned long *) out; + register unsigned long *ivec = (unsigned long *) iv; + + unsigned long i,j; + static unsigned long t_input[2]; + static unsigned long t_output[2]; + static unsigned char *t_in_p; + static unsigned long xor_0, xor_1; + + t_in_p = (unsigned char *) t_input; + if (encrypt) { +#ifdef MUSTALIGN + if ((long) ivec & 3) { + bcopy((char *)ivec++, (char *)&t_output[0], sizeof(t_output[0])); + bcopy((char *)ivec, (char *)&t_output[1], sizeof(t_output[1])); + } + else +#endif + { + t_output[0] = *ivec++; + t_output[1] = *ivec; + } + + for (i = 0; length > 0; i++, length -= 8) { + /* get input */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input++,(char *)&t_input[0],sizeof(t_input[0])); + bcopy((char *)input++,(char *)&t_input[1],sizeof(t_input[1])); + } + else +#endif + { + t_input[0] = *input++; + t_input[1] = *input++; + } + + /* zero pad */ + if (length < 8) + for (j = length; j <= 7; j++) + *(t_in_p+j)= 0; + +#ifdef DEBUG + if (des_debug) + des_debug_print("clear",length,t_input[0],t_input[1]); +#endif + /* do the xor for cbc into the temp */ + t_input[0] ^= t_output[0]; + t_input[1] ^= t_output[1]; + /* encrypt */ + (void) des_ecb_encrypt(t_input,t_output,key,encrypt); + /* copy temp output and save it for cbc */ +#ifdef MUSTALIGN + if ((long) output & 3) { + bcopy((char *)&t_output[0],(char *)output++, + sizeof(t_output[0])); + bcopy((char *)&t_output[1],(char *)output++, + sizeof(t_output[1])); + } + else +#endif + { + *output++ = t_output[0]; + *output++ = t_output[1]; + } + +#ifdef DEBUG + if (des_debug) { + des_debug_print("xor'ed",i,t_input[0],t_input[1]); + des_debug_print("cipher",i,t_output[0],t_output[1]); + } +#endif + } + return 0; + } + + else { + /* decrypt */ +#ifdef MUSTALIGN + if ((long) ivec & 3) { + bcopy((char *)ivec++,(char *)&xor_0,sizeof(xor_0)); + bcopy((char *)ivec,(char *)&xor_1,sizeof(xor_1)); + } + else +#endif + { + xor_0 = *ivec++; + xor_1 = *ivec; + } + + for (i = 0; length > 0; i++, length -= 8) { + /* get input */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input++,(char *)&t_input[0],sizeof(t_input[0])); + bcopy((char *)input++,(char *)&t_input[1],sizeof(t_input[0])); + } + else +#endif + { + t_input[0] = *input++; + t_input[1] = *input++; + } + + /* no padding for decrypt */ +#ifdef DEBUG + if (des_debug) + des_debug_print("cipher",i,t_input[0],t_input[1]); +#else +#ifdef lint + i = i; +#endif +#endif + /* encrypt */ + (void) des_ecb_encrypt(t_input,t_output,key,encrypt); +#ifdef DEBUG + if (des_debug) + des_debug_print("out pre xor",i,t_output[0],t_output[1]); +#endif + /* do the xor for cbc into the output */ + t_output[0] ^= xor_0; + t_output[1] ^= xor_1; + /* copy temp output */ +#ifdef MUSTALIGN + if ((long) output & 3) { + bcopy((char *)&t_output[0],(char *)output++, + sizeof(t_output[0])); + bcopy((char *)&t_output[1],(char *)output++, + sizeof(t_output[1])); + } + else +#endif + { + *output++ = t_output[0]; + *output++ = t_output[1]; + } + + /* save xor value for next round */ + xor_0 = t_input[0]; + xor_1 = t_input[1]; +#ifdef DEBUG + if (des_debug) + des_debug_print("clear",i,t_output[0],t_output[1]); +#endif + } + return 0; + } +} diff --git a/Domestic/src/kerberosIV/des/cksum.c b/Domestic/src/kerberosIV/des/cksum.c new file mode 100644 index 0000000000..069a685be0 --- /dev/null +++ b/Domestic/src/kerberosIV/des/cksum.c @@ -0,0 +1,136 @@ +/* + * $Source: /afs/athena.mit.edu/astaff/project/kerberos/src/lib/des/RCS/cksum.c,v $ + * $Author: jtkohl $ + * + * Copyright 1985, 1986, 1987, 1988 by the Massachusetts Institute + * of Technology. + * + * For copying and distribution information, please see the file + * . + * + * These routines perform encryption and decryption using the DES + * private key algorithm, or else a subset of it-- fewer inner loops. + * (AUTH_DES_ITER defaults to 16, may be less.) + * + * Under U.S. law, this software may not be exported outside the US + * without license from the U.S. Commerce department. + * + * These routines form the library interface to the DES facilities. + * + * spm 8/85 MIT project athena + */ + +#ifndef lint +static char rcsid_cksum_c[] = +"$Id: cksum.c,v 4.10 90/01/02 13:46:25 jtkohl Exp $"; +#endif lint + +#include +#include +#include + +#include +#include "des_internal.h" + +extern int des_debug; +extern int des_debug_print(); + +/* + * This routine performs DES cipher-block-chaining checksum operation, + * a.k.a. Message Authentication Code. It ALWAYS encrypts from input + * to a single 64 bit output MAC checksum. + * + * The key schedule is passed as an arg, as well as the cleartext or + * ciphertext. The cleartext and ciphertext should be in host order. + * + * NOTE-- the output is ALWAYS 8 bytes long. If not enough space was + * provided, your program will get trashed. + * + * The input is null padded, at the end (highest addr), to an integral + * multiple of eight bytes. + */ + +unsigned long +des_cbc_cksum(in,out,length,key,iv) + des_cblock *in; /* >= length bytes of inputtext */ + des_cblock *out; /* >= length bytes of outputtext */ + register long length; /* in bytes */ + des_key_schedule key; /* precomputed key schedule */ + des_cblock *iv; /* 8 bytes of ivec */ +{ + register unsigned long *input = (unsigned long *) in; + register unsigned long *output = (unsigned long *) out; + unsigned long *ivec = (unsigned long *) iv; + + unsigned long i,j; + static unsigned long t_input[2]; + static unsigned long t_output[8]; + static unsigned char *t_in_p; + + t_in_p = (unsigned char *) t_input; +#ifdef MUSTALIGN + if ((long) ivec & 3) { + bcopy((char *)ivec++,(char *)&t_output[0],sizeof(t_output[0])); + bcopy((char *)ivec,(char *)&t_output[1],sizeof(t_output[1])); + } + else +#endif + { + t_output[0] = *ivec++; + t_output[1] = *ivec; + } + + for (i = 0; length > 0; i++, length -= 8) { + /* get input */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input++,(char *)&t_input[0],sizeof(t_input[0])); + bcopy((char *)input++,(char *)&t_input[1],sizeof(t_input[1])); + } + else +#endif + { + t_input[0] = *input++; + t_input[1] = *input++; + } + + /* zero pad */ + if (length < 8) + for (j = length; j <= 7; j++) + *(t_in_p+j)= 0; + +#ifdef DEBUG + if (des_debug) + des_debug_print("clear",length,t_input[0],t_input[1]); +#endif + /* do the xor for cbc into the temp */ + t_input[0] ^= t_output[0] ; + t_input[1] ^= t_output[1] ; + /* encrypt */ + (void) des_ecb_encrypt(t_input,t_output,key,1); +#ifdef DEBUG + if (des_debug) { + des_debug_print("xor'ed",i,t_input[0],t_input[1]); + des_debug_print("cipher",i,t_output[0],t_output[1]); + } +#else +#ifdef lint + i = i; +#endif +#endif + } + /* copy temp output and save it for checksum */ +#ifdef MUSTALIGN + if ((long) output & 3) { + bcopy((char *)&t_output[0],(char *)output++,sizeof(t_output[0])); + bcopy((char *)&t_output[1],(char *)output,sizeof(t_output[1])); + } + else +#endif + { + *output++ = t_output[0]; + *output = t_output[1]; + } + + return (unsigned long) t_output[1]; +} diff --git a/Domestic/src/kerberosIV/des/pcbc_encrypt.c b/Domestic/src/kerberosIV/des/pcbc_encrypt.c new file mode 100644 index 0000000000..147d3f1bd0 --- /dev/null +++ b/Domestic/src/kerberosIV/des/pcbc_encrypt.c @@ -0,0 +1,253 @@ +/* + * $Source: /afs/athena.mit.edu/astaff/project/kerberos/src/lib/des/RCS/pcbc_encrypt.c,v $ + * $Author: jtkohl $ + * + * Copyright 1985, 1986, 1987, 1988 by the Massachusetts Institute + * of Technology. + * + * For copying and distribution information, please see the file + * . + * + * These routines perform encryption and decryption using the DES + * private key algorithm, or else a subset of it-- fewer inner loops. + * ( AUTH_DES_ITER defaults to 16, may be less) + * + * Under U.S. law, this software may not be exported outside the US + * without license from the U.S. Commerce department. + * + * The key schedule is passed as an arg, as well as the cleartext or + * ciphertext. The cleartext and ciphertext should be in host order. + * + * These routines form the library interface to the des facilities. + * + * spm 8/85 MIT project athena + */ + +#ifndef lint +static char rcsid_pcbc_encrypt_c[] = +"$Id: pcbc_encrypt.c,v 4.11 90/01/02 13:46:30 jtkohl Exp $"; +#endif lint + +#include +#include +#include +#include "des_internal.h" + +extern int des_debug; +extern int des_debug_print(); + +/* + * pcbc_encrypt is an "error propagation chaining" encrypt operation + * for DES, similar to CBC, but that, on encryption, "xor"s the + * plaintext of block N with the ciphertext resulting from block N, + * then "xor"s that result with the plaintext of block N+1 prior to + * encrypting block N+1. (decryption the appropriate inverse. This + * "pcbc" mode propagates a single bit error anywhere in either the + * cleartext or ciphertext chain all the way through to the end. In + * contrast, CBC mode limits a single bit error in the ciphertext to + * affect only the current (8byte) block and the subsequent block. + * + * performs pcbc error-propagation chaining operation by xor-ing block + * N+1 with both the plaintext (block N) and the ciphertext from block + * N. Either encrypts from cleartext to ciphertext, if encrypt != 0 + * or decrypts from ciphertext to cleartext, if encrypt == 0 + * + * NOTE-- the output is ALWAYS an multiple of 8 bytes long. If not + * enough space was provided, your program will get trashed. + * + * For encryption, the cleartext string is null padded, at the end, to + * an integral multiple of eight bytes. + * + * For decryption, the ciphertext will be used in integral multiples + * of 8 bytes, but only the first "length" bytes returned into the + * cleartext. + * + * This is NOT a standard mode of operation. + * + */ + +int +des_pcbc_encrypt(in,out,length,key,iv,encrypt) + des_cblock *in; /* >= length bytes of inputtext */ + des_cblock *out; /* >= length bytes of outputtext */ + register long length; /* in bytes */ + int encrypt; /* 0 ==> decrypt, else encrypt */ + des_key_schedule key; /* precomputed key schedule */ + des_cblock *iv; /* 8 bytes of ivec */ +{ + register unsigned long *input = (unsigned long *) in; + register unsigned long *output = (unsigned long *) out; + register unsigned long *ivec = (unsigned long *) iv; + + unsigned long i,j; + static unsigned long t_input[2]; + static unsigned long t_output[2]; + static unsigned char *t_in_p; + static unsigned long xor_0, xor_1; + + t_in_p = (unsigned char *) t_input; + if (encrypt) { +#ifdef MUSTALIGN + if ((long) ivec & 3) { + bcopy((char *)ivec++,(char *)&xor_0,sizeof(xor_0)); + bcopy((char *)ivec,(char *)&xor_1,sizeof(xor_1)); + } + else +#endif + { + xor_0 = *ivec++; + xor_1 = *ivec; + } + + for (i = 0; length > 0; i++, length -= 8) { + /* get input */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input,(char *)&t_input[0],sizeof(t_input[0])); + bcopy((char *)(input+1),(char *)&t_input[1],sizeof(t_input[1])); + } + else +#endif + { + t_input[0] = *input; + t_input[1] = *(input+1); + } + + /* zero pad */ + if (length < 8) { + for (j = length; j <= 7; j++) + *(t_in_p+j)= 0; + } + +#ifdef DEBUG + if (des_debug) + des_debug_print("clear",length,t_input[0],t_input[1]); +#endif + /* do the xor for cbc into the temp */ + t_input[0] ^= xor_0 ; + t_input[1] ^= xor_1 ; + /* encrypt */ + (void) des_ecb_encrypt(t_input,t_output,key,encrypt); + + /* + * We want to XOR with both the plaintext and ciphertext + * of the previous block, before we write the output, in + * case both input and output are the same space. + */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input++,(char *)&xor_0,sizeof(xor_0)); + xor_0 ^= t_output[0]; + bcopy((char *)input++,(char *)&xor_1,sizeof(xor_1)); + xor_1 ^= t_output[1]; + } + else +#endif + { + xor_0 = *input++ ^ t_output[0]; + xor_1 = *input++ ^ t_output[1]; + } + + + /* copy temp output and save it for cbc */ +#ifdef MUSTALIGN + if ((long) output & 3) { + bcopy((char *)&t_output[0],(char *)output++, + sizeof(t_output[0])); + bcopy((char *)&t_output[1],(char *)output++, + sizeof(t_output[1])); + } + else +#endif + { + *output++ = t_output[0]; + *output++ = t_output[1]; + } + +#ifdef DEBUG + if (des_debug) { + des_debug_print("xor'ed",i,t_input[0],t_input[1]); + des_debug_print("cipher",i,t_output[0],t_output[1]); + } +#endif + } + t_output[0] = 0; + t_output[1] = 0; + xor_0 = 0; + xor_1 = 0; + return 0; + } + + else { + /* decrypt */ +#ifdef MUSTALIGN + if ((long) ivec & 3) { + bcopy((char *)ivec++,(char *)&xor_0,sizeof(xor_0)); + bcopy((char *)ivec,(char *)&xor_1,sizeof(xor_1)); + } + else +#endif + { + xor_0 = *ivec++; + xor_1 = *ivec; + } + + for (i = 0; length > 0; i++, length -= 8) { + /* get input */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input++,(char *)&t_input[0],sizeof(t_input[0])); + bcopy((char *)input++,(char *)&t_input[1],sizeof(t_input[1])); + } + else +#endif + { + t_input[0] = *input++; + t_input[1] = *input++; + } + + /* no padding for decrypt */ +#ifdef DEBUG + if (des_debug) + des_debug_print("cipher",i,t_input[0],t_input[1]); +#else +#ifdef lint + i = i; +#endif +#endif + /* encrypt */ + (void) des_ecb_encrypt(t_input,t_output,key,encrypt); +#ifdef DEBUG + if (des_debug) + des_debug_print("out pre xor",i,t_output[0],t_output[1]); +#endif + /* do the xor for cbc into the output */ + t_output[0] ^= xor_0 ; + t_output[1] ^= xor_1 ; + /* copy temp output */ +#ifdef MUSTALIGN + if ((long) output & 3) { + bcopy((char *)&t_output[0],(char *)output++, + sizeof(t_output[0])); + bcopy((char *)&t_output[1],(char *)output++, + sizeof(t_output[1])); + } + else +#endif + { + *output++ = t_output[0]; + *output++ = t_output[1]; + } + + /* save xor value for next round */ + xor_0 = t_output[0] ^ t_input[0]; + xor_1 = t_output[1] ^ t_input[1]; + +#ifdef DEBUG + if (des_debug) + des_debug_print("clear",i,t_output[0],t_output[1]); +#endif + } + return 0; + } +} diff --git a/Domestic/src/kerberosIV/des/quad_cksum.c b/Domestic/src/kerberosIV/des/quad_cksum.c new file mode 100644 index 0000000000..e27f1d95c0 --- /dev/null +++ b/Domestic/src/kerberosIV/des/quad_cksum.c @@ -0,0 +1,216 @@ +/* + * $Source: /afs/athena.mit.edu/astaff/project/kerberos/src/lib/des/RCS/quad_cksum.c,v $ + * $Author: jtkohl $ + * + * Copyright 1985, 1986, 1987, 1988 by the Massachusetts Institute + * of Technology. + * + * For copying and distribution information, please see the file + * . + * + * Quadratic Congruential Manipulation Dectection Code + * + * ref: "Message Authentication" + * R.R. Jueneman, S. M. Matyas, C.H. Meyer + * IEEE Communications Magazine, + * Sept 1985 Vol 23 No 9 p 29-40 + * + * This routine, part of the Athena DES library built for the Kerberos + * authentication system, calculates a manipulation detection code for + * a message. It is a much faster alternative to the DES-checksum + * method. No guarantees are offered for its security. Refer to the + * paper noted above for more information + * + * Implementation for 4.2bsd + * by S.P. Miller Project Athena/MIT + */ + +/* + * Algorithm (per paper): + * define: + * message to be composed of n m-bit blocks X1,...,Xn + * optional secret seed S in block X1 + * MDC in block Xn+1 + * prime modulus N + * accumulator Z + * initial (secret) value of accumulator C + * N, C, and S are known at both ends + * C and , optionally, S, are hidden from the end users + * then + * (read array references as subscripts over time) + * Z[0] = c; + * for i = 1...n + * Z[i] = (Z[i+1] + X[i])**2 modulo N + * X[n+1] = Z[n] = MDC + * + * Then pick + * N = 2**31 -1 + * m = 16 + * iterate 4 times over plaintext, also use Zn + * from iteration j as seed for iteration j+1, + * total MDC is then a 128 bit array of the four + * Zn; + * + * return the last Zn and optionally, all + * four as output args. + * + * Modifications: + * To inhibit brute force searches of the seed space, this + * implementation is modified to have + * Z = 64 bit accumulator + * C = 64 bit C seed + * N = 2**63 - 1 + * S = S seed is not implemented here + * arithmetic is not quite real double integer precision, since we + * cant get at the carry or high order results from multiply, + * but nontheless is 64 bit arithmetic. + */ + +#ifndef lint +static char rcsid_quad_cksum_c[] = +"$Id: quad_cksum.c,v 4.13 90/01/02 13:46:34 jtkohl Exp $"; +#endif lint + +#include + +/* System include files */ +#include +#include + +/* Application include files */ +#include +#include "des_internal.h" +/* Definitions for byte swapping */ + +#ifdef LSBFIRST +#ifdef MUSTALIGN +static unsigned long vaxtohl(); +static unsigned short vaxtohs(); +#else /* ! MUSTALIGN */ +#define vaxtohl(x) *((unsigned long *)(x)) +#define vaxtohs(x) *((unsigned short *)(x)) +#endif /* MUSTALIGN */ +#else /* !LSBFIRST */ +static unsigned long four_bytes_vax_to_nets(); +#define vaxtohl(x) four_bytes_vax_to_nets((char *)(x)) +static unsigned short two_bytes_vax_to_nets(); +#define vaxtohs(x) two_bytes_vax_to_nets((char *)(x)) +#endif + +/* Externals */ +extern char *errmsg(); +extern int errno; +extern int des_debug; + +/*** Routines ***************************************************** */ + +unsigned long +des_quad_cksum(in,out,length,out_count,c_seed) + des_cblock *c_seed; /* secret seed, 8 bytes */ + unsigned char *in; /* input block */ + unsigned long *out; /* optional longer output */ + int out_count; /* number of iterations */ + long length; /* original length in bytes */ +{ + + /* + * this routine both returns the low order of the final (last in + * time) 32bits of the checksum, and if "out" is not a null + * pointer, a longer version, up to entire 32 bytes of the + * checksum is written unto the address pointed to. + */ + + register unsigned long z; + register unsigned long z2; + register unsigned long x; + register unsigned long x2; + register unsigned char *p; + register long len; + register int i; + + /* use all 8 bytes of seed */ + + z = vaxtohl(c_seed); + z2 = vaxtohl((char *)c_seed+4); + if (out == NULL) + out_count = 1; /* default */ + + /* This is repeated n times!! */ + for (i = 1; i <=4 && i<= out_count; i++) { + len = length; + p = in; + while (len) { + if (len > 1) { + x = (z + vaxtohs(p)); + p += 2; + len -= 2; + } + else { + x = (z + *(char *)p++); + len = 0; + } + x2 = z2; + z = ((x * x) + (x2 * x2)) % 0x7fffffff; + z2 = (x * (x2+83653421)) % 0x7fffffff; /* modulo */ + if (des_debug & 8) + printf("%d %d\n",z,z2); + } + + if (out != NULL) { + *out++ = z; + *out++ = z2; + } + } + /* return final z value as 32 bit version of checksum */ + return z; +} +#ifdef MSBFIRST + +static unsigned short two_bytes_vax_to_nets(p) + char *p; +{ + union { + char pieces[2]; + unsigned short result; + } short_conv; + + short_conv.pieces[0] = p[1]; + short_conv.pieces[1] = p[0]; + return(short_conv.result); +} + +static unsigned long four_bytes_vax_to_nets(p) + char *p; +{ + static union { + char pieces[4]; + unsigned long result; + } long_conv; + + long_conv.pieces[0] = p[3]; + long_conv.pieces[1] = p[2]; + long_conv.pieces[2] = p[1]; + long_conv.pieces[3] = p[0]; + return(long_conv.result); +} + +#endif +#ifdef LSBFIRST +#ifdef MUSTALIGN +static unsigned long vaxtohl(x) +char *x; +{ + unsigned long val; + bcopy(x, (char *)&val, sizeof(val)); + return(val); +} + +static unsigned short vaxtohs(x) +char *x; +{ + unsigned short val; + bcopy(x, (char *)&val, sizeof(val)); + return(val); +} +#endif /* MUSTALIGN */ +#endif /* LSBFIRST */ diff --git a/usr/src/kerberosIV/des/cbc_encrypt.c b/usr/src/kerberosIV/des/cbc_encrypt.c new file mode 100644 index 0000000000..5d27e9f4d8 --- /dev/null +++ b/usr/src/kerberosIV/des/cbc_encrypt.c @@ -0,0 +1,211 @@ +/* + * $Source: /afs/athena.mit.edu/astaff/project/kerberos/src/lib/des/RCS/cbc_encrypt.c,v $ + * $Author: jtkohl $ + * + * Copyright 1985, 1986, 1987, 1988 by the Massachusetts Institute + * of Technology. + * + * For copying and distribution information, please see the file + * . + * + * These routines perform encryption and decryption using the DES + * private key algorithm, or else a subset of it -- fewer inner loops. + * (AUTH_DES_ITER defaults to 16, may be less.) + * + * Under U.S. law, this software may not be exported outside the US + * without license from the U.S. Commerce department. + * + * These routines form the library interface to the DES facilities. + * + * Originally written 8/85 by Steve Miller, MIT Project Athena. + */ + +#ifndef lint +static char rcsid_cbc_encrypt_c[] = +"$Id: cbc_encrypt.c,v 4.10 90/01/02 13:46:14 jtkohl Exp $"; +#endif lint + +#include +#include +#include + +extern int des_debug; +extern int des_debug_print(); + +/* + * This routine performs DES cipher-block-chaining operation, either + * encrypting from cleartext to ciphertext, if encrypt != 0 or + * decrypting from ciphertext to cleartext, if encrypt == 0. + * + * The key schedule is passed as an arg, as well as the cleartext or + * ciphertext. The cleartext and ciphertext should be in host order. + * + * NOTE-- the output is ALWAYS an multiple of 8 bytes long. If not + * enough space was provided, your program will get trashed. + * + * For encryption, the cleartext string is null padded, at the end, to + * an integral multiple of eight bytes. + * + * For decryption, the ciphertext will be used in integral multiples + * of 8 bytes, but only the first "length" bytes returned into the + * cleartext. + */ + +int +des_cbc_encrypt(in,out,length,key,iv,encrypt) + des_cblock *in; /* >= length bytes of input text */ + des_cblock *out; /* >= length bytes of output text */ + register long length; /* in bytes */ + int encrypt; /* 0 ==> decrypt, else encrypt */ + des_key_schedule key; /* precomputed key schedule */ + des_cblock *iv; /* 8 bytes of ivec */ +{ + register unsigned long *input = (unsigned long *) in; + register unsigned long *output = (unsigned long *) out; + register unsigned long *ivec = (unsigned long *) iv; + + unsigned long i,j; + static unsigned long t_input[2]; + static unsigned long t_output[2]; + static unsigned char *t_in_p; + static unsigned long xor_0, xor_1; + + t_in_p = (unsigned char *) t_input; + if (encrypt) { +#ifdef MUSTALIGN + if ((long) ivec & 3) { + bcopy((char *)ivec++, (char *)&t_output[0], sizeof(t_output[0])); + bcopy((char *)ivec, (char *)&t_output[1], sizeof(t_output[1])); + } + else +#endif + { + t_output[0] = *ivec++; + t_output[1] = *ivec; + } + + for (i = 0; length > 0; i++, length -= 8) { + /* get input */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input++,(char *)&t_input[0],sizeof(t_input[0])); + bcopy((char *)input++,(char *)&t_input[1],sizeof(t_input[1])); + } + else +#endif + { + t_input[0] = *input++; + t_input[1] = *input++; + } + + /* zero pad */ + if (length < 8) + for (j = length; j <= 7; j++) + *(t_in_p+j)= 0; + +#ifdef DEBUG + if (des_debug) + des_debug_print("clear",length,t_input[0],t_input[1]); +#endif + /* do the xor for cbc into the temp */ + t_input[0] ^= t_output[0]; + t_input[1] ^= t_output[1]; + /* encrypt */ + (void) des_ecb_encrypt(t_input,t_output,key,encrypt); + /* copy temp output and save it for cbc */ +#ifdef MUSTALIGN + if ((long) output & 3) { + bcopy((char *)&t_output[0],(char *)output++, + sizeof(t_output[0])); + bcopy((char *)&t_output[1],(char *)output++, + sizeof(t_output[1])); + } + else +#endif + { + *output++ = t_output[0]; + *output++ = t_output[1]; + } + +#ifdef DEBUG + if (des_debug) { + des_debug_print("xor'ed",i,t_input[0],t_input[1]); + des_debug_print("cipher",i,t_output[0],t_output[1]); + } +#endif + } + return 0; + } + + else { + /* decrypt */ +#ifdef MUSTALIGN + if ((long) ivec & 3) { + bcopy((char *)ivec++,(char *)&xor_0,sizeof(xor_0)); + bcopy((char *)ivec,(char *)&xor_1,sizeof(xor_1)); + } + else +#endif + { + xor_0 = *ivec++; + xor_1 = *ivec; + } + + for (i = 0; length > 0; i++, length -= 8) { + /* get input */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input++,(char *)&t_input[0],sizeof(t_input[0])); + bcopy((char *)input++,(char *)&t_input[1],sizeof(t_input[0])); + } + else +#endif + { + t_input[0] = *input++; + t_input[1] = *input++; + } + + /* no padding for decrypt */ +#ifdef DEBUG + if (des_debug) + des_debug_print("cipher",i,t_input[0],t_input[1]); +#else +#ifdef lint + i = i; +#endif +#endif + /* encrypt */ + (void) des_ecb_encrypt(t_input,t_output,key,encrypt); +#ifdef DEBUG + if (des_debug) + des_debug_print("out pre xor",i,t_output[0],t_output[1]); +#endif + /* do the xor for cbc into the output */ + t_output[0] ^= xor_0; + t_output[1] ^= xor_1; + /* copy temp output */ +#ifdef MUSTALIGN + if ((long) output & 3) { + bcopy((char *)&t_output[0],(char *)output++, + sizeof(t_output[0])); + bcopy((char *)&t_output[1],(char *)output++, + sizeof(t_output[1])); + } + else +#endif + { + *output++ = t_output[0]; + *output++ = t_output[1]; + } + + /* save xor value for next round */ + xor_0 = t_input[0]; + xor_1 = t_input[1]; +#ifdef DEBUG + if (des_debug) + des_debug_print("clear",i,t_output[0],t_output[1]); +#endif + } + return 0; + } +} diff --git a/usr/src/kerberosIV/des/cksum.c b/usr/src/kerberosIV/des/cksum.c new file mode 100644 index 0000000000..069a685be0 --- /dev/null +++ b/usr/src/kerberosIV/des/cksum.c @@ -0,0 +1,136 @@ +/* + * $Source: /afs/athena.mit.edu/astaff/project/kerberos/src/lib/des/RCS/cksum.c,v $ + * $Author: jtkohl $ + * + * Copyright 1985, 1986, 1987, 1988 by the Massachusetts Institute + * of Technology. + * + * For copying and distribution information, please see the file + * . + * + * These routines perform encryption and decryption using the DES + * private key algorithm, or else a subset of it-- fewer inner loops. + * (AUTH_DES_ITER defaults to 16, may be less.) + * + * Under U.S. law, this software may not be exported outside the US + * without license from the U.S. Commerce department. + * + * These routines form the library interface to the DES facilities. + * + * spm 8/85 MIT project athena + */ + +#ifndef lint +static char rcsid_cksum_c[] = +"$Id: cksum.c,v 4.10 90/01/02 13:46:25 jtkohl Exp $"; +#endif lint + +#include +#include +#include + +#include +#include "des_internal.h" + +extern int des_debug; +extern int des_debug_print(); + +/* + * This routine performs DES cipher-block-chaining checksum operation, + * a.k.a. Message Authentication Code. It ALWAYS encrypts from input + * to a single 64 bit output MAC checksum. + * + * The key schedule is passed as an arg, as well as the cleartext or + * ciphertext. The cleartext and ciphertext should be in host order. + * + * NOTE-- the output is ALWAYS 8 bytes long. If not enough space was + * provided, your program will get trashed. + * + * The input is null padded, at the end (highest addr), to an integral + * multiple of eight bytes. + */ + +unsigned long +des_cbc_cksum(in,out,length,key,iv) + des_cblock *in; /* >= length bytes of inputtext */ + des_cblock *out; /* >= length bytes of outputtext */ + register long length; /* in bytes */ + des_key_schedule key; /* precomputed key schedule */ + des_cblock *iv; /* 8 bytes of ivec */ +{ + register unsigned long *input = (unsigned long *) in; + register unsigned long *output = (unsigned long *) out; + unsigned long *ivec = (unsigned long *) iv; + + unsigned long i,j; + static unsigned long t_input[2]; + static unsigned long t_output[8]; + static unsigned char *t_in_p; + + t_in_p = (unsigned char *) t_input; +#ifdef MUSTALIGN + if ((long) ivec & 3) { + bcopy((char *)ivec++,(char *)&t_output[0],sizeof(t_output[0])); + bcopy((char *)ivec,(char *)&t_output[1],sizeof(t_output[1])); + } + else +#endif + { + t_output[0] = *ivec++; + t_output[1] = *ivec; + } + + for (i = 0; length > 0; i++, length -= 8) { + /* get input */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input++,(char *)&t_input[0],sizeof(t_input[0])); + bcopy((char *)input++,(char *)&t_input[1],sizeof(t_input[1])); + } + else +#endif + { + t_input[0] = *input++; + t_input[1] = *input++; + } + + /* zero pad */ + if (length < 8) + for (j = length; j <= 7; j++) + *(t_in_p+j)= 0; + +#ifdef DEBUG + if (des_debug) + des_debug_print("clear",length,t_input[0],t_input[1]); +#endif + /* do the xor for cbc into the temp */ + t_input[0] ^= t_output[0] ; + t_input[1] ^= t_output[1] ; + /* encrypt */ + (void) des_ecb_encrypt(t_input,t_output,key,1); +#ifdef DEBUG + if (des_debug) { + des_debug_print("xor'ed",i,t_input[0],t_input[1]); + des_debug_print("cipher",i,t_output[0],t_output[1]); + } +#else +#ifdef lint + i = i; +#endif +#endif + } + /* copy temp output and save it for checksum */ +#ifdef MUSTALIGN + if ((long) output & 3) { + bcopy((char *)&t_output[0],(char *)output++,sizeof(t_output[0])); + bcopy((char *)&t_output[1],(char *)output,sizeof(t_output[1])); + } + else +#endif + { + *output++ = t_output[0]; + *output = t_output[1]; + } + + return (unsigned long) t_output[1]; +} diff --git a/usr/src/kerberosIV/des/pcbc_encrypt.c b/usr/src/kerberosIV/des/pcbc_encrypt.c new file mode 100644 index 0000000000..147d3f1bd0 --- /dev/null +++ b/usr/src/kerberosIV/des/pcbc_encrypt.c @@ -0,0 +1,253 @@ +/* + * $Source: /afs/athena.mit.edu/astaff/project/kerberos/src/lib/des/RCS/pcbc_encrypt.c,v $ + * $Author: jtkohl $ + * + * Copyright 1985, 1986, 1987, 1988 by the Massachusetts Institute + * of Technology. + * + * For copying and distribution information, please see the file + * . + * + * These routines perform encryption and decryption using the DES + * private key algorithm, or else a subset of it-- fewer inner loops. + * ( AUTH_DES_ITER defaults to 16, may be less) + * + * Under U.S. law, this software may not be exported outside the US + * without license from the U.S. Commerce department. + * + * The key schedule is passed as an arg, as well as the cleartext or + * ciphertext. The cleartext and ciphertext should be in host order. + * + * These routines form the library interface to the des facilities. + * + * spm 8/85 MIT project athena + */ + +#ifndef lint +static char rcsid_pcbc_encrypt_c[] = +"$Id: pcbc_encrypt.c,v 4.11 90/01/02 13:46:30 jtkohl Exp $"; +#endif lint + +#include +#include +#include +#include "des_internal.h" + +extern int des_debug; +extern int des_debug_print(); + +/* + * pcbc_encrypt is an "error propagation chaining" encrypt operation + * for DES, similar to CBC, but that, on encryption, "xor"s the + * plaintext of block N with the ciphertext resulting from block N, + * then "xor"s that result with the plaintext of block N+1 prior to + * encrypting block N+1. (decryption the appropriate inverse. This + * "pcbc" mode propagates a single bit error anywhere in either the + * cleartext or ciphertext chain all the way through to the end. In + * contrast, CBC mode limits a single bit error in the ciphertext to + * affect only the current (8byte) block and the subsequent block. + * + * performs pcbc error-propagation chaining operation by xor-ing block + * N+1 with both the plaintext (block N) and the ciphertext from block + * N. Either encrypts from cleartext to ciphertext, if encrypt != 0 + * or decrypts from ciphertext to cleartext, if encrypt == 0 + * + * NOTE-- the output is ALWAYS an multiple of 8 bytes long. If not + * enough space was provided, your program will get trashed. + * + * For encryption, the cleartext string is null padded, at the end, to + * an integral multiple of eight bytes. + * + * For decryption, the ciphertext will be used in integral multiples + * of 8 bytes, but only the first "length" bytes returned into the + * cleartext. + * + * This is NOT a standard mode of operation. + * + */ + +int +des_pcbc_encrypt(in,out,length,key,iv,encrypt) + des_cblock *in; /* >= length bytes of inputtext */ + des_cblock *out; /* >= length bytes of outputtext */ + register long length; /* in bytes */ + int encrypt; /* 0 ==> decrypt, else encrypt */ + des_key_schedule key; /* precomputed key schedule */ + des_cblock *iv; /* 8 bytes of ivec */ +{ + register unsigned long *input = (unsigned long *) in; + register unsigned long *output = (unsigned long *) out; + register unsigned long *ivec = (unsigned long *) iv; + + unsigned long i,j; + static unsigned long t_input[2]; + static unsigned long t_output[2]; + static unsigned char *t_in_p; + static unsigned long xor_0, xor_1; + + t_in_p = (unsigned char *) t_input; + if (encrypt) { +#ifdef MUSTALIGN + if ((long) ivec & 3) { + bcopy((char *)ivec++,(char *)&xor_0,sizeof(xor_0)); + bcopy((char *)ivec,(char *)&xor_1,sizeof(xor_1)); + } + else +#endif + { + xor_0 = *ivec++; + xor_1 = *ivec; + } + + for (i = 0; length > 0; i++, length -= 8) { + /* get input */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input,(char *)&t_input[0],sizeof(t_input[0])); + bcopy((char *)(input+1),(char *)&t_input[1],sizeof(t_input[1])); + } + else +#endif + { + t_input[0] = *input; + t_input[1] = *(input+1); + } + + /* zero pad */ + if (length < 8) { + for (j = length; j <= 7; j++) + *(t_in_p+j)= 0; + } + +#ifdef DEBUG + if (des_debug) + des_debug_print("clear",length,t_input[0],t_input[1]); +#endif + /* do the xor for cbc into the temp */ + t_input[0] ^= xor_0 ; + t_input[1] ^= xor_1 ; + /* encrypt */ + (void) des_ecb_encrypt(t_input,t_output,key,encrypt); + + /* + * We want to XOR with both the plaintext and ciphertext + * of the previous block, before we write the output, in + * case both input and output are the same space. + */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input++,(char *)&xor_0,sizeof(xor_0)); + xor_0 ^= t_output[0]; + bcopy((char *)input++,(char *)&xor_1,sizeof(xor_1)); + xor_1 ^= t_output[1]; + } + else +#endif + { + xor_0 = *input++ ^ t_output[0]; + xor_1 = *input++ ^ t_output[1]; + } + + + /* copy temp output and save it for cbc */ +#ifdef MUSTALIGN + if ((long) output & 3) { + bcopy((char *)&t_output[0],(char *)output++, + sizeof(t_output[0])); + bcopy((char *)&t_output[1],(char *)output++, + sizeof(t_output[1])); + } + else +#endif + { + *output++ = t_output[0]; + *output++ = t_output[1]; + } + +#ifdef DEBUG + if (des_debug) { + des_debug_print("xor'ed",i,t_input[0],t_input[1]); + des_debug_print("cipher",i,t_output[0],t_output[1]); + } +#endif + } + t_output[0] = 0; + t_output[1] = 0; + xor_0 = 0; + xor_1 = 0; + return 0; + } + + else { + /* decrypt */ +#ifdef MUSTALIGN + if ((long) ivec & 3) { + bcopy((char *)ivec++,(char *)&xor_0,sizeof(xor_0)); + bcopy((char *)ivec,(char *)&xor_1,sizeof(xor_1)); + } + else +#endif + { + xor_0 = *ivec++; + xor_1 = *ivec; + } + + for (i = 0; length > 0; i++, length -= 8) { + /* get input */ +#ifdef MUSTALIGN + if ((long) input & 3) { + bcopy((char *)input++,(char *)&t_input[0],sizeof(t_input[0])); + bcopy((char *)input++,(char *)&t_input[1],sizeof(t_input[1])); + } + else +#endif + { + t_input[0] = *input++; + t_input[1] = *input++; + } + + /* no padding for decrypt */ +#ifdef DEBUG + if (des_debug) + des_debug_print("cipher",i,t_input[0],t_input[1]); +#else +#ifdef lint + i = i; +#endif +#endif + /* encrypt */ + (void) des_ecb_encrypt(t_input,t_output,key,encrypt); +#ifdef DEBUG + if (des_debug) + des_debug_print("out pre xor",i,t_output[0],t_output[1]); +#endif + /* do the xor for cbc into the output */ + t_output[0] ^= xor_0 ; + t_output[1] ^= xor_1 ; + /* copy temp output */ +#ifdef MUSTALIGN + if ((long) output & 3) { + bcopy((char *)&t_output[0],(char *)output++, + sizeof(t_output[0])); + bcopy((char *)&t_output[1],(char *)output++, + sizeof(t_output[1])); + } + else +#endif + { + *output++ = t_output[0]; + *output++ = t_output[1]; + } + + /* save xor value for next round */ + xor_0 = t_output[0] ^ t_input[0]; + xor_1 = t_output[1] ^ t_input[1]; + +#ifdef DEBUG + if (des_debug) + des_debug_print("clear",i,t_output[0],t_output[1]); +#endif + } + return 0; + } +} diff --git a/usr/src/kerberosIV/des/quad_cksum.c b/usr/src/kerberosIV/des/quad_cksum.c new file mode 100644 index 0000000000..e27f1d95c0 --- /dev/null +++ b/usr/src/kerberosIV/des/quad_cksum.c @@ -0,0 +1,216 @@ +/* + * $Source: /afs/athena.mit.edu/astaff/project/kerberos/src/lib/des/RCS/quad_cksum.c,v $ + * $Author: jtkohl $ + * + * Copyright 1985, 1986, 1987, 1988 by the Massachusetts Institute + * of Technology. + * + * For copying and distribution information, please see the file + * . + * + * Quadratic Congruential Manipulation Dectection Code + * + * ref: "Message Authentication" + * R.R. Jueneman, S. M. Matyas, C.H. Meyer + * IEEE Communications Magazine, + * Sept 1985 Vol 23 No 9 p 29-40 + * + * This routine, part of the Athena DES library built for the Kerberos + * authentication system, calculates a manipulation detection code for + * a message. It is a much faster alternative to the DES-checksum + * method. No guarantees are offered for its security. Refer to the + * paper noted above for more information + * + * Implementation for 4.2bsd + * by S.P. Miller Project Athena/MIT + */ + +/* + * Algorithm (per paper): + * define: + * message to be composed of n m-bit blocks X1,...,Xn + * optional secret seed S in block X1 + * MDC in block Xn+1 + * prime modulus N + * accumulator Z + * initial (secret) value of accumulator C + * N, C, and S are known at both ends + * C and , optionally, S, are hidden from the end users + * then + * (read array references as subscripts over time) + * Z[0] = c; + * for i = 1...n + * Z[i] = (Z[i+1] + X[i])**2 modulo N + * X[n+1] = Z[n] = MDC + * + * Then pick + * N = 2**31 -1 + * m = 16 + * iterate 4 times over plaintext, also use Zn + * from iteration j as seed for iteration j+1, + * total MDC is then a 128 bit array of the four + * Zn; + * + * return the last Zn and optionally, all + * four as output args. + * + * Modifications: + * To inhibit brute force searches of the seed space, this + * implementation is modified to have + * Z = 64 bit accumulator + * C = 64 bit C seed + * N = 2**63 - 1 + * S = S seed is not implemented here + * arithmetic is not quite real double integer precision, since we + * cant get at the carry or high order results from multiply, + * but nontheless is 64 bit arithmetic. + */ + +#ifndef lint +static char rcsid_quad_cksum_c[] = +"$Id: quad_cksum.c,v 4.13 90/01/02 13:46:34 jtkohl Exp $"; +#endif lint + +#include + +/* System include files */ +#include +#include + +/* Application include files */ +#include +#include "des_internal.h" +/* Definitions for byte swapping */ + +#ifdef LSBFIRST +#ifdef MUSTALIGN +static unsigned long vaxtohl(); +static unsigned short vaxtohs(); +#else /* ! MUSTALIGN */ +#define vaxtohl(x) *((unsigned long *)(x)) +#define vaxtohs(x) *((unsigned short *)(x)) +#endif /* MUSTALIGN */ +#else /* !LSBFIRST */ +static unsigned long four_bytes_vax_to_nets(); +#define vaxtohl(x) four_bytes_vax_to_nets((char *)(x)) +static unsigned short two_bytes_vax_to_nets(); +#define vaxtohs(x) two_bytes_vax_to_nets((char *)(x)) +#endif + +/* Externals */ +extern char *errmsg(); +extern int errno; +extern int des_debug; + +/*** Routines ***************************************************** */ + +unsigned long +des_quad_cksum(in,out,length,out_count,c_seed) + des_cblock *c_seed; /* secret seed, 8 bytes */ + unsigned char *in; /* input block */ + unsigned long *out; /* optional longer output */ + int out_count; /* number of iterations */ + long length; /* original length in bytes */ +{ + + /* + * this routine both returns the low order of the final (last in + * time) 32bits of the checksum, and if "out" is not a null + * pointer, a longer version, up to entire 32 bytes of the + * checksum is written unto the address pointed to. + */ + + register unsigned long z; + register unsigned long z2; + register unsigned long x; + register unsigned long x2; + register unsigned char *p; + register long len; + register int i; + + /* use all 8 bytes of seed */ + + z = vaxtohl(c_seed); + z2 = vaxtohl((char *)c_seed+4); + if (out == NULL) + out_count = 1; /* default */ + + /* This is repeated n times!! */ + for (i = 1; i <=4 && i<= out_count; i++) { + len = length; + p = in; + while (len) { + if (len > 1) { + x = (z + vaxtohs(p)); + p += 2; + len -= 2; + } + else { + x = (z + *(char *)p++); + len = 0; + } + x2 = z2; + z = ((x * x) + (x2 * x2)) % 0x7fffffff; + z2 = (x * (x2+83653421)) % 0x7fffffff; /* modulo */ + if (des_debug & 8) + printf("%d %d\n",z,z2); + } + + if (out != NULL) { + *out++ = z; + *out++ = z2; + } + } + /* return final z value as 32 bit version of checksum */ + return z; +} +#ifdef MSBFIRST + +static unsigned short two_bytes_vax_to_nets(p) + char *p; +{ + union { + char pieces[2]; + unsigned short result; + } short_conv; + + short_conv.pieces[0] = p[1]; + short_conv.pieces[1] = p[0]; + return(short_conv.result); +} + +static unsigned long four_bytes_vax_to_nets(p) + char *p; +{ + static union { + char pieces[4]; + unsigned long result; + } long_conv; + + long_conv.pieces[0] = p[3]; + long_conv.pieces[1] = p[2]; + long_conv.pieces[2] = p[1]; + long_conv.pieces[3] = p[0]; + return(long_conv.result); +} + +#endif +#ifdef LSBFIRST +#ifdef MUSTALIGN +static unsigned long vaxtohl(x) +char *x; +{ + unsigned long val; + bcopy(x, (char *)&val, sizeof(val)); + return(val); +} + +static unsigned short vaxtohs(x) +char *x; +{ + unsigned short val; + bcopy(x, (char *)&val, sizeof(val)); + return(val); +} +#endif /* MUSTALIGN */ +#endif /* LSBFIRST */