Advertisement
Shokedbrain

Lucifer alg

May 18th, 2022
844
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 4.72 KB | None | 0 0
  1. #include <iostream>
  2.  
  3. using namespace std;
  4.  
  5.  
  6. template<typename T>
  7. void Swap(T& arg1, T& arg2) {
  8.     T tmp = arg1;
  9.     arg1 = arg2;
  10.     arg2 = tmp;
  11. }
  12.  
  13. const size_t block_size = 16; // 128 bit
  14. const size_t key_size = 16; // 128 bit
  15.  
  16. static const unsigned char s0[16] = {
  17.     /*0*/ 0x0C,
  18.     /*1*/ 0x0F,
  19.     /*2*/ 0x07,
  20.     /*3*/ 0x0A,
  21.     /*4*/ 0x0E,
  22.     /*5*/ 0x0D,
  23.     /*6*/ 0x0B,
  24.     /*7*/ 0x00,
  25.     /*8*/ 0x02,
  26.     /*9*/ 0x06,
  27.     /*A*/ 0x03,
  28.     /*B*/ 0x01,
  29.     /*C*/ 0x09,
  30.     /*D*/ 0x04,
  31.     /*E*/ 0x05,
  32.     /*F*/ 0x08
  33. };
  34.  
  35. static const unsigned char s1[16] = {
  36.     /*0*/ 0x07,
  37.     /*1*/ 0x02,
  38.     /*2*/ 0x0E,
  39.     /*3*/ 0x09,
  40.     /*4*/ 0x03,
  41.     /*5*/ 0x0B,
  42.     /*6*/ 0x00,
  43.     /*7*/ 0x04,
  44.     /*8*/ 0x0C,
  45.     /*9*/ 0x0D,
  46.     /*A*/ 0x01,
  47.     /*B*/ 0x0A,
  48.     /*C*/ 0x06,
  49.     /*D*/ 0x0F,
  50.     /*E*/ 0x08,
  51.     /*F*/ 0x05
  52. };
  53.  
  54. static const unsigned char m1[8] = {
  55.   0x80, 0x40, 0x20, 0x10, 0x08, 0x04, 0x02, 0x01
  56. };
  57.  
  58. static const unsigned char m2[8] = {
  59.   0x7F, 0xBF, 0xDF, 0xEF, 0xF7, 0xFB, 0xFD, 0xFE
  60. };
  61.  
  62. #define SHIFTLEFT(x, n) (x) << (n)
  63. #define SHIFTRIGHT(x, n) static_cast<unsigned char>(x) >> (n)
  64.  
  65. #define HIGHSUBBYTE(x) SHIFTRIGHT((x), 4)
  66. #define LOWSUBBYTE(x) (x) & 0x0F
  67.  
  68. void Lucifer(char block[block_size], char key[key_size], bool decrypt) {
  69.     char* lower_half = block;
  70.     char* upper_half = block + block_size / 2;
  71.  
  72.     int key_byte_idx = decrypt ? 8 : 0;
  73.  
  74.     const int round_count = 16;
  75.     for (int round = 0; round < round_count; ++round) {
  76.         if (decrypt)
  77.             key_byte_idx = (key_byte_idx + 1) % round_count;
  78.  
  79.         int transform_countrol_byte_idx = key_byte_idx;
  80.  
  81.         const int step_count = 8;
  82.         for (int step = 0; step < step_count; ++step) {
  83.             char message_byte = upper_half[step];
  84.  
  85.             // Confusion
  86.             if (key[transform_countrol_byte_idx] & m1[step_count - step - 1])
  87.                 message_byte = SHIFTLEFT(s1[HIGHSUBBYTE(message_byte)], 4) | s0[LOWSUBBYTE(message_byte)];
  88.             else
  89.                 message_byte = SHIFTLEFT(s0[HIGHSUBBYTE(message_byte)], 4) | s1[LOWSUBBYTE(message_byte)];
  90.  
  91.             // Key interruption
  92.             message_byte ^= key[key_byte_idx];
  93.  
  94.             // Permutation
  95.             message_byte = SHIFTRIGHT(message_byte & m1[0], 3) |
  96.                 SHIFTRIGHT(message_byte & m1[1], 4) |
  97.                 SHIFTLEFT(message_byte & m1[2], 2) |
  98.                 SHIFTRIGHT(message_byte & m1[3], 1) |
  99.                 SHIFTLEFT(message_byte & m1[4], 2) |
  100.                 SHIFTLEFT(message_byte & m1[5], 4) |
  101.                 SHIFTRIGHT(message_byte & m1[6], 1) |
  102.                 SHIFTLEFT(message_byte & m1[7], 1);
  103.  
  104.             // Diffusion
  105.             lower_half[(7 + step) % step_count] = ((message_byte ^ lower_half[(7 + step) % step_count]) & m1[0]) | (lower_half[(7 + step) % step_count] & m2[0]);
  106.             lower_half[(6 + step) % step_count] = ((message_byte ^ lower_half[(6 + step) % step_count]) & m1[1]) | (lower_half[(6 + step) % step_count] & m2[1]);
  107.             lower_half[(2 + step) % step_count] = ((message_byte ^ lower_half[(2 + step) % step_count]) & m1[2]) | (lower_half[(2 + step) % step_count] & m2[2]);
  108.             lower_half[(1 + step) % step_count] = ((message_byte ^ lower_half[(1 + step) % step_count]) & m1[3]) | (lower_half[(1 + step) % step_count] & m2[3]);
  109.             lower_half[(5 + step) % step_count] = ((message_byte ^ lower_half[(5 + step) % step_count]) & m1[4]) | (lower_half[(5 + step) % step_count] & m2[4]);
  110.             lower_half[(0 + step) % step_count] = ((message_byte ^ lower_half[(0 + step) % step_count]) & m1[5]) | (lower_half[(0 + step) % step_count] & m2[5]);
  111.             lower_half[(3 + step) % step_count] = ((message_byte ^ lower_half[(3 + step) % step_count]) & m1[6]) | (lower_half[(3 + step) % step_count] & m2[6]);
  112.             lower_half[(4 + step) % step_count] = ((message_byte ^ lower_half[(4 + step) % step_count]) & m1[7]) | (lower_half[(4 + step) % step_count] & m2[7]);
  113.  
  114.             if (step < step_count - 1 || decrypt)
  115.                 key_byte_idx = (key_byte_idx + 1) % round_count;
  116.         }
  117.  
  118.         // Swap halves
  119.         Swap(lower_half, upper_half);
  120.     }
  121.  
  122.     // Physically swap halves
  123.     for (int i = 0; i < block_size / 2; ++i)
  124.         Swap(block[i], block[i + block_size / 2]);
  125. }
  126.  
  127. int main()
  128. {
  129.     char crypt[block_size] = "hello, world";
  130.     char key[block_size] = {'1','2','3','4','5','6','7','8','9',
  131.         '0','A','B','C','D','E','F'};
  132.     bool check = false;
  133.     Lucifer(crypt, key, check);
  134.     for (char i : crypt)
  135.         cout << i;
  136.     cout << endl;
  137.     check = true;
  138.     Lucifer(crypt, key, check);
  139.     for (char i : crypt)
  140.         cout << i;
  141.     cout << endl;
  142.     system("pause");
  143.     return 0;
  144. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement