/* * Adapted from nacl-20110221/crypto_core/salsa20/ref/core.c: * * - Renamed ROUNDS -> crypto_core_ROUNDS. * - Added #include and used uint32_t rather than unsigned int. * - Rewrote body of core with QUARTERROUND. * - Replaced bytes by words; let caller align and order bytes. * - Merged xi += ji; out[i] = xi; into out[i] = ji + xi. */ /* version 20080912 D. J. Bernstein Public domain. */ #include typedef uint32_t uint32; #include "crypto_core.h" static uint32 rotate(uint32 u,int c) { return (u << c) | (u >> (32 - c)); } #define QUARTERROUND(v0,v1,v2,v3) do { \ (v1) ^= rotate((v0) + (v3), 7); \ (v2) ^= rotate((v1) + (v0), 9); \ (v3) ^= rotate((v2) + (v1),13); \ (v0) ^= rotate((v3) + (v2),18); \ } while (0) void crypto_core( uint32 *out, const uint32 *in, const uint32 *k, const uint32 *c ) { uint32 x0, x1, x2, x3, x4, x5, x6, x7, x8, x9, x10, x11, x12, x13, x14, x15; uint32 j0, j1, j2, j3, j4, j5, j6, j7, j8, j9, j10, j11, j12, j13, j14, j15; int i; j0 = x0 = c[0]; j1 = x1 = k[0]; j2 = x2 = k[1]; j3 = x3 = k[2]; j4 = x4 = k[3]; j5 = x5 = c[1]; j6 = x6 = in[0]; j7 = x7 = in[1]; j8 = x8 = in[2]; j9 = x9 = in[3]; j10 = x10 = c[2]; j11 = x11 = k[4]; j12 = x12 = k[5]; j13 = x13 = k[6]; j14 = x14 = k[7]; j15 = x15 = c[3]; for (i = crypto_core_ROUNDS;i > 0;i -= 2) { QUARTERROUND( x0, x4, x8,x12); QUARTERROUND( x5, x9,x13, x1); QUARTERROUND(x10,x14, x2, x6); QUARTERROUND(x15, x3, x7,x11); QUARTERROUND( x0, x1, x2, x3); QUARTERROUND( x5, x6, x7, x4); QUARTERROUND(x10,x11, x8, x9); QUARTERROUND(x15,x12,x13,x14); } out[0] = x0 + j0; out[1] = x1 + j1; out[2] = x2 + j2; out[3] = x3 + j3; out[4] = x4 + j4; out[5] = x5 + j5; out[6] = x6 + j6; out[7] = x7 + j7; out[8] = x8 + j8; out[9] = x9 + j9; out[10] = x10 + j10; out[11] = x11 + j11; out[12] = x12 + j12; out[13] = x13 + j13; out[14] = x14 + j14; out[15] = x15 + j15; }