Initialize Keccak before use
This commit is contained in:
@@ -18,6 +18,7 @@ http://creativecommons.org/publicdomain/zero/1.0/
|
||||
#define KeccakPermutationSize 1600
|
||||
#define KeccakPermutationSizeInBytes (KeccakPermutationSize/8)
|
||||
|
||||
void KeccakInitialize(void);
|
||||
void KeccakInitializeState(unsigned char *state);
|
||||
void KeccakPermutation(unsigned char *state);
|
||||
void KeccakAbsorb(unsigned char *state, const unsigned char *data, unsigned int laneCount);
|
||||
|
||||
@@ -20,18 +20,21 @@ typedef unsigned char UINT8;
|
||||
typedef unsigned long long int UINT64;
|
||||
|
||||
#define nrRounds 24
|
||||
UINT64 KeccakRoundConstants[nrRounds];
|
||||
static UINT64 KeccakRoundConstants[nrRounds];
|
||||
#define nrLanes 25
|
||||
unsigned int KeccakRhoOffsets[nrLanes];
|
||||
static unsigned int KeccakRhoOffsets[nrLanes];
|
||||
|
||||
/*
|
||||
void KeccakPermutationOnWords(UINT64 *state);
|
||||
void theta(UINT64 *A);
|
||||
void rho(UINT64 *A);
|
||||
void pi(UINT64 *A);
|
||||
void chi(UINT64 *A);
|
||||
void iota(UINT64 *A, unsigned int indexRound);
|
||||
*/
|
||||
|
||||
void fromBytesToWords(UINT64 *stateAsWords, const unsigned char *state)
|
||||
#if (PLATFORM_BYTE_ORDER != IS_LITTLE_ENDIAN)
|
||||
static void fromBytesToWords(UINT64 *stateAsWords, const unsigned char *state)
|
||||
{
|
||||
unsigned int i, j;
|
||||
|
||||
@@ -42,7 +45,7 @@ void fromBytesToWords(UINT64 *stateAsWords, const unsigned char *state)
|
||||
}
|
||||
}
|
||||
|
||||
void fromWordsToBytes(unsigned char *state, const UINT64 *stateAsWords)
|
||||
static void fromWordsToBytes(unsigned char *state, const UINT64 *stateAsWords)
|
||||
{
|
||||
unsigned int i, j;
|
||||
|
||||
@@ -50,6 +53,97 @@ void fromWordsToBytes(unsigned char *state, const UINT64 *stateAsWords)
|
||||
for(j=0; j<(64/8); j++)
|
||||
state[i*(64/8)+j] = (stateAsWords[i] >> (8*j)) & 0xFF;
|
||||
}
|
||||
#endif
|
||||
|
||||
void KeccakPermutationAfterXor(unsigned char *state, const unsigned char *data, unsigned int dataLengthInBytes)
|
||||
{
|
||||
unsigned int i;
|
||||
|
||||
for(i=0; i<dataLengthInBytes; i++)
|
||||
state[i] ^= data[i];
|
||||
KeccakPermutation(state);
|
||||
}
|
||||
|
||||
#define index(x, y) (((x)%5)+5*((y)%5))
|
||||
#define ROL64(a, offset) ((offset != 0) ? ((((UINT64)a) << offset) ^ (((UINT64)a) >> (64-offset))) : a)
|
||||
|
||||
static void theta(UINT64 *A)
|
||||
{
|
||||
unsigned int x, y;
|
||||
UINT64 C[5], D[5];
|
||||
|
||||
for(x=0; x<5; x++) {
|
||||
C[x] = 0;
|
||||
for(y=0; y<5; y++)
|
||||
C[x] ^= A[index(x, y)];
|
||||
}
|
||||
for(x=0; x<5; x++)
|
||||
D[x] = ROL64(C[(x+1)%5], 1) ^ C[(x+4)%5];
|
||||
for(x=0; x<5; x++)
|
||||
for(y=0; y<5; y++)
|
||||
A[index(x, y)] ^= D[x];
|
||||
}
|
||||
|
||||
static void rho(UINT64 *A)
|
||||
{
|
||||
unsigned int x, y;
|
||||
|
||||
for(x=0; x<5; x++) for(y=0; y<5; y++)
|
||||
A[index(x, y)] = ROL64(A[index(x, y)], KeccakRhoOffsets[index(x, y)]);
|
||||
}
|
||||
|
||||
static void pi(UINT64 *A)
|
||||
{
|
||||
unsigned int x, y;
|
||||
UINT64 tempA[25];
|
||||
|
||||
for(x=0; x<5; x++) for(y=0; y<5; y++)
|
||||
tempA[index(x, y)] = A[index(x, y)];
|
||||
for(x=0; x<5; x++) for(y=0; y<5; y++)
|
||||
A[index(0*x+1*y, 2*x+3*y)] = tempA[index(x, y)];
|
||||
}
|
||||
|
||||
static void chi(UINT64 *A)
|
||||
{
|
||||
unsigned int x, y;
|
||||
UINT64 C[5];
|
||||
|
||||
for(y=0; y<5; y++) {
|
||||
for(x=0; x<5; x++)
|
||||
C[x] = A[index(x, y)] ^ ((~A[index(x+1, y)]) & A[index(x+2, y)]);
|
||||
for(x=0; x<5; x++)
|
||||
A[index(x, y)] = C[x];
|
||||
}
|
||||
}
|
||||
|
||||
static void iota(UINT64 *A, unsigned int indexRound)
|
||||
{
|
||||
A[index(0, 0)] ^= KeccakRoundConstants[indexRound];
|
||||
}
|
||||
|
||||
static int LFSR86540(UINT8 *LFSR)
|
||||
{
|
||||
int result = ((*LFSR) & 0x01) != 0;
|
||||
if (((*LFSR) & 0x80) != 0)
|
||||
// Primitive polynomial over GF(2): x^8+x^6+x^5+x^4+1
|
||||
(*LFSR) = ((*LFSR) << 1) ^ 0x71;
|
||||
else
|
||||
(*LFSR) <<= 1;
|
||||
return result;
|
||||
}
|
||||
|
||||
void KeccakPermutationOnWords(UINT64 *state)
|
||||
{
|
||||
unsigned int i;
|
||||
|
||||
for(i=0; i<nrRounds; i++) {
|
||||
theta(state);
|
||||
rho(state);
|
||||
pi(state);
|
||||
chi(state);
|
||||
iota(state, i);
|
||||
}
|
||||
}
|
||||
|
||||
void KeccakPermutation(unsigned char *state)
|
||||
{
|
||||
@@ -66,97 +160,7 @@ void KeccakPermutation(unsigned char *state)
|
||||
#endif
|
||||
}
|
||||
|
||||
void KeccakPermutationAfterXor(unsigned char *state, const unsigned char *data, unsigned int dataLengthInBytes)
|
||||
{
|
||||
unsigned int i;
|
||||
|
||||
for(i=0; i<dataLengthInBytes; i++)
|
||||
state[i] ^= data[i];
|
||||
KeccakPermutation(state);
|
||||
}
|
||||
|
||||
void KeccakPermutationOnWords(UINT64 *state)
|
||||
{
|
||||
unsigned int i;
|
||||
|
||||
for(i=0; i<nrRounds; i++) {
|
||||
theta(state);
|
||||
rho(state);
|
||||
pi(state);
|
||||
chi(state);
|
||||
iota(state, i);
|
||||
}
|
||||
}
|
||||
|
||||
#define index(x, y) (((x)%5)+5*((y)%5))
|
||||
#define ROL64(a, offset) ((offset != 0) ? ((((UINT64)a) << offset) ^ (((UINT64)a) >> (64-offset))) : a)
|
||||
|
||||
void theta(UINT64 *A)
|
||||
{
|
||||
unsigned int x, y;
|
||||
UINT64 C[5], D[5];
|
||||
|
||||
for(x=0; x<5; x++) {
|
||||
C[x] = 0;
|
||||
for(y=0; y<5; y++)
|
||||
C[x] ^= A[index(x, y)];
|
||||
}
|
||||
for(x=0; x<5; x++)
|
||||
D[x] = ROL64(C[(x+1)%5], 1) ^ C[(x+4)%5];
|
||||
for(x=0; x<5; x++)
|
||||
for(y=0; y<5; y++)
|
||||
A[index(x, y)] ^= D[x];
|
||||
}
|
||||
|
||||
void rho(UINT64 *A)
|
||||
{
|
||||
unsigned int x, y;
|
||||
|
||||
for(x=0; x<5; x++) for(y=0; y<5; y++)
|
||||
A[index(x, y)] = ROL64(A[index(x, y)], KeccakRhoOffsets[index(x, y)]);
|
||||
}
|
||||
|
||||
void pi(UINT64 *A)
|
||||
{
|
||||
unsigned int x, y;
|
||||
UINT64 tempA[25];
|
||||
|
||||
for(x=0; x<5; x++) for(y=0; y<5; y++)
|
||||
tempA[index(x, y)] = A[index(x, y)];
|
||||
for(x=0; x<5; x++) for(y=0; y<5; y++)
|
||||
A[index(0*x+1*y, 2*x+3*y)] = tempA[index(x, y)];
|
||||
}
|
||||
|
||||
void chi(UINT64 *A)
|
||||
{
|
||||
unsigned int x, y;
|
||||
UINT64 C[5];
|
||||
|
||||
for(y=0; y<5; y++) {
|
||||
for(x=0; x<5; x++)
|
||||
C[x] = A[index(x, y)] ^ ((~A[index(x+1, y)]) & A[index(x+2, y)]);
|
||||
for(x=0; x<5; x++)
|
||||
A[index(x, y)] = C[x];
|
||||
}
|
||||
}
|
||||
|
||||
void iota(UINT64 *A, unsigned int indexRound)
|
||||
{
|
||||
A[index(0, 0)] ^= KeccakRoundConstants[indexRound];
|
||||
}
|
||||
|
||||
int LFSR86540(UINT8 *LFSR)
|
||||
{
|
||||
int result = ((*LFSR) & 0x01) != 0;
|
||||
if (((*LFSR) & 0x80) != 0)
|
||||
// Primitive polynomial over GF(2): x^8+x^6+x^5+x^4+1
|
||||
(*LFSR) = ((*LFSR) << 1) ^ 0x71;
|
||||
else
|
||||
(*LFSR) <<= 1;
|
||||
return result;
|
||||
}
|
||||
|
||||
void KeccakInitializeRoundConstants()
|
||||
static void KeccakInitializeRoundConstants()
|
||||
{
|
||||
UINT8 LFSRstate = 0x01;
|
||||
unsigned int i, j, bitPosition;
|
||||
@@ -171,7 +175,7 @@ void KeccakInitializeRoundConstants()
|
||||
}
|
||||
}
|
||||
|
||||
void KeccakInitializeRhoOffsets()
|
||||
static void KeccakInitializeRhoOffsets()
|
||||
{
|
||||
unsigned int x, y, t, newX, newY;
|
||||
|
||||
@@ -187,7 +191,7 @@ void KeccakInitializeRhoOffsets()
|
||||
}
|
||||
}
|
||||
|
||||
void KeccakInitialize()
|
||||
void KeccakInitialize(void)
|
||||
{
|
||||
KeccakInitializeRoundConstants();
|
||||
KeccakInitializeRhoOffsets();
|
||||
|
||||
Reference in New Issue
Block a user