📄 des.c
字号:
return(0); } /* Clear key schedule */ for (i=0; i<16; i++) for (j=0; j<8; j++) kn1[i][j]=0; for (j=0; j<56; j++) { /* convert pc1 to bits of key */ l=pc1[j]-1; /* integer bit location */ m = l & 07; /* find bit */ pc1m[j]=(key[l>>3] & /* find which key byte l is in */ bytebit[m]) /* and which bit of that byte */ ? 1 : 0; /* and store 1-bit result */ } for (i=0; i<16; i++) { /* key chunk for each iteration */ for (j=0; j<56; j++) /* rotate pc1 the right amount */ pcr[j] = pc1m[(l=j+totrot[i])<(j<28? 28 : 56) ? l: l-28]; /* rotate left and right halves independently */ for (j=0; j<48; j++){ /* select bits individually */ /* check bit that goes to kn1[j] */ if (pcr[pc2[j]-1]){ /* mask it in if it's there */ l= j % 6; kn1[i][j/6] |= bytebit[l] >> 2; } } } return(0);}/* In-place encryption of 64-bit block */endes(block)char *block;{ register int i; unsigned long work[2]; /* Working data storage */ long tmp; permute(block,iperm,(char *)work); /* Initial Permutation */#ifdef LITTLE_ENDIAN work[0] = byteswap(work[0]); work[1] = byteswap(work[1]);#endif /* Do the 16 rounds */ for (i=0; i<16; i++) round(i,work); /* Left/right half swap */ tmp = work[0]; work[0] = work[1]; work[1] = tmp;#ifdef LITTLE_ENDIAN work[0] = byteswap(work[0]); work[1] = byteswap(work[1]);#endif permute((char *)work,fperm,block); /* Inverse initial permutation */ return(0);}/* In-place encryption of 64-bit block */endes1(block)char *block;{ register int i; unsigned long work[2]; /* Working data storage */ long tmp; permute(block,iperm1,(char *)work); /* Initial Permutation */#ifdef LITTLE_ENDIAN work[0] = byteswap(work[0]); work[1] = byteswap(work[1]);#endif /* Do the 16 rounds */ for (i=0; i<16; i++) round1(i,work); /* Left/right half swap */ tmp = work[0]; work[0] = work[1]; work[1] = tmp;#ifdef LITTLE_ENDIAN work[0] = byteswap(work[0]); work[1] = byteswap(work[1]);#endif permute((char *)work,fperm1,block); /* Inverse initial permutation */ return(0);}/* In-place decryption of 64-bit block */dedes(block)char *block;{ register int i; unsigned long work[2]; /* Working data storage */ long tmp; permute(block,iperm,(char *)work); /* Initial permutation */#ifdef LITTLE_ENDIAN work[0] = byteswap(work[0]); work[1] = byteswap(work[1]);#endif /* Left/right half swap */ tmp = work[0]; work[0] = work[1]; work[1] = tmp; /* Do the 16 rounds in reverse order */ for (i=15; i >= 0; i--) round(i,work);#ifdef LITTLE_ENDIAN work[0] = byteswap(work[0]); work[1] = byteswap(work[1]);#endif permute((char *)work,fperm,block); /* Inverse initial permutation */ return(0);}/* In-place decryption of 64-bit block */dedes1(block)char *block;{ register int i; unsigned long work[2]; /* Working data storage */ long tmp; permute(block,iperm1,(char *)work); /* Initial permutation */#ifdef LITTLE_ENDIAN work[0] = byteswap(work[0]); work[1] = byteswap(work[1]);#endif /* Left/right half swap */ tmp = work[0]; work[0] = work[1]; work[1] = tmp; /* Do the 16 rounds in reverse order */ for (i=15; i >= 0; i--) round1(i,work);#ifdef LITTLE_ENDIAN work[0] = byteswap(work[0]); work[1] = byteswap(work[1]);#endif permute((char *)work,fperm1,block); /* Inverse initial permutation */ return(0);}/* Permute inblock with perm */staticpermute(inblock,perm,outblock)char *inblock, *outblock; /* result into outblock,64 bits */char perm[16][16][8]; /* 2K bytes defining perm. */{ register int i,j; register char *ib, *ob; /* ptr to input or output block */ register char *p, *q; if(perm == NULL){ /* No permutation, just copy */ for(i=8; i!=0; i--) *outblock++ = *inblock++; return(0); } /* Clear output block */ for (i=8, ob = outblock; i != 0; i--) *ob++ = 0; ib = inblock; for (j = 0; j < 16; j += 2, ib++) { /* for each input nibble */ ob = outblock; p = perm[j][(*ib >> 4) & 017]; q = perm[j + 1][*ib & 017]; for (i = 8; i != 0; i--){ /* and each output byte */ *ob++ |= *p++ | *q++; /* OR the masks together*/ } } return(0);}/* Do one DES cipher round */staticround(num,block)int num; /* i.e. the num-th one */unsigned long *block;{ /* The rounds are numbered from 0 to 15. On even rounds * the right half is fed to f() and the result exclusive-ORs * the left half; on odd rounds the reverse is done. */ if(num & 1){ block[1] ^= f(block[0],kn[num]); } else { block[0] ^= f(block[1],kn[num]); } return(0);}/* Do one DES cipher round */staticround1(num,block)int num; /* i.e. the num-th one */unsigned long *block;{ /* The rounds are numbered from 0 to 15. On even rounds * the right half is fed to f() and the result exclusive-ORs * the left half; on odd rounds the reverse is done. */ if(num & 1){ block[1] ^= f(block[0],kn1[num]); } else { block[0] ^= f(block[1],kn1[num]); } return(0);}/* The nonlinear function f(r,k), the heart of DES */staticlongf(r,subkey)unsigned long r; /* 32 bits */unsigned char subkey[8]; /* 48-bit key for this round */{ register unsigned long rval,rt;#ifdef TRACE unsigned char *cp; int i; printf("f(%08lx, %02x %02x %02x %02x %02x %02x %02x %02x) = ", r, subkey[0], subkey[1], subkey[2], subkey[3], subkey[4], subkey[5], subkey[6], subkey[7]);#endif /* Run E(R) ^ K through the combined S & P boxes * This code takes advantage of a convenient regularity in * E, namely that each group of 6 bits in E(R) feeding * a single S-box is a contiguous segment of R. */ rt = (r >> 1) | ((r & 1) ? 0x80000000 : 0); rval = 0; rval |= sp[0][((rt >> 26) ^ *subkey++) & 0x3f]; rval |= sp[1][((rt >> 22) ^ *subkey++) & 0x3f]; rval |= sp[2][((rt >> 18) ^ *subkey++) & 0x3f]; rval |= sp[3][((rt >> 14) ^ *subkey++) & 0x3f]; rval |= sp[4][((rt >> 10) ^ *subkey++) & 0x3f]; rval |= sp[5][((rt >> 6) ^ *subkey++) & 0x3f]; rval |= sp[6][((rt >> 2) ^ *subkey++) & 0x3f]; rt = (r << 1) | ((r & 0x80000000) ? 1 : 0); rval |= sp[7][(rt ^ *subkey) & 0x3f];#ifdef TRACE printf(" %08lx\n",rval);#endif return rval;}/* initialize a perm array */staticperminit(perm,p)char perm[16][16][8]; /* 64-bit, either init or final */char p[64];{ register int l, j, k; int i,m; /* Clear the permutation array */ for (i=0; i<16; i++) for (j=0; j<16; j++) for (k=0; k<8; k++) perm[i][j][k]=0; for (i=0; i<16; i++) /* each input nibble position */ for (j = 0; j < 16; j++)/* each possible input nibble */ for (k = 0; k < 64; k++)/* each output bit position */ { l = p[k] - 1; /* where does this bit come from*/ if ((l >> 2) != i) /* does it come from input posn?*/ continue; /* if not, bit k is 0 */ if (!(j & nibblebit[l & 3])) continue; /* any such bit in input? */ m = k & 07; /* which bit is this in the byte*/ perm[i][j][k>>3] |= bytebit[m]; } return(0);}/* Initialize the lookup table for the combined S and P boxes */static intspinit(){ char pbox[32]; int p,i,s,j,rowcol; long val; /* Compute pbox, the inverse of p32i. * This is easier to work with */ for(p=0;p<32;p++){ for(i=0;i<32;i++){ if(p32i[i]-1 == p){ pbox[p] = i; break; } } } for(s = 0; s < 8; s++){ /* For each S-box */ for(i=0; i<64; i++){ /* For each possible input */ val = 0; /* The row number is formed from the first and last * bits; the column number is from the middle 4 */ rowcol = (i & 32) | ((i & 1) ? 16 : 0) | ((i >> 1) & 0xf); for(j=0;j<4;j++){ /* For each output bit */ if(si[s][rowcol] & (8 >> j)){ val |= 1L << (31 - pbox[4*s + j]); } } sp[s][i] = val;#ifdef DEBUG printf("sp[%d][%2d] = %08lx\n",s,i,sp[s][i]);#endif } } return(0);}#ifdef LITTLE_ENDIAN/* Byte swap a long */staticunsigned longbyteswap(x)unsigned long x;{ register char *cp,tmp; cp = (char *)&x; tmp = cp[3]; cp[3] = cp[0]; cp[0] = tmp; tmp = cp[2]; cp[2] = cp[1]; cp[1] = tmp; return x;}#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -