#include #include #include "api.h" #include "blockcipher.h" #include "options.h" //options.h to define BLOCKSIZE #if BLOCKSIZE == 64 #define MSZ 8 #elif BLOCKSIZE == 128 #define MSZ 16 #endif typedef unsigned char u8; //used for Byte-Arrays typedef unsigned int u32; //used for regular counters typedef unsigned long long ull; //used for long counters #define KSZ CRYPTO_KEYBYTES void E(u8 *ct, const u8 *key, const u8 *pt){ blockcipher_encrypt(ct, pt, key); return; } void init_state_64(u8 *X, u8 *Z, const u8 *K, const u8 *N){ u8 zero[MSZ] = { 0 }; //X <- E(K, 0) E(X, K, zero); //Z <- 0^(|K|-r)||N memset(Z, 0, KSZ); memcpy(Z, N, CRYPTO_NPUBBYTES); //Z <- K XOR 0^(|K|-r)||N for(u32 j=0; j>7; } if(Z_[p-1] & 0x80){ /*10000000*/ Z[0] ^= 0x1B; /*00011011*/ } //Z <- (Z'1, _) memcpy(&Z[p], &Z_[p], p); return; } void get_blk_key(u8 *Z, const u8 *Z_){ //Z <- permute(Z') permute(Z, Z_); return; } void opt_pad_0s_1(u8 *pad, const u8 *tbpad, const u32 tbpadLen){ if (tbpadLen == 0){ //if len == 0: return a block 0*1 memset(pad, 0, MSZ); memset(pad, 1, 1); } else { if( (tbpadLen%MSZ) == 0 ){ //if tbpad has blocklength: return tbpad memcpy(pad, tbpad, tbpadLen); } else { //else fill the remaining MSBs with 0*1 //append a full block of 0s memset(pad, 0, MSZ); //set remaining bytelength+1 as 1s memset(pad, 1, tbpadLen+1); //overwrite remaining bytelength with actual content memcpy(pad, tbpad, tbpadLen); } } return; } void shuffle(u8 *X, const u8 *X_){ u32 n_4 = MSZ/4; //X2 <- X'2 >>> 1 for(u32 j=0; j>1; } //X <- (X'1, X'0, _, _) memcpy(&X[2*n_4], X_, 2*n_4); //X <- (_, _, _, X'3) memcpy(X, &X_[3*n_4], n_4); return; } void update(u8 *Y, u8 *O, const u8 *X, const u8 *I, const u32 Ilen, const u8 b){ if(b == 0){ //Y <- opt_pad0*1(I) opt_pad_0s_1(Y, I, Ilen); //Y <- X XOR opt_pad0*1(I) for(u32 j=0; j is_auth = 1 is_auth = 1; } else { //if T' =/= T -> is_auth = 0 is_auth = 0; } free(Y); free(Z); free(M_temp); free(C); free(A); if(is_auth){ return 0; } else { return -1; } }