Guest User

Cipher POC #2

a guest
Apr 26th, 2016
93
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. #include <stdint.h>
  2. #include <stdio.h>
  3. #include <inttypes.h>
  4. #include <string.h>
  5.  
  6. #define ROUNDS 32 //32 plus 1/2 rounds
  7. #define SUBKEYS (ROUNDS+2)
  8.  
  9. static const uint64_t pi[] = {
  10.     0x243f6a8885a308d3, 0x13198a2e03707344, 0xa4093822299f31d0, 0x082efa98ec4e6c89
  11. };
  12.  
  13. struct schedule
  14. {
  15.     uint64_t subkeys[SUBKEYS][4];
  16. };
  17.  
  18. uint64_t rotl(uint64_t x, uint8_t r)
  19. {
  20.     return (x << r) | (x >> (64-r));
  21. }
  22.  
  23. void F(const uint64_t x[4], uint64_t y[4])
  24. {
  25.     y[0] = x[1] + x[2] + x[3];
  26.     y[1] = x[2] + x[0] + x[3];
  27.     y[2] = x[1] - x[0] - x[3];
  28.     y[3] = x[0] - x[1] - x[2];
  29. }
  30.  
  31. void G(const uint64_t x[4], uint64_t y[4])
  32. {
  33.     y[0] = rotl(x[1],17) ^ rotl(x[2],30) ^ rotl(x[3],48);
  34.     y[1] = rotl(x[0],47) ^ rotl(x[2],13) ^ rotl(x[3],31);
  35.     y[2] = rotl(x[0],34) ^ rotl(x[1],51) ^ rotl(x[3],18);
  36.     y[3] = rotl(x[0],16) ^ rotl(x[1],33) ^ rotl(x[2],46);
  37. }
  38.  
  39. void P(const uint64_t x[4], uint64_t y[4])
  40. {
  41.     y[0] = x[2] - x[1] + x[3];
  42.     y[1] = x[3] - x[0] - x[2];
  43.     y[2] = x[0] + x[1] - x[3];
  44.     y[3] = x[0] + x[1] + x[2];
  45. }
  46.  
  47. void Q(const uint64_t x[4], uint64_t y[4])
  48. {
  49.     y[0] = rotl(x[1],13) ^ rotl(x[2],40) ^ rotl(x[3],56);
  50.     y[1] = rotl(x[0],51) ^ rotl(x[2],27) ^ rotl(x[3],43);
  51.     y[2] = rotl(x[0],24) ^ rotl(x[1],37) ^ rotl(x[3],16);
  52.     y[3] = rotl(x[0], 8) ^ rotl(x[1],21) ^ rotl(x[2],48);
  53. }
  54.  
  55. int crypt_init(const char *key, size_t key_len, struct schedule *s)
  56. {
  57.     uint64_t k[4], t1[4], t2[4], count = 0;
  58.     int i, j;
  59.  
  60.     if (key_len != 32)
  61.         return 0;
  62.    
  63.     memcpy(k, key, key_len);
  64.  
  65.     for (i=0; i<SUBKEYS/2; i++)
  66.     {
  67.         k[0] ^= pi[0];
  68.         k[1] ^= pi[1];
  69.         k[2] ^= pi[2];
  70.         k[3] ^= pi[3];
  71.  
  72.         for (j=0; j<4; j++)
  73.         {
  74.             Q(k,t1);
  75.             P(t1,k);
  76.             t2[j] = k[j];
  77.             k[j] ^= ++count;
  78.         }
  79.  
  80.         Q(t1,t2);
  81.         P(t2,s->subkeys[i]);
  82.  
  83.         if (i == 0)
  84.         {
  85.             memcpy(s->subkeys[SUBKEYS-1-i], s->subkeys[i], sizeof(s->subkeys[i]));
  86.         }
  87.         else
  88.         {
  89.             G(s->subkeys[i],s->subkeys[SUBKEYS-1-i]);
  90.         }
  91.     }
  92.     return 1;
  93. }
  94.  
  95. void crypt(const uint64_t in[4], const uint64_t tweak[4],
  96.         uint64_t out[4], const struct schedule *s)
  97. {
  98.     uint64_t a[4], b[4];
  99.     int i;
  100.  
  101.     a[0] = in[0];
  102.     a[1] = in[1];
  103.     a[2] = in[2];
  104.     a[3] = in[3];
  105.  
  106.     for (i=0; i<ROUNDS; i++)
  107.     {
  108.         a[0] ^= s->subkeys[i][0];
  109.         a[1] ^= s->subkeys[i][1];
  110.         a[2] ^= s->subkeys[i][2];
  111.         a[3] ^= s->subkeys[i][3];
  112.  
  113.         F(a,b);
  114.  
  115.         b[0] += tweak[0];
  116.         b[1] += tweak[1];
  117.         b[2] += tweak[2];
  118.         b[3] += tweak[3];
  119.  
  120.         G(b,a);
  121.     }
  122.     a[0] ^= s->subkeys[SUBKEYS-2][0];
  123.     a[1] ^= s->subkeys[SUBKEYS-2][1];
  124.     a[2] ^= s->subkeys[SUBKEYS-2][2];
  125.     a[3] ^= s->subkeys[SUBKEYS-2][3];
  126.  
  127.     F(a,b);
  128.  
  129.     b[0] += tweak[0];
  130.     b[1] += tweak[1];
  131.     b[2] += tweak[2];
  132.     b[3] += tweak[3];
  133.  
  134.     out[0] = b[0] ^ s->subkeys[SUBKEYS-1][0];
  135.     out[1] = b[1] ^ s->subkeys[SUBKEYS-1][1];
  136.     out[2] = b[2] ^ s->subkeys[SUBKEYS-1][2];
  137.     out[3] = b[3] ^ s->subkeys[SUBKEYS-1][3];
  138. }
  139.  
  140.  
  141. int main()
  142. {
  143.     struct schedule s;
  144.     uint64_t x[4] = {0x0123456789ABCDEF,0x0000000000000000,0xFFFFFFFFFFFFFFFF,0xFEDCBA9876543210}, y[4], z[4];
  145.     char k[32] = {0};
  146.     uint64_t t1[4] = {0x8888888888888888,0x7777777777777777,0x0000000000000000,0x0000000000000001};
  147.     uint64_t t2[4];
  148.  
  149.     if (crypt_init(k, sizeof(k), &s))
  150.     {
  151.         crypt(x, t1, y, &s);
  152.         printf("%016"PRIx64"%016"PRIx64"%016"PRIx64"%016"PRIx64"\n", y[0], y[1], y[2], y[3]);
  153.  
  154.         t1[0] = 0-t1[0];
  155.         t1[1] = 0-t1[1];
  156.         t1[2] = 0-t1[2];
  157.         t1[3] = 0-t1[3];
  158.  
  159.         F(t1,t2);
  160.  
  161.         crypt(y, t2, z, &s);
  162.         printf("%016"PRIx64"%016"PRIx64"%016"PRIx64"%016"PRIx64"\n", z[0], z[1], z[2], z[3]);
  163.     }
  164.     return 0;
  165. }
RAW Paste Data