The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/crypto/cast128/cast128.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /*      $NetBSD: cast128.c,v 1.7 2003/08/26 20:03:57 thorpej Exp $      */
    2 /*      $OpenBSD: cast.c,v 1.2 2000/06/06 06:49:47 deraadt Exp $       */
    3 
    4 /*
    5  *      CAST-128 in C
    6  *      Written by Steve Reid <sreid@sea-to-sky.net>
    7  *      100% Public Domain - no warranty
    8  *      Released 1997.10.11
    9  */
   10 
   11 #include <sys/cdefs.h>
   12 __KERNEL_RCSID(0, "$NetBSD: cast128.c,v 1.7 2003/08/26 20:03:57 thorpej Exp $");
   13 
   14 #include <sys/types.h>
   15 #include <crypto/cast128/cast128.h>
   16 #include <crypto/cast128/cast128sb.h>
   17 
   18 /* Macros to access 8-bit bytes out of a 32-bit word */
   19 #define U_INT8_Ta(x) ( (u_int8_t) (x>>24) )
   20 #define U_INT8_Tb(x) ( (u_int8_t) ((x>>16)&255) )
   21 #define U_INT8_Tc(x) ( (u_int8_t) ((x>>8)&255) )
   22 #define U_INT8_Td(x) ( (u_int8_t) ((x)&255) )
   23 
   24 /* Circular left shift */
   25 #define ROL(x, n) ( ((x)<<(n)) | ((x)>>(32-(n))) )
   26 
   27 /* CAST-128 uses three different round functions */
   28 #define F1(l, r, i) \
   29         t = ROL(key->xkey[i] + r, key->xkey[i+16]); \
   30         l ^= ((cast_sbox1[U_INT8_Ta(t)] ^ cast_sbox2[U_INT8_Tb(t)]) - \
   31          cast_sbox3[U_INT8_Tc(t)]) + cast_sbox4[U_INT8_Td(t)];
   32 #define F2(l, r, i) \
   33         t = ROL(key->xkey[i] ^ r, key->xkey[i+16]); \
   34         l ^= ((cast_sbox1[U_INT8_Ta(t)] - cast_sbox2[U_INT8_Tb(t)]) + \
   35          cast_sbox3[U_INT8_Tc(t)]) ^ cast_sbox4[U_INT8_Td(t)];
   36 #define F3(l, r, i) \
   37         t = ROL(key->xkey[i] - r, key->xkey[i+16]); \
   38         l ^= ((cast_sbox1[U_INT8_Ta(t)] + cast_sbox2[U_INT8_Tb(t)]) ^ \
   39          cast_sbox3[U_INT8_Tc(t)]) - cast_sbox4[U_INT8_Td(t)];
   40 
   41 
   42 /***** Encryption Function *****/
   43 
   44 void cast128_encrypt(const cast128_key* key, const u_int8_t* inblock,
   45     u_int8_t* outblock)
   46 {
   47 u_int32_t t, l, r;
   48 
   49         /* Get inblock into l,r */
   50         l = ((u_int32_t)inblock[0] << 24) | ((u_int32_t)inblock[1] << 16) |
   51          ((u_int32_t)inblock[2] << 8) | (u_int32_t)inblock[3];
   52         r = ((u_int32_t)inblock[4] << 24) | ((u_int32_t)inblock[5] << 16) |
   53          ((u_int32_t)inblock[6] << 8) | (u_int32_t)inblock[7];
   54         /* Do the work */
   55         F1(l, r,  0);
   56         F2(r, l,  1);
   57         F3(l, r,  2);
   58         F1(r, l,  3);
   59         F2(l, r,  4);
   60         F3(r, l,  5);
   61         F1(l, r,  6);
   62         F2(r, l,  7);
   63         F3(l, r,  8);
   64         F1(r, l,  9);
   65         F2(l, r, 10);
   66         F3(r, l, 11);
   67         /* Only do full 16 rounds if key length > 80 bits */
   68         if (key->rounds > 12) {
   69                 F1(l, r, 12);
   70                 F2(r, l, 13);
   71                 F3(l, r, 14);
   72                 F1(r, l, 15);
   73         }
   74         /* Put l,r into outblock */
   75         outblock[0] = U_INT8_Ta(r);
   76         outblock[1] = U_INT8_Tb(r);
   77         outblock[2] = U_INT8_Tc(r);
   78         outblock[3] = U_INT8_Td(r);
   79         outblock[4] = U_INT8_Ta(l);
   80         outblock[5] = U_INT8_Tb(l);
   81         outblock[6] = U_INT8_Tc(l);
   82         outblock[7] = U_INT8_Td(l);
   83         /* Wipe clean */
   84         t = l = r = 0;
   85 }
   86 
   87 
   88 /***** Decryption Function *****/
   89 
   90 void cast128_decrypt(const cast128_key* key, const u_int8_t* inblock,
   91     u_int8_t* outblock)
   92 {
   93 u_int32_t t, l, r;
   94 
   95         /* Get inblock into l,r */
   96         r = ((u_int32_t)inblock[0] << 24) | ((u_int32_t)inblock[1] << 16) |
   97          ((u_int32_t)inblock[2] << 8) | (u_int32_t)inblock[3];
   98         l = ((u_int32_t)inblock[4] << 24) | ((u_int32_t)inblock[5] << 16) |
   99          ((u_int32_t)inblock[6] << 8) | (u_int32_t)inblock[7];
  100         /* Do the work */
  101         /* Only do full 16 rounds if key length > 80 bits */
  102         if (key->rounds > 12) {
  103                 F1(r, l, 15);
  104                 F3(l, r, 14);
  105                 F2(r, l, 13);
  106                 F1(l, r, 12);
  107         }
  108         F3(r, l, 11);
  109         F2(l, r, 10);
  110         F1(r, l,  9);
  111         F3(l, r,  8);
  112         F2(r, l,  7);
  113         F1(l, r,  6);
  114         F3(r, l,  5);
  115         F2(l, r,  4);
  116         F1(r, l,  3);
  117         F3(l, r,  2);
  118         F2(r, l,  1);
  119         F1(l, r,  0);
  120         /* Put l,r into outblock */
  121         outblock[0] = U_INT8_Ta(l);
  122         outblock[1] = U_INT8_Tb(l);
  123         outblock[2] = U_INT8_Tc(l);
  124         outblock[3] = U_INT8_Td(l);
  125         outblock[4] = U_INT8_Ta(r);
  126         outblock[5] = U_INT8_Tb(r);
  127         outblock[6] = U_INT8_Tc(r);
  128         outblock[7] = U_INT8_Td(r);
  129         /* Wipe clean */
  130         t = l = r = 0;
  131 }
  132 
  133 
  134 /***** Key Schedual *****/
  135 
  136 void cast128_setkey(cast128_key* key, const u_int8_t* rawkey, int keybytes)
  137 {
  138 u_int32_t t[4], z[4], x[4];
  139 int i;
  140 
  141         /* Set number of rounds to 12 or 16, depending on key length */
  142         key->rounds = (keybytes <= 10 ? 12 : 16);
  143 
  144         /* Copy key to workspace x */
  145         for (i = 0; i < 4; i++) {
  146                 x[i] = 0;
  147                 if ((i*4+0) < keybytes) x[i] = (u_int32_t)rawkey[i*4+0] << 24;
  148                 if ((i*4+1) < keybytes) x[i] |= (u_int32_t)rawkey[i*4+1] << 16;
  149                 if ((i*4+2) < keybytes) x[i] |= (u_int32_t)rawkey[i*4+2] << 8;
  150                 if ((i*4+3) < keybytes) x[i] |= (u_int32_t)rawkey[i*4+3];
  151         }
  152         /* Generate 32 subkeys, four at a time */
  153         for (i = 0; i < 32; i+=4) {
  154                 switch (i & 4) {
  155                  case 0:
  156                         t[0] = z[0] = x[0] ^ cast_sbox5[U_INT8_Tb(x[3])] ^
  157                          cast_sbox6[U_INT8_Td(x[3])] ^ cast_sbox7[U_INT8_Ta(x[3])] ^
  158                          cast_sbox8[U_INT8_Tc(x[3])] ^ cast_sbox7[U_INT8_Ta(x[2])];
  159                         t[1] = z[1] = x[2] ^ cast_sbox5[U_INT8_Ta(z[0])] ^
  160                          cast_sbox6[U_INT8_Tc(z[0])] ^ cast_sbox7[U_INT8_Tb(z[0])] ^
  161                          cast_sbox8[U_INT8_Td(z[0])] ^ cast_sbox8[U_INT8_Tc(x[2])];
  162                         t[2] = z[2] = x[3] ^ cast_sbox5[U_INT8_Td(z[1])] ^
  163                          cast_sbox6[U_INT8_Tc(z[1])] ^ cast_sbox7[U_INT8_Tb(z[1])] ^
  164                          cast_sbox8[U_INT8_Ta(z[1])] ^ cast_sbox5[U_INT8_Tb(x[2])];
  165                         t[3] = z[3] = x[1] ^ cast_sbox5[U_INT8_Tc(z[2])] ^
  166                          cast_sbox6[U_INT8_Tb(z[2])] ^ cast_sbox7[U_INT8_Td(z[2])] ^
  167                          cast_sbox8[U_INT8_Ta(z[2])] ^ cast_sbox6[U_INT8_Td(x[2])];
  168                         break;
  169                  case 4:
  170                         t[0] = x[0] = z[2] ^ cast_sbox5[U_INT8_Tb(z[1])] ^
  171                          cast_sbox6[U_INT8_Td(z[1])] ^ cast_sbox7[U_INT8_Ta(z[1])] ^
  172                          cast_sbox8[U_INT8_Tc(z[1])] ^ cast_sbox7[U_INT8_Ta(z[0])];
  173                         t[1] = x[1] = z[0] ^ cast_sbox5[U_INT8_Ta(x[0])] ^
  174                          cast_sbox6[U_INT8_Tc(x[0])] ^ cast_sbox7[U_INT8_Tb(x[0])] ^
  175                          cast_sbox8[U_INT8_Td(x[0])] ^ cast_sbox8[U_INT8_Tc(z[0])];
  176                         t[2] = x[2] = z[1] ^ cast_sbox5[U_INT8_Td(x[1])] ^
  177                          cast_sbox6[U_INT8_Tc(x[1])] ^ cast_sbox7[U_INT8_Tb(x[1])] ^
  178                          cast_sbox8[U_INT8_Ta(x[1])] ^ cast_sbox5[U_INT8_Tb(z[0])];
  179                         t[3] = x[3] = z[3] ^ cast_sbox5[U_INT8_Tc(x[2])] ^
  180                          cast_sbox6[U_INT8_Tb(x[2])] ^ cast_sbox7[U_INT8_Td(x[2])] ^
  181                          cast_sbox8[U_INT8_Ta(x[2])] ^ cast_sbox6[U_INT8_Td(z[0])];
  182                         break;
  183                 }
  184                 switch (i & 12) {
  185                  case 0:
  186                  case 12:
  187                         key->xkey[i+0] = cast_sbox5[U_INT8_Ta(t[2])] ^ cast_sbox6[U_INT8_Tb(t[2])] ^
  188                          cast_sbox7[U_INT8_Td(t[1])] ^ cast_sbox8[U_INT8_Tc(t[1])];
  189                         key->xkey[i+1] = cast_sbox5[U_INT8_Tc(t[2])] ^ cast_sbox6[U_INT8_Td(t[2])] ^
  190                          cast_sbox7[U_INT8_Tb(t[1])] ^ cast_sbox8[U_INT8_Ta(t[1])];
  191                         key->xkey[i+2] = cast_sbox5[U_INT8_Ta(t[3])] ^ cast_sbox6[U_INT8_Tb(t[3])] ^
  192                          cast_sbox7[U_INT8_Td(t[0])] ^ cast_sbox8[U_INT8_Tc(t[0])];
  193                         key->xkey[i+3] = cast_sbox5[U_INT8_Tc(t[3])] ^ cast_sbox6[U_INT8_Td(t[3])] ^
  194                          cast_sbox7[U_INT8_Tb(t[0])] ^ cast_sbox8[U_INT8_Ta(t[0])];
  195                         break;
  196                  case 4:
  197                  case 8:
  198                         key->xkey[i+0] = cast_sbox5[U_INT8_Td(t[0])] ^ cast_sbox6[U_INT8_Tc(t[0])] ^
  199                          cast_sbox7[U_INT8_Ta(t[3])] ^ cast_sbox8[U_INT8_Tb(t[3])];
  200                         key->xkey[i+1] = cast_sbox5[U_INT8_Tb(t[0])] ^ cast_sbox6[U_INT8_Ta(t[0])] ^
  201                          cast_sbox7[U_INT8_Tc(t[3])] ^ cast_sbox8[U_INT8_Td(t[3])];
  202                         key->xkey[i+2] = cast_sbox5[U_INT8_Td(t[1])] ^ cast_sbox6[U_INT8_Tc(t[1])] ^
  203                          cast_sbox7[U_INT8_Ta(t[2])] ^ cast_sbox8[U_INT8_Tb(t[2])];
  204                         key->xkey[i+3] = cast_sbox5[U_INT8_Tb(t[1])] ^ cast_sbox6[U_INT8_Ta(t[1])] ^
  205                          cast_sbox7[U_INT8_Tc(t[2])] ^ cast_sbox8[U_INT8_Td(t[2])];
  206                         break;
  207                 }
  208                 switch (i & 12) {
  209                  case 0:
  210                         key->xkey[i+0] ^= cast_sbox5[U_INT8_Tc(z[0])];
  211                         key->xkey[i+1] ^= cast_sbox6[U_INT8_Tc(z[1])];
  212                         key->xkey[i+2] ^= cast_sbox7[U_INT8_Tb(z[2])];
  213                         key->xkey[i+3] ^= cast_sbox8[U_INT8_Ta(z[3])];
  214                         break;
  215                  case 4:
  216                         key->xkey[i+0] ^= cast_sbox5[U_INT8_Ta(x[2])];
  217                         key->xkey[i+1] ^= cast_sbox6[U_INT8_Tb(x[3])];
  218                         key->xkey[i+2] ^= cast_sbox7[U_INT8_Td(x[0])];
  219                         key->xkey[i+3] ^= cast_sbox8[U_INT8_Td(x[1])];
  220                         break;
  221                  case 8:
  222                         key->xkey[i+0] ^= cast_sbox5[U_INT8_Tb(z[2])];
  223                         key->xkey[i+1] ^= cast_sbox6[U_INT8_Ta(z[3])];
  224                         key->xkey[i+2] ^= cast_sbox7[U_INT8_Tc(z[0])];
  225                         key->xkey[i+3] ^= cast_sbox8[U_INT8_Tc(z[1])];
  226                         break;
  227                  case 12:
  228                         key->xkey[i+0] ^= cast_sbox5[U_INT8_Td(x[0])];
  229                         key->xkey[i+1] ^= cast_sbox6[U_INT8_Td(x[1])];
  230                         key->xkey[i+2] ^= cast_sbox7[U_INT8_Ta(x[2])];
  231                         key->xkey[i+3] ^= cast_sbox8[U_INT8_Tb(x[3])];
  232                         break;
  233                 }
  234                 if (i >= 16) {
  235                         key->xkey[i+0] &= 31;
  236                         key->xkey[i+1] &= 31;
  237                         key->xkey[i+2] &= 31;
  238                         key->xkey[i+3] &= 31;
  239                 }
  240         }
  241         /* Wipe clean */
  242         for (i = 0; i < 4; i++) {
  243                 t[i] = x[i] = z[i] = 0;
  244         }
  245 }
  246 
  247 /* Made in Canada */

Cache object: e92c7716995b982ef84aa084a0866d6e


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.