Revert "Update myserpent.c"

This reverts commit 41411e2f9b.
This commit is contained in:
Simon
2017-04-13 13:05:20 +08:00
parent 47d687de92
commit e014549e6a

View File

@@ -1,230 +1,319 @@
/** /* This is an implementation of the encryption algorithm: */
Copyright © 2015 Odzhan /* Serpent by Ross Anderson, Eli Biham and Lars Knudsen */
Copyright © 2008 Daniel Otte /* which is a candidate algorithm in the Advanced Encryption Standard */
All Rights Reserved. /* programme of the US National Institute of Standards and Technology. */
/* Copyright in this implementation is held by Dou Qinglin. but I */
/* hereby give permission for its free direct or derivative use subject */
/* to acknowledgment of its origin and compliance with any conditions */
/* that the originators of the algorithm place on its exploitation. */
Redistribution and use in source and binary forms, with or without #include <stdio.h>
modification, are permitted provided that the following conditions are #include <stdlib.h>
met: #include "myserpent.h"
1. Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in the
documentation and/or other materials provided with the distribution.
3. The name of the author may not be used to endorse or promote products
derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY AUTHORS "AS IS" AND ANY EXPRESS OR
IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
POSSIBILITY OF SUCH DAMAGE. */
#include "serpent.h" #define IN
#define OUT
void linear(IN unsigned long int *li_0,IN unsigned long int *li_1,IN unsigned long int *li_2,IN unsigned long int *li_3,OUT unsigned long int *lo_0,OUT unsigned long int *lo_1,OUT unsigned long int *lo_2,OUT unsigned long int *lo_3);
void IP(IN unsigned long int *ip_i0,IN unsigned long int *ip_i1,IN unsigned long int *ip_i2,IN unsigned long int *ip_i3,OUT unsigned long int *ip_o0,OUT unsigned long int *ip_o1,OUT unsigned long int *ip_o2,OUT unsigned long int *ip_o3);
void FP(IN unsigned long int *fp_i0,IN unsigned long int *fp_i1,IN unsigned long int *fp_i2,IN unsigned long int *fp_i3,OUT unsigned long int *fp_o0,OUT unsigned long int *fp_o1,OUT unsigned long int *fp_o2,OUT unsigned long int *fp_o3);
volatile unsigned long int takbit_in0,takbit_in1,takbit_in2,takbit_in3;
void serpent_whiten(serpent_blk *dst, serpent_key_t *src, int idx) { unsigned char takebit(unsigned char bit_num){
uint8_t i; unsigned char bit_out;
serpent_blk *p = (serpent_blk*)&src->x[idx]; if (bit_num< 32) bit_out = ((takbit_in0<< bit_num )&0x80000000)>>31;
else if (bit_num< 64) bit_out = ((takbit_in1<<(bit_num-32))&0x80000000)>>31;
for (i = 0; i<SERPENT_BLK_LEN / 4; i++) { else if (bit_num< 96) bit_out = ((takbit_in2<<(bit_num-64))&0x80000000)>>31;
dst->w[i] ^= p->w[i]; else if (bit_num< 128) bit_out = ((takbit_in3<<(bit_num-96))&0x80000000)>>31;
} else ;
return (bit_out & 0x00000001);
} }
void permute(serpent_blk *out, //sbox involking func, each block use 1 sbox 32 times by involking this func for 4 times
serpent_blk *in, int type) unsigned long int sb(char sb_num,unsigned long int sb_in_long){
{ char sb_i[8];
uint8_t cy; char sb_o[8];
uint8_t n, m; unsigned long int sb_out_long;
char cnt;
for (n = 0; n<SERPENT_BLK_LEN / 4; n++) { //data div, 32bit input divide into 8 parts, each 4bit
out->w[n] = 0; sb_i[0] = (sb_in_long>>28) & 0x0f; // 0~3f
} sb_i[1] = (sb_in_long>>24) & 0x0f; // 4~7
sb_i[2] = (sb_in_long>>20) & 0x0f; // 8~11
if (type == SERPENT_IP) sb_i[3] = (sb_in_long>>16) & 0x0f; // 12~15
sb_i[4] = (sb_in_long>>12) & 0x0f; // 16~19
sb_i[5] = (sb_in_long>> 8) & 0x0f; // 20~23
sb_i[6] = (sb_in_long>> 4) & 0x0f; // 24~27
sb_i[7] = (sb_in_long ) & 0x0f; // 28~31
//judge which sbox to use,and get 8 outputs of 8 independent
switch (sb_num)
{ {
for (n = 0; n<16; n++) { case 0: for (cnt = 0; cnt < 8; cnt++) sb_o[cnt] = sb0(sb_i[cnt] );break;
for (m = 0; m<8; m++) { case 1: for (cnt = 0; cnt < 8; cnt++) sb_o[cnt] = sb1(sb_i[cnt] );break;
cy = in->w[m % 4] & 1; case 2: for (cnt = 0; cnt < 8; cnt++) sb_o[cnt] = sb2(sb_i[cnt] );break;
in->w[m % 4] >>= 1; case 3: for (cnt = 0; cnt < 8; cnt++) sb_o[cnt] = sb3(sb_i[cnt] );break;
out->b[n] = (cy << 7) | (out->b[n] >> 1); case 4: for (cnt = 0; cnt < 8; cnt++) sb_o[cnt] = sb4(sb_i[cnt] );break;
} case 5: for (cnt = 0; cnt < 8; cnt++) sb_o[cnt] = sb5(sb_i[cnt] );break;
} case 6: for (cnt = 0; cnt < 8; cnt++) sb_o[cnt] = sb6(sb_i[cnt] );break;
} case 7: for (cnt = 0; cnt < 8; cnt++) sb_o[cnt] = sb7(sb_i[cnt] );break;
else { default: for (cnt = 0; cnt < 8; cnt++) sb_o[cnt] = 0x0; break;
for (n = 0; n<4; n++) {
for (m = 0; m<32; m++) {
cy = in->w[n] & 1;
in->w[n] >>= 1;
out->w[m % 4] = (cy << 31) | (out->w[m % 4] >> 1);
}
}
} }
//combine the sbox output together
sb_out_long = (sb_o[0]<<28) + (sb_o[1]<<24) + (sb_o[2]<<20) + (sb_o[3]<<16) + (sb_o[4]<<12) + (sb_o[5]<<8) + (sb_o[6]<<4) + sb_o[7];
return sb_out_long;
} }
#define HI_NIBBLE(b) (((b) >> 4) & 0x0F) //define the sbox0~7 un-linear logic
#define LO_NIBBLE(b) ((b) & 0x0F) char sb0(char sb0_in){
char sb0_o;
uint32_t serpent_gen_w(uint32_t *b, uint32_t i) { switch (sb0_in){
uint32_t ret; case 0x0: sb0_o= 3 ;break;
ret = b[0] ^ b[3] ^ b[5] ^ b[7] ^ GOLDEN_RATIO ^ i; case 0x1: sb0_o= 8 ;break;
return ROTL32(ret, 11); case 0x2: sb0_o= 15;break;
case 0x3: sb0_o= 1 ;break;
case 0x4: sb0_o= 10;break;
case 0x5: sb0_o= 6 ;break;
case 0x6: sb0_o= 5 ;break;
case 0x7: sb0_o= 11;break;
case 0x8: sb0_o= 14;break;
case 0x9: sb0_o= 13;break;
case 0xA: sb0_o= 4 ;break;
case 0xB: sb0_o= 2 ;break;
case 0xC: sb0_o= 7 ;break;
case 0xD: sb0_o= 0 ;break;
case 0xE: sb0_o= 9 ;break;
case 0xF: sb0_o= 12;break;
default: sb0_o= 0 ;break;
}
return sb0_o;
} }
void serpent_subbytes(serpent_blk *blk, uint32_t box_idx, int type) char sb1(char sb1_in){
{ char sb1_o;
serpent_blk tmp_blk, sb; switch (sb1_in){
uint8_t *sbp; case 0x0: sb1_o= 15;break;
uint8_t i, t; case 0x1: sb1_o= 12;break;
case 0x2: sb1_o= 2 ;break;
uint8_t sbox[8][8] = case 0x3: sb1_o= 7 ;break;
{ { 0x83, 0x1F, 0x6A, 0xB5, 0xDE, 0x24, 0x07, 0xC9 }, case 0x4: sb1_o= 9 ;break;
{ 0xCF, 0x72, 0x09, 0xA5, 0xB1, 0x8E, 0xD6, 0x43 }, case 0x5: sb1_o= 0 ;break;
{ 0x68, 0x97, 0xC3, 0xFA, 0x1D, 0x4E, 0xB0, 0x25 }, case 0x6: sb1_o= 5 ;break;
{ 0xF0, 0x8B, 0x9C, 0x36, 0x1D, 0x42, 0x7A, 0xE5 }, case 0x7: sb1_o= 10;break;
{ 0xF1, 0x38, 0x0C, 0x6B, 0x52, 0xA4, 0xE9, 0xD7 }, case 0x8: sb1_o= 1 ;break;
{ 0x5F, 0xB2, 0xA4, 0xC9, 0x30, 0x8E, 0x6D, 0x17 }, case 0x9: sb1_o= 11;break;
{ 0x27, 0x5C, 0x48, 0xB6, 0x9E, 0xF1, 0x3D, 0x0A }, case 0xA: sb1_o= 14;break;
{ 0xD1, 0x0F, 0x8E, 0xB2, 0x47, 0xAC, 0x39, 0x65 } case 0xB: sb1_o= 8 ;break;
}; case 0xC: sb1_o= 6 ;break;
case 0xD: sb1_o= 13;break;
uint8_t sbox_inv[8][8] = case 0xE: sb1_o= 3 ;break;
{ { 0x3D, 0x0B, 0x6A, 0xC5, 0xE1, 0x74, 0x9F, 0x28 }, case 0xF: sb1_o= 4 ;break;
{ 0x85, 0xE2, 0x6F, 0x3C, 0x4B, 0x97, 0xD1, 0x0A }, default: sb1_o= 0 ;break;
{ 0x9C, 0x4F, 0xEB, 0x21, 0x30, 0xD6, 0x85, 0x7A },
{ 0x90, 0x7A, 0xEB, 0xD6, 0x53, 0x2C, 0x84, 0x1F },
{ 0x05, 0x38, 0x9A, 0xE7, 0xC2, 0x6B, 0xF4, 0x1D },
{ 0xF8, 0x92, 0x14, 0xED, 0x6B, 0x35, 0xC7, 0x0A },
{ 0xAF, 0xD1, 0x35, 0x06, 0x94, 0x7E, 0xC2, 0xB8 },
{ 0x03, 0xD6, 0xE9, 0x8F, 0xC5, 0x7B, 0x1A, 0x24 }
};
box_idx &= 7;
if (type == SERPENT_ENCRYPT) {
sbp = (uint8_t*)&sbox[box_idx][0];
} }
else { return sb1_o;
sbp = (uint8_t*)&sbox_inv[box_idx][0];
}
for (i = 0; i<16; i += 2) {
t = sbp[i / 2];
sb.b[i + 0] = LO_NIBBLE(t);
sb.b[i + 1] = HI_NIBBLE(t);
}
permute(&tmp_blk, blk, SERPENT_IP);
for (i = 0; i<SERPENT_BLK_LEN; i++) {
t = tmp_blk.b[i];
tmp_blk.b[i] = (sb.b[HI_NIBBLE(t)] << 4) | sb.b[LO_NIBBLE(t)];
}
permute(blk, &tmp_blk, SERPENT_FP);
} }
void serpent_lt(serpent_blk* x, int enc) char sb2(char sb2_in){
{ char sb2_o;
uint32_t x0, x1, x2, x3; switch (sb2_in){
case 0x0: sb2_o= 8 ;break;
// load case 0x1: sb2_o= 6 ;break;
x0 = x->w[0]; case 0x2: sb2_o= 7 ;break;
x1 = x->w[1]; case 0x3: sb2_o= 9 ;break;
x2 = x->w[2]; case 0x4: sb2_o= 3 ;break;
x3 = x->w[3]; case 0x5: sb2_o= 12;break;
case 0x6: sb2_o= 10;break;
if (enc == SERPENT_DECRYPT) { case 0x7: sb2_o= 15;break;
x2 = ROTL32(x2, 10); case 0x8: sb2_o= 13;break;
x0 = ROTR32(x0, 5); case 0x9: sb2_o= 1 ;break;
x2 ^= x3 ^ (x1 << 7); case 0xA: sb2_o= 14;break;
x0 ^= x1 ^ x3; case 0xB: sb2_o= 4 ;break;
x3 = ROTR32(x3, 7); case 0xC: sb2_o= 0 ;break;
x1 = ROTR32(x1, 1); case 0xD: sb2_o= 11;break;
x3 ^= x2 ^ (x0 << 3); case 0xE: sb2_o= 5 ;break;
x1 ^= x0 ^ x2; case 0xF: sb2_o= 2 ;break;
x2 = ROTR32(x2, 3); default: sb2_o= 0 ;break;
x0 = ROTR32(x0, 13);
} }
else { return sb2_o;
x0 = ROTL32(x0, 13); }
x2 = ROTL32(x2, 3);
x1 ^= x0 ^ x2; char sb3(char sb3_in){
x3 ^= x2 ^ (x0 << 3); char sb3_o;
x1 = ROTL32(x1, 1); switch (sb3_in){
x3 = ROTL32(x3, 7); case 0x0: sb3_o= 0 ;break;
x0 ^= x1 ^ x3; case 0x1: sb3_o= 15;break;
x2 ^= x3 ^ (x1 << 7); case 0x2: sb3_o= 11;break;
x0 = ROTL32(x0, 5); case 0x3: sb3_o= 8 ;break;
x2 = ROTR32(x2, 10); case 0x4: sb3_o= 12;break;
case 0x5: sb3_o= 9 ;break;
case 0x6: sb3_o= 6 ;break;
case 0x7: sb3_o= 3 ;break;
case 0x8: sb3_o= 13;break;
case 0x9: sb3_o= 1 ;break;
case 0xA: sb3_o= 2 ;break;
case 0xB: sb3_o= 4 ;break;
case 0xC: sb3_o= 10;break;
case 0xD: sb3_o= 7 ;break;
case 0xE: sb3_o= 5 ;break;
case 0xF: sb3_o= 14;break;
default: sb3_o= 0 ;break;
} }
x->w[0] = x0; return sb3_o;
x->w[1] = x1;
x->w[2] = x2;
x->w[3] = x3;
} }
void serpent_set_encrypt_key(serpent_key_t *key, void *user_key) char sb4(char sb4_in){
{ char sb4_o;
union { switch (sb4_in){
uint8_t b[32]; case 0x0: sb4_o= 1 ;break;
uint32_t w[8]; case 0x1: sb4_o= 15;break;
} s_ws; case 0x2: sb4_o= 8 ;break;
case 0x3: sb4_o= 3 ;break;
uint32_t i, j; case 0x4: sb4_o= 12;break;
case 0x5: sb4_o= 0 ;break;
// copy key input to local buffer case 0x6: sb4_o= 11;break;
memcpy(&s_ws.b[0], user_key, SERPENT_KEY256); case 0x7: sb4_o= 6 ;break;
case 0x8: sb4_o= 2 ;break;
// expand the key case 0x9: sb4_o= 5 ;break;
for (i = 0; i <= SERPENT_ROUNDS; i++) { case 0xA: sb4_o= 4 ;break;
for (j = 0; j<4; j++) { case 0xB: sb4_o= 10;break;
key->x[i][j] = serpent_gen_w(s_ws.w, i * 4 + j); case 0xC: sb4_o= 9 ;break;
memmove(&s_ws.b, &s_ws.b[4], 7 * 4); case 0xD: sb4_o= 14;break;
s_ws.w[7] = key->x[i][j]; case 0xE: sb4_o= 7 ;break;
} case 0xF: sb4_o= 13;break;
serpent_subbytes((serpent_blk*)&key->x[i], 3 - i, SERPENT_ENCRYPT); default: sb4_o= 0; break;
} }
return sb4_o;
} }
void serpent_encrypt(void *in, serpent_key_t *key) char sb5(char sb5_in){
{ char sb5_o;
int8_t i; switch (sb5_in){
serpent_blk *out = in; case 0x0: sb5_o= 15;break;
case 0x1: sb5_o= 5 ;break;
i = 0; case 0x2: sb5_o= 2 ;break;
for (;;) { case 0x3: sb5_o= 11;break;
// xor with subkey case 0x4: sb5_o= 4 ;break;
serpent_whiten(out, key, i); case 0x5: sb5_o= 10;break;
// apply sbox case 0x6: sb5_o= 9 ;break;
serpent_subbytes(out, i, SERPENT_ENCRYPT); case 0x7: sb5_o= 12;break;
if (++i == SERPENT_ROUNDS) break; case 0x8: sb5_o= 0 ;break;
// linear transformation case 0x9: sb5_o= 3 ;break;
serpent_lt(out, SERPENT_ENCRYPT); case 0xA: sb5_o= 14;break;
} case 0xB: sb5_o= 8 ;break;
serpent_whiten(out, key, i); case 0xC: sb5_o= 13;break;
case 0xD: sb5_o= 6 ;break;
case 0xE: sb5_o= 7 ;break;
case 0xF: sb5_o= 1 ;break;
default: sb5_o= 0; break;
}
return sb5_o;
} }
void serpent_decrypt(void *in, serpent_key_t *key) char sb6(char sb6_in){
{ char sb6_o;
int8_t i; switch (sb6_in){
serpent_blk *out = in; case 0x0: sb6_o= 7 ;break;
case 0x1: sb6_o= 2 ;break;
i = SERPENT_ROUNDS; case 0x2: sb6_o= 12;break;
serpent_whiten(out, key, i); case 0x3: sb6_o= 5 ;break;
for (;;) { case 0x4: sb6_o= 8 ;break;
--i; case 0x5: sb6_o= 4 ;break;
// apply sbox case 0x6: sb6_o= 6 ;break;
serpent_subbytes(out, i, SERPENT_DECRYPT); case 0x7: sb6_o= 11;break;
// xor with subkey case 0x8: sb6_o= 14;break;
serpent_whiten(out, key, i); case 0x9: sb6_o= 9 ;break;
if (i == 0) break; case 0xA: sb6_o= 1 ;break;
// linear transformation case 0xB: sb6_o= 15;break;
serpent_lt(out, SERPENT_DECRYPT); case 0xC: sb6_o= 13;break;
} case 0xD: sb6_o= 3 ;break;
case 0xE: sb6_o= 10;break;
case 0xF: sb6_o= 0 ;break;
default: sb6_o= 0 ;break;
}
return sb6_o;
}
char sb7(char sb7_in){
char sb7_o;
switch (sb7_in){
case 0x0: sb7_o= 1 ;break;
case 0x1: sb7_o= 13;break;
case 0x2: sb7_o= 15;break;
case 0x3: sb7_o= 0 ;break;
case 0x4: sb7_o= 14;break;
case 0x5: sb7_o= 8 ;break;
case 0x6: sb7_o= 2 ;break;
case 0x7: sb7_o= 11;break;
case 0x8: sb7_o= 7 ;break;
case 0x9: sb7_o= 4 ;break;
case 0xA: sb7_o= 12;break;
case 0xB: sb7_o= 10;break;
case 0xC: sb7_o= 9 ;break;
case 0xD: sb7_o= 3 ;break;
case 0xE: sb7_o= 5 ;break;
case 0xF: sb7_o= 6 ;break;
default: sb7_o= 0 ;break;
}
return sb7_o;
}
//initial permutation
void IP(IN unsigned long int *ip_i0,IN unsigned long int *ip_i1,IN unsigned long int *ip_i2,IN unsigned long int *ip_i3,OUT unsigned long int *ip_o0,OUT unsigned long int *ip_o1,OUT unsigned long int *ip_o2,OUT unsigned long int *ip_o3){
unsigned long int tmp_0,tmp_1,tmp_2,tmp_3;
takbit_in0 = *ip_i0;
takbit_in1 = *ip_i1;
takbit_in2 = *ip_i2;
takbit_in3 = *ip_i3;
//execute takbit function
tmp_0 = (takebit(120)<<31) + (takebit( 88)<<30) + (takebit( 56)<<29) + (takebit( 24)<<28) + (takebit(121)<<27) + (takebit( 89)<<26) + (takebit( 57)<<25) + (takebit( 25)<<24) + (takebit(122)<<23) + (takebit( 90)<<22) + (takebit( 58)<<21) + (takebit( 26)<<20) + (takebit(123)<<19) + (takebit( 91)<<18) + (takebit( 59)<<17) + (takebit( 27)<<16) + (takebit(124)<<15) + (takebit( 92)<<14) + (takebit( 60)<<13) + (takebit( 28)<<12) + (takebit(125)<<11) + (takebit( 93)<<10) + (takebit( 61)<<9 ) + (takebit( 29)<<8 ) + (takebit(126)<<7 ) + (takebit( 94)<<6 ) + (takebit( 62)<<5 ) + (takebit( 30)<<4 ) + (takebit(127)<<3 ) + (takebit( 95)<<2 ) + (takebit( 63)<<1 ) + (takebit( 31) );
tmp_1 = (takebit(112)<<31) + (takebit( 80)<<30) + (takebit( 48)<<29) + (takebit( 16)<<28) + (takebit(113)<<27) + (takebit( 81)<<26) + (takebit( 49)<<25) + (takebit( 17)<<24) + (takebit(114)<<23) + (takebit( 82)<<22) + (takebit( 50)<<21) + (takebit( 18)<<20) + (takebit(115)<<19) + (takebit( 83)<<18) + (takebit( 51)<<17) + (takebit( 19)<<16) + (takebit(116)<<15) + (takebit( 84)<<14) + (takebit( 52)<<13) + (takebit( 20)<<12) + (takebit(117)<<11) + (takebit( 85)<<10) + (takebit( 53)<<9 ) + (takebit( 21)<<8 ) + (takebit(118)<<7 ) + (takebit( 86)<<6 ) + (takebit( 54)<<5 ) + (takebit( 22)<<4 ) + (takebit(119)<<3 ) + (takebit( 87)<<2 ) + (takebit( 55)<<1 ) + (takebit( 23) );
tmp_2 = (takebit(104)<<31) + (takebit( 72)<<30) + (takebit( 40)<<29) + (takebit( 8)<<28) + (takebit(105)<<27) + (takebit( 73)<<26) + (takebit( 41)<<25) + (takebit( 9)<<24) + (takebit(106)<<23) + (takebit( 74)<<22) + (takebit( 42)<<21) + (takebit( 10)<<20) + (takebit(107)<<19) + (takebit( 75)<<18) + (takebit( 43)<<17) + (takebit( 11)<<16) + (takebit(108)<<15) + (takebit( 76)<<14) + (takebit( 44)<<13) + (takebit( 12)<<12) + (takebit(109)<<11) + (takebit( 77)<<10) + (takebit( 45)<<9 ) + (takebit( 13)<<8 ) + (takebit(110)<<7 ) + (takebit( 78)<<6 ) + (takebit( 46)<<5 ) + (takebit( 14)<<4 ) + (takebit(111)<<3 ) + (takebit( 79)<<2 ) + (takebit( 47)<<1 ) + (takebit( 15) );
tmp_3 = (takebit( 96)<<31) + (takebit( 64)<<30) + (takebit( 32)<<29) + (takebit( 0)<<28) + (takebit( 97)<<27) + (takebit( 65)<<26) + (takebit( 33)<<25) + (takebit( 1)<<24) + (takebit( 98)<<23) + (takebit( 66)<<22) + (takebit( 34)<<21) + (takebit( 2)<<20) + (takebit( 99)<<19) + (takebit( 67)<<18) + (takebit( 35)<<17) + (takebit( 3)<<16) + (takebit(100)<<15) + (takebit( 68)<<14) + (takebit( 36)<<13) + (takebit( 4)<<12) + (takebit(101)<<11) + (takebit( 69)<<10) + (takebit( 37)<<9 ) + (takebit( 5)<<8 ) + (takebit(102)<<7 ) + (takebit( 70)<<6 ) + (takebit( 38)<<5 ) + (takebit( 6)<<4 ) + (takebit(103)<<3 ) + (takebit( 71)<<2 ) + (takebit( 39)<<1 ) + (takebit( 7) );
//write data to sb_in[]
*ip_o0 = tmp_0;
*ip_o1 = tmp_1;
*ip_o2 = tmp_2;
*ip_o3 = tmp_3;
}
//initial permutation
void FP(IN unsigned long int *fp_i0,IN unsigned long int *fp_i1,IN unsigned long int *fp_i2,IN unsigned long int *fp_i3,OUT unsigned long int *fp_o0,OUT unsigned long int *fp_o1,OUT unsigned long int *fp_o2,OUT unsigned long int *fp_o3){
unsigned long int tmp_0,tmp_1,tmp_2,tmp_3;
takbit_in0 = *fp_i0;
takbit_in1 = *fp_i1;
takbit_in2 = *fp_i2;
takbit_in3 = *fp_i3;
//execute takbit function
tmp_3 = (takebit(96)<<31) + (takebit(100 )<<30) + (takebit(104 )<<29) + (takebit(108 )<<28) + (takebit(112 )<<27) + (takebit(116 )<<26) + (takebit(120 )<<25) + (takebit(124 )<<24) + (takebit(64)<<23) + (takebit(68 )<<22) + (takebit(72 )<<21) + (takebit(76 )<<20) + (takebit(80 )<<19) + (takebit(84 )<<18) + (takebit(88 )<<17) + (takebit(92 )<<16) + (takebit(32)<<15) + (takebit(36 )<<14) + (takebit(40 )<<13) + (takebit(44 )<<12) + (takebit(48 )<<11) + (takebit(52 )<<10) + (takebit(56 )<<9) + (takebit(60 )<<8) + (takebit(0 )<<7) + (takebit( 4 )<<6) + (takebit( 8 )<<5) + (takebit(12 )<<4) + (takebit(16 )<<3) + (takebit(20 )<<2) + (takebit(24 )<<1) + takebit(28 );
tmp_2 = (takebit(97)<<31) + (takebit(101 )<<30) + (takebit(105 )<<29) + (takebit(109 )<<28) + (takebit(113 )<<27) + (takebit(117 )<<26) + (takebit(121 )<<25) + (takebit(125 )<<24) + (takebit(65)<<23) + (takebit(69 )<<22) + (takebit(73 )<<21) + (takebit(77 )<<20) + (takebit(81 )<<19) + (takebit(85 )<<18) + (takebit(89 )<<17) + (takebit(93 )<<16) + (takebit(33)<<15) + (takebit(37 )<<14) + (takebit(41 )<<13) + (takebit(45 )<<12) + (takebit(49 )<<11) + (takebit(53 )<<10) + (takebit(57 )<<9) + (takebit(61 )<<8) + (takebit(1 )<<7) + (takebit( 5 )<<6) + (takebit( 9 )<<5) + (takebit(13 )<<4) + (takebit(17 )<<3) + (takebit(21 )<<2) + (takebit(25 )<<1) + takebit(29 );
tmp_1 = (takebit(98)<<31) + (takebit(102 )<<30) + (takebit(106 )<<29) + (takebit(110 )<<28) + (takebit(114 )<<27) + (takebit(118 )<<26) + (takebit(122 )<<25) + (takebit(126 )<<24) + (takebit(66)<<23) + (takebit(70 )<<22) + (takebit(74 )<<21) + (takebit(78 )<<20) + (takebit(82 )<<19) + (takebit(86 )<<18) + (takebit(90 )<<17) + (takebit(94 )<<16) + (takebit(34)<<15) + (takebit(38 )<<14) + (takebit(42 )<<13) + (takebit(46 )<<12) + (takebit(50 )<<11) + (takebit(54 )<<10) + (takebit(58 )<<9) + (takebit(62 )<<8) + (takebit(2 )<<7) + (takebit( 6 )<<6) + (takebit(10 )<<5) + (takebit(14 )<<4) + (takebit(18 )<<3) + (takebit(22 )<<2) + (takebit(26 )<<1) + takebit(30 );
tmp_0 = (takebit(99)<<31) + (takebit(103 )<<30) + (takebit(107 )<<29) + (takebit(111 )<<28) + (takebit(115 )<<27) + (takebit(119 )<<26) + (takebit(123 )<<25) + (takebit(127 )<<24) + (takebit(67)<<23) + (takebit(71 )<<22) + (takebit(75 )<<21) + (takebit(79 )<<20) + (takebit(83 )<<19) + (takebit(87 )<<18) + (takebit(91 )<<17) + (takebit(95 )<<16) + (takebit(35)<<15) + (takebit(39 )<<14) + (takebit(43 )<<13) + (takebit(47 )<<12) + (takebit(51 )<<11) + (takebit(55 )<<10) + (takebit(59 )<<9) + (takebit(63 )<<8) + (takebit(3 )<<7) + (takebit( 7 )<<6) + (takebit(11 )<<5) + (takebit(15 )<<4) + (takebit(19 )<<3) + (takebit(23 )<<2) + (takebit(27 )<<1) + takebit(31 );
//data out
*fp_o0 = tmp_0;
*fp_o1 = tmp_1;
*fp_o2 = tmp_2;
*fp_o3 = tmp_3;
}
void linear(IN unsigned long int *li_0,IN unsigned long int *li_1,IN unsigned long int *li_2,IN unsigned long int *li_3,OUT unsigned long int *lo_0,OUT unsigned long int *lo_1,OUT unsigned long int *lo_2,OUT unsigned long int *lo_3){
unsigned long int tmp_0,tmp_1,tmp_2,tmp_3;
tmp_0 = *li_0;
tmp_1 = *li_1;
tmp_2 = *li_2;
tmp_3 = *li_3;
tmp_0 = rotl(tmp_0, 13);
tmp_2 = rotl(tmp_2, 3);
tmp_1 = tmp_1 ^ tmp_0 ^ tmp_2;
tmp_3 = tmp_3 ^ tmp_2 ^ (tmp_0 << 3);
tmp_1 = rotl(tmp_1, 1);
tmp_3 = rotl(tmp_3, 7);
tmp_0 = tmp_0 ^ tmp_1 ^ tmp_3;
tmp_2 = tmp_2 ^ tmp_3 ^ (tmp_1 << 7);
tmp_0 = rotl(tmp_0, 5);
tmp_2 = rotl(tmp_2, 22);
*lo_0 = tmp_0;
*lo_1 = tmp_1;
*lo_2 = tmp_2;
*lo_3 = tmp_3;
} }