Path: blob/master/sha3/sph_ripemd.c
1299 views
/* $Id: ripemd.c 216 2010-06-08 09:46:57Z tp $ */1/*2* RIPEMD-160 implementation.3*4* ==========================(LICENSE BEGIN)============================5*6* Copyright (c) 2007-2010 Projet RNRT SAPHIR7*8* Permission is hereby granted, free of charge, to any person obtaining9* a copy of this software and associated documentation files (the10* "Software"), to deal in the Software without restriction, including11* without limitation the rights to use, copy, modify, merge, publish,12* distribute, sublicense, and/or sell copies of the Software, and to13* permit persons to whom the Software is furnished to do so, subject to14* the following conditions:15*16* The above copyright notice and this permission notice shall be17* included in all copies or substantial portions of the Software.18*19* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,20* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF21* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.22* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY23* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,24* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE25* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.26*27* ===========================(LICENSE END)=============================28*29* @author Thomas Pornin <[email protected]>30*/3132#include <stddef.h>33#include <string.h>3435#include "sph_ripemd.h"3637/*38* Round functions for RIPEMD (original).39*/40#define F(x, y, z) ((((y) ^ (z)) & (x)) ^ (z))41#define G(x, y, z) (((x) & (y)) | (((x) | (y)) & (z)))42#define H(x, y, z) ((x) ^ (y) ^ (z))4344static const sph_u32 oIV[5] = {45SPH_C32(0x67452301), SPH_C32(0xEFCDAB89),46SPH_C32(0x98BADCFE), SPH_C32(0x10325476)47};4849/*50* Round functions for RIPEMD-128 and RIPEMD-160.51*/52#define F1(x, y, z) ((x) ^ (y) ^ (z))53#define F2(x, y, z) ((((y) ^ (z)) & (x)) ^ (z))54#define F3(x, y, z) (((x) | ~(y)) ^ (z))55#define F4(x, y, z) ((((x) ^ (y)) & (z)) ^ (y))56#define F5(x, y, z) ((x) ^ ((y) | ~(z)))5758static const sph_u32 IV[5] = {59SPH_C32(0x67452301), SPH_C32(0xEFCDAB89), SPH_C32(0x98BADCFE),60SPH_C32(0x10325476), SPH_C32(0xC3D2E1F0)61};6263#define ROTL SPH_ROTL326465/* ===================================================================== */66/*67* RIPEMD (original hash, deprecated).68*/6970#define FF1(A, B, C, D, X, s) do { \71sph_u32 tmp = SPH_T32((A) + F(B, C, D) + (X)); \72(A) = ROTL(tmp, (s)); \73} while (0)7475#define GG1(A, B, C, D, X, s) do { \76sph_u32 tmp = SPH_T32((A) + G(B, C, D) \77+ (X) + SPH_C32(0x5A827999)); \78(A) = ROTL(tmp, (s)); \79} while (0)8081#define HH1(A, B, C, D, X, s) do { \82sph_u32 tmp = SPH_T32((A) + H(B, C, D) \83+ (X) + SPH_C32(0x6ED9EBA1)); \84(A) = ROTL(tmp, (s)); \85} while (0)8687#define FF2(A, B, C, D, X, s) do { \88sph_u32 tmp = SPH_T32((A) + F(B, C, D) \89+ (X) + SPH_C32(0x50A28BE6)); \90(A) = ROTL(tmp, (s)); \91} while (0)9293#define GG2(A, B, C, D, X, s) do { \94sph_u32 tmp = SPH_T32((A) + G(B, C, D) + (X)); \95(A) = ROTL(tmp, (s)); \96} while (0)9798#define HH2(A, B, C, D, X, s) do { \99sph_u32 tmp = SPH_T32((A) + H(B, C, D) \100+ (X) + SPH_C32(0x5C4DD124)); \101(A) = ROTL(tmp, (s)); \102} while (0)103104#define RIPEMD_ROUND_BODY(in, h) do { \105sph_u32 A1, B1, C1, D1; \106sph_u32 A2, B2, C2, D2; \107sph_u32 tmp; \108\109A1 = A2 = (h)[0]; \110B1 = B2 = (h)[1]; \111C1 = C2 = (h)[2]; \112D1 = D2 = (h)[3]; \113\114FF1(A1, B1, C1, D1, in( 0), 11); \115FF1(D1, A1, B1, C1, in( 1), 14); \116FF1(C1, D1, A1, B1, in( 2), 15); \117FF1(B1, C1, D1, A1, in( 3), 12); \118FF1(A1, B1, C1, D1, in( 4), 5); \119FF1(D1, A1, B1, C1, in( 5), 8); \120FF1(C1, D1, A1, B1, in( 6), 7); \121FF1(B1, C1, D1, A1, in( 7), 9); \122FF1(A1, B1, C1, D1, in( 8), 11); \123FF1(D1, A1, B1, C1, in( 9), 13); \124FF1(C1, D1, A1, B1, in(10), 14); \125FF1(B1, C1, D1, A1, in(11), 15); \126FF1(A1, B1, C1, D1, in(12), 6); \127FF1(D1, A1, B1, C1, in(13), 7); \128FF1(C1, D1, A1, B1, in(14), 9); \129FF1(B1, C1, D1, A1, in(15), 8); \130\131GG1(A1, B1, C1, D1, in( 7), 7); \132GG1(D1, A1, B1, C1, in( 4), 6); \133GG1(C1, D1, A1, B1, in(13), 8); \134GG1(B1, C1, D1, A1, in( 1), 13); \135GG1(A1, B1, C1, D1, in(10), 11); \136GG1(D1, A1, B1, C1, in( 6), 9); \137GG1(C1, D1, A1, B1, in(15), 7); \138GG1(B1, C1, D1, A1, in( 3), 15); \139GG1(A1, B1, C1, D1, in(12), 7); \140GG1(D1, A1, B1, C1, in( 0), 12); \141GG1(C1, D1, A1, B1, in( 9), 15); \142GG1(B1, C1, D1, A1, in( 5), 9); \143GG1(A1, B1, C1, D1, in(14), 7); \144GG1(D1, A1, B1, C1, in( 2), 11); \145GG1(C1, D1, A1, B1, in(11), 13); \146GG1(B1, C1, D1, A1, in( 8), 12); \147\148HH1(A1, B1, C1, D1, in( 3), 11); \149HH1(D1, A1, B1, C1, in(10), 13); \150HH1(C1, D1, A1, B1, in( 2), 14); \151HH1(B1, C1, D1, A1, in( 4), 7); \152HH1(A1, B1, C1, D1, in( 9), 14); \153HH1(D1, A1, B1, C1, in(15), 9); \154HH1(C1, D1, A1, B1, in( 8), 13); \155HH1(B1, C1, D1, A1, in( 1), 15); \156HH1(A1, B1, C1, D1, in(14), 6); \157HH1(D1, A1, B1, C1, in( 7), 8); \158HH1(C1, D1, A1, B1, in( 0), 13); \159HH1(B1, C1, D1, A1, in( 6), 6); \160HH1(A1, B1, C1, D1, in(11), 12); \161HH1(D1, A1, B1, C1, in(13), 5); \162HH1(C1, D1, A1, B1, in( 5), 7); \163HH1(B1, C1, D1, A1, in(12), 5); \164\165FF2(A2, B2, C2, D2, in( 0), 11); \166FF2(D2, A2, B2, C2, in( 1), 14); \167FF2(C2, D2, A2, B2, in( 2), 15); \168FF2(B2, C2, D2, A2, in( 3), 12); \169FF2(A2, B2, C2, D2, in( 4), 5); \170FF2(D2, A2, B2, C2, in( 5), 8); \171FF2(C2, D2, A2, B2, in( 6), 7); \172FF2(B2, C2, D2, A2, in( 7), 9); \173FF2(A2, B2, C2, D2, in( 8), 11); \174FF2(D2, A2, B2, C2, in( 9), 13); \175FF2(C2, D2, A2, B2, in(10), 14); \176FF2(B2, C2, D2, A2, in(11), 15); \177FF2(A2, B2, C2, D2, in(12), 6); \178FF2(D2, A2, B2, C2, in(13), 7); \179FF2(C2, D2, A2, B2, in(14), 9); \180FF2(B2, C2, D2, A2, in(15), 8); \181\182GG2(A2, B2, C2, D2, in( 7), 7); \183GG2(D2, A2, B2, C2, in( 4), 6); \184GG2(C2, D2, A2, B2, in(13), 8); \185GG2(B2, C2, D2, A2, in( 1), 13); \186GG2(A2, B2, C2, D2, in(10), 11); \187GG2(D2, A2, B2, C2, in( 6), 9); \188GG2(C2, D2, A2, B2, in(15), 7); \189GG2(B2, C2, D2, A2, in( 3), 15); \190GG2(A2, B2, C2, D2, in(12), 7); \191GG2(D2, A2, B2, C2, in( 0), 12); \192GG2(C2, D2, A2, B2, in( 9), 15); \193GG2(B2, C2, D2, A2, in( 5), 9); \194GG2(A2, B2, C2, D2, in(14), 7); \195GG2(D2, A2, B2, C2, in( 2), 11); \196GG2(C2, D2, A2, B2, in(11), 13); \197GG2(B2, C2, D2, A2, in( 8), 12); \198\199HH2(A2, B2, C2, D2, in( 3), 11); \200HH2(D2, A2, B2, C2, in(10), 13); \201HH2(C2, D2, A2, B2, in( 2), 14); \202HH2(B2, C2, D2, A2, in( 4), 7); \203HH2(A2, B2, C2, D2, in( 9), 14); \204HH2(D2, A2, B2, C2, in(15), 9); \205HH2(C2, D2, A2, B2, in( 8), 13); \206HH2(B2, C2, D2, A2, in( 1), 15); \207HH2(A2, B2, C2, D2, in(14), 6); \208HH2(D2, A2, B2, C2, in( 7), 8); \209HH2(C2, D2, A2, B2, in( 0), 13); \210HH2(B2, C2, D2, A2, in( 6), 6); \211HH2(A2, B2, C2, D2, in(11), 12); \212HH2(D2, A2, B2, C2, in(13), 5); \213HH2(C2, D2, A2, B2, in( 5), 7); \214HH2(B2, C2, D2, A2, in(12), 5); \215\216tmp = SPH_T32((h)[1] + C1 + D2); \217(h)[1] = SPH_T32((h)[2] + D1 + A2); \218(h)[2] = SPH_T32((h)[3] + A1 + B2); \219(h)[3] = SPH_T32((h)[0] + B1 + C2); \220(h)[0] = tmp; \221} while (0)222223/*224* One round of RIPEMD. The data must be aligned for 32-bit access.225*/226static void227ripemd_round(const unsigned char *data, sph_u32 r[5])228{229#if SPH_LITTLE_FAST230231#define RIPEMD_IN(x) sph_dec32le_aligned(data + (4 * (x)))232233#else234235sph_u32 X_var[16];236int i;237238for (i = 0; i < 16; i ++)239X_var[i] = sph_dec32le_aligned(data + 4 * i);240#define RIPEMD_IN(x) X_var[x]241242#endif243RIPEMD_ROUND_BODY(RIPEMD_IN, r);244#undef RIPEMD_IN245}246247/* see sph_ripemd.h */248void249sph_ripemd_init(void *cc)250{251sph_ripemd_context *sc;252253sc = (sph_ripemd_context*)cc;254memcpy(sc->val, oIV, sizeof sc->val);255#if SPH_64256sc->count = 0;257#else258sc->count_high = sc->count_low = 0;259#endif260}261262#define RFUN ripemd_round263#define HASH ripemd264#define LE32 1265#include "md_helper.c"266#undef RFUN267#undef HASH268#undef LE32269270/* see sph_ripemd.h */271void272sph_ripemd_close(void *cc, void *dst)273{274ripemd_close(cc, dst, 4);275sph_ripemd_init(cc);276}277278/* see sph_ripemd.h */279void280sph_ripemd_comp(const sph_u32 msg[16], sph_u32 val[4])281{282#define RIPEMD_IN(x) msg[x]283RIPEMD_ROUND_BODY(RIPEMD_IN, val);284#undef RIPEMD_IN285}286287/* ===================================================================== */288/*289* RIPEMD-128.290*/291292/*293* Round constants for RIPEMD-128.294*/295#define sK11 SPH_C32(0x00000000)296#define sK12 SPH_C32(0x5A827999)297#define sK13 SPH_C32(0x6ED9EBA1)298#define sK14 SPH_C32(0x8F1BBCDC)299300#define sK21 SPH_C32(0x50A28BE6)301#define sK22 SPH_C32(0x5C4DD124)302#define sK23 SPH_C32(0x6D703EF3)303#define sK24 SPH_C32(0x00000000)304305#define sRR(a, b, c, d, f, s, r, k) do { \306a = ROTL(SPH_T32(a + f(b, c, d) + r + k), s); \307} while (0)308309#define sROUND1(a, b, c, d, f, s, r, k) \310sRR(a ## 1, b ## 1, c ## 1, d ## 1, f, s, r, sK1 ## k)311312#define sROUND2(a, b, c, d, f, s, r, k) \313sRR(a ## 2, b ## 2, c ## 2, d ## 2, f, s, r, sK2 ## k)314315/*316* This macro defines the body for a RIPEMD-128 compression function317* implementation. The "in" parameter should evaluate, when applied to a318* numerical input parameter from 0 to 15, to an expression which yields319* the corresponding input block. The "h" parameter should evaluate to320* an array or pointer expression designating the array of 4 words which321* contains the input and output of the compression function.322*/323324#define RIPEMD128_ROUND_BODY(in, h) do { \325sph_u32 A1, B1, C1, D1; \326sph_u32 A2, B2, C2, D2; \327sph_u32 tmp; \328\329A1 = A2 = (h)[0]; \330B1 = B2 = (h)[1]; \331C1 = C2 = (h)[2]; \332D1 = D2 = (h)[3]; \333\334sROUND1(A, B, C, D, F1, 11, in( 0), 1); \335sROUND1(D, A, B, C, F1, 14, in( 1), 1); \336sROUND1(C, D, A, B, F1, 15, in( 2), 1); \337sROUND1(B, C, D, A, F1, 12, in( 3), 1); \338sROUND1(A, B, C, D, F1, 5, in( 4), 1); \339sROUND1(D, A, B, C, F1, 8, in( 5), 1); \340sROUND1(C, D, A, B, F1, 7, in( 6), 1); \341sROUND1(B, C, D, A, F1, 9, in( 7), 1); \342sROUND1(A, B, C, D, F1, 11, in( 8), 1); \343sROUND1(D, A, B, C, F1, 13, in( 9), 1); \344sROUND1(C, D, A, B, F1, 14, in(10), 1); \345sROUND1(B, C, D, A, F1, 15, in(11), 1); \346sROUND1(A, B, C, D, F1, 6, in(12), 1); \347sROUND1(D, A, B, C, F1, 7, in(13), 1); \348sROUND1(C, D, A, B, F1, 9, in(14), 1); \349sROUND1(B, C, D, A, F1, 8, in(15), 1); \350\351sROUND1(A, B, C, D, F2, 7, in( 7), 2); \352sROUND1(D, A, B, C, F2, 6, in( 4), 2); \353sROUND1(C, D, A, B, F2, 8, in(13), 2); \354sROUND1(B, C, D, A, F2, 13, in( 1), 2); \355sROUND1(A, B, C, D, F2, 11, in(10), 2); \356sROUND1(D, A, B, C, F2, 9, in( 6), 2); \357sROUND1(C, D, A, B, F2, 7, in(15), 2); \358sROUND1(B, C, D, A, F2, 15, in( 3), 2); \359sROUND1(A, B, C, D, F2, 7, in(12), 2); \360sROUND1(D, A, B, C, F2, 12, in( 0), 2); \361sROUND1(C, D, A, B, F2, 15, in( 9), 2); \362sROUND1(B, C, D, A, F2, 9, in( 5), 2); \363sROUND1(A, B, C, D, F2, 11, in( 2), 2); \364sROUND1(D, A, B, C, F2, 7, in(14), 2); \365sROUND1(C, D, A, B, F2, 13, in(11), 2); \366sROUND1(B, C, D, A, F2, 12, in( 8), 2); \367\368sROUND1(A, B, C, D, F3, 11, in( 3), 3); \369sROUND1(D, A, B, C, F3, 13, in(10), 3); \370sROUND1(C, D, A, B, F3, 6, in(14), 3); \371sROUND1(B, C, D, A, F3, 7, in( 4), 3); \372sROUND1(A, B, C, D, F3, 14, in( 9), 3); \373sROUND1(D, A, B, C, F3, 9, in(15), 3); \374sROUND1(C, D, A, B, F3, 13, in( 8), 3); \375sROUND1(B, C, D, A, F3, 15, in( 1), 3); \376sROUND1(A, B, C, D, F3, 14, in( 2), 3); \377sROUND1(D, A, B, C, F3, 8, in( 7), 3); \378sROUND1(C, D, A, B, F3, 13, in( 0), 3); \379sROUND1(B, C, D, A, F3, 6, in( 6), 3); \380sROUND1(A, B, C, D, F3, 5, in(13), 3); \381sROUND1(D, A, B, C, F3, 12, in(11), 3); \382sROUND1(C, D, A, B, F3, 7, in( 5), 3); \383sROUND1(B, C, D, A, F3, 5, in(12), 3); \384\385sROUND1(A, B, C, D, F4, 11, in( 1), 4); \386sROUND1(D, A, B, C, F4, 12, in( 9), 4); \387sROUND1(C, D, A, B, F4, 14, in(11), 4); \388sROUND1(B, C, D, A, F4, 15, in(10), 4); \389sROUND1(A, B, C, D, F4, 14, in( 0), 4); \390sROUND1(D, A, B, C, F4, 15, in( 8), 4); \391sROUND1(C, D, A, B, F4, 9, in(12), 4); \392sROUND1(B, C, D, A, F4, 8, in( 4), 4); \393sROUND1(A, B, C, D, F4, 9, in(13), 4); \394sROUND1(D, A, B, C, F4, 14, in( 3), 4); \395sROUND1(C, D, A, B, F4, 5, in( 7), 4); \396sROUND1(B, C, D, A, F4, 6, in(15), 4); \397sROUND1(A, B, C, D, F4, 8, in(14), 4); \398sROUND1(D, A, B, C, F4, 6, in( 5), 4); \399sROUND1(C, D, A, B, F4, 5, in( 6), 4); \400sROUND1(B, C, D, A, F4, 12, in( 2), 4); \401\402sROUND2(A, B, C, D, F4, 8, in( 5), 1); \403sROUND2(D, A, B, C, F4, 9, in(14), 1); \404sROUND2(C, D, A, B, F4, 9, in( 7), 1); \405sROUND2(B, C, D, A, F4, 11, in( 0), 1); \406sROUND2(A, B, C, D, F4, 13, in( 9), 1); \407sROUND2(D, A, B, C, F4, 15, in( 2), 1); \408sROUND2(C, D, A, B, F4, 15, in(11), 1); \409sROUND2(B, C, D, A, F4, 5, in( 4), 1); \410sROUND2(A, B, C, D, F4, 7, in(13), 1); \411sROUND2(D, A, B, C, F4, 7, in( 6), 1); \412sROUND2(C, D, A, B, F4, 8, in(15), 1); \413sROUND2(B, C, D, A, F4, 11, in( 8), 1); \414sROUND2(A, B, C, D, F4, 14, in( 1), 1); \415sROUND2(D, A, B, C, F4, 14, in(10), 1); \416sROUND2(C, D, A, B, F4, 12, in( 3), 1); \417sROUND2(B, C, D, A, F4, 6, in(12), 1); \418\419sROUND2(A, B, C, D, F3, 9, in( 6), 2); \420sROUND2(D, A, B, C, F3, 13, in(11), 2); \421sROUND2(C, D, A, B, F3, 15, in( 3), 2); \422sROUND2(B, C, D, A, F3, 7, in( 7), 2); \423sROUND2(A, B, C, D, F3, 12, in( 0), 2); \424sROUND2(D, A, B, C, F3, 8, in(13), 2); \425sROUND2(C, D, A, B, F3, 9, in( 5), 2); \426sROUND2(B, C, D, A, F3, 11, in(10), 2); \427sROUND2(A, B, C, D, F3, 7, in(14), 2); \428sROUND2(D, A, B, C, F3, 7, in(15), 2); \429sROUND2(C, D, A, B, F3, 12, in( 8), 2); \430sROUND2(B, C, D, A, F3, 7, in(12), 2); \431sROUND2(A, B, C, D, F3, 6, in( 4), 2); \432sROUND2(D, A, B, C, F3, 15, in( 9), 2); \433sROUND2(C, D, A, B, F3, 13, in( 1), 2); \434sROUND2(B, C, D, A, F3, 11, in( 2), 2); \435\436sROUND2(A, B, C, D, F2, 9, in(15), 3); \437sROUND2(D, A, B, C, F2, 7, in( 5), 3); \438sROUND2(C, D, A, B, F2, 15, in( 1), 3); \439sROUND2(B, C, D, A, F2, 11, in( 3), 3); \440sROUND2(A, B, C, D, F2, 8, in( 7), 3); \441sROUND2(D, A, B, C, F2, 6, in(14), 3); \442sROUND2(C, D, A, B, F2, 6, in( 6), 3); \443sROUND2(B, C, D, A, F2, 14, in( 9), 3); \444sROUND2(A, B, C, D, F2, 12, in(11), 3); \445sROUND2(D, A, B, C, F2, 13, in( 8), 3); \446sROUND2(C, D, A, B, F2, 5, in(12), 3); \447sROUND2(B, C, D, A, F2, 14, in( 2), 3); \448sROUND2(A, B, C, D, F2, 13, in(10), 3); \449sROUND2(D, A, B, C, F2, 13, in( 0), 3); \450sROUND2(C, D, A, B, F2, 7, in( 4), 3); \451sROUND2(B, C, D, A, F2, 5, in(13), 3); \452\453sROUND2(A, B, C, D, F1, 15, in( 8), 4); \454sROUND2(D, A, B, C, F1, 5, in( 6), 4); \455sROUND2(C, D, A, B, F1, 8, in( 4), 4); \456sROUND2(B, C, D, A, F1, 11, in( 1), 4); \457sROUND2(A, B, C, D, F1, 14, in( 3), 4); \458sROUND2(D, A, B, C, F1, 14, in(11), 4); \459sROUND2(C, D, A, B, F1, 6, in(15), 4); \460sROUND2(B, C, D, A, F1, 14, in( 0), 4); \461sROUND2(A, B, C, D, F1, 6, in( 5), 4); \462sROUND2(D, A, B, C, F1, 9, in(12), 4); \463sROUND2(C, D, A, B, F1, 12, in( 2), 4); \464sROUND2(B, C, D, A, F1, 9, in(13), 4); \465sROUND2(A, B, C, D, F1, 12, in( 9), 4); \466sROUND2(D, A, B, C, F1, 5, in( 7), 4); \467sROUND2(C, D, A, B, F1, 15, in(10), 4); \468sROUND2(B, C, D, A, F1, 8, in(14), 4); \469\470tmp = SPH_T32((h)[1] + C1 + D2); \471(h)[1] = SPH_T32((h)[2] + D1 + A2); \472(h)[2] = SPH_T32((h)[3] + A1 + B2); \473(h)[3] = SPH_T32((h)[0] + B1 + C2); \474(h)[0] = tmp; \475} while (0)476477/*478* One round of RIPEMD-128. The data must be aligned for 32-bit access.479*/480static void481ripemd128_round(const unsigned char *data, sph_u32 r[5])482{483#if SPH_LITTLE_FAST484485#define RIPEMD128_IN(x) sph_dec32le_aligned(data + (4 * (x)))486487#else488489sph_u32 X_var[16];490int i;491492for (i = 0; i < 16; i ++)493X_var[i] = sph_dec32le_aligned(data + 4 * i);494#define RIPEMD128_IN(x) X_var[x]495496#endif497RIPEMD128_ROUND_BODY(RIPEMD128_IN, r);498#undef RIPEMD128_IN499}500501/* see sph_ripemd.h */502void503sph_ripemd128_init(void *cc)504{505sph_ripemd128_context *sc;506507sc = (sph_ripemd128_context*)cc;508memcpy(sc->val, IV, sizeof sc->val);509#if SPH_64510sc->count = 0;511#else512sc->count_high = sc->count_low = 0;513#endif514}515516#define RFUN ripemd128_round517#define HASH ripemd128518#define LE32 1519#include "md_helper.c"520#undef RFUN521#undef HASH522#undef LE32523524/* see sph_ripemd.h */525void526sph_ripemd128_close(void *cc, void *dst)527{528ripemd128_close(cc, dst, 4);529sph_ripemd128_init(cc);530}531532/* see sph_ripemd.h */533void534sph_ripemd128_comp(const sph_u32 msg[16], sph_u32 val[4])535{536#define RIPEMD128_IN(x) msg[x]537RIPEMD128_ROUND_BODY(RIPEMD128_IN, val);538#undef RIPEMD128_IN539}540541/* ===================================================================== */542/*543* RIPEMD-160.544*/545546/*547* Round constants for RIPEMD-160.548*/549#define K11 SPH_C32(0x00000000)550#define K12 SPH_C32(0x5A827999)551#define K13 SPH_C32(0x6ED9EBA1)552#define K14 SPH_C32(0x8F1BBCDC)553#define K15 SPH_C32(0xA953FD4E)554555#define K21 SPH_C32(0x50A28BE6)556#define K22 SPH_C32(0x5C4DD124)557#define K23 SPH_C32(0x6D703EF3)558#define K24 SPH_C32(0x7A6D76E9)559#define K25 SPH_C32(0x00000000)560561#define RR(a, b, c, d, e, f, s, r, k) do { \562a = SPH_T32(ROTL(SPH_T32(a + f(b, c, d) + r + k), s) + e); \563c = ROTL(c, 10); \564} while (0)565566#define ROUND1(a, b, c, d, e, f, s, r, k) \567RR(a ## 1, b ## 1, c ## 1, d ## 1, e ## 1, f, s, r, K1 ## k)568569#define ROUND2(a, b, c, d, e, f, s, r, k) \570RR(a ## 2, b ## 2, c ## 2, d ## 2, e ## 2, f, s, r, K2 ## k)571572/*573* This macro defines the body for a RIPEMD-160 compression function574* implementation. The "in" parameter should evaluate, when applied to a575* numerical input parameter from 0 to 15, to an expression which yields576* the corresponding input block. The "h" parameter should evaluate to577* an array or pointer expression designating the array of 5 words which578* contains the input and output of the compression function.579*/580581#define RIPEMD160_ROUND_BODY(in, h) do { \582sph_u32 A1, B1, C1, D1, E1; \583sph_u32 A2, B2, C2, D2, E2; \584sph_u32 tmp; \585\586A1 = A2 = (h)[0]; \587B1 = B2 = (h)[1]; \588C1 = C2 = (h)[2]; \589D1 = D2 = (h)[3]; \590E1 = E2 = (h)[4]; \591\592ROUND1(A, B, C, D, E, F1, 11, in( 0), 1); \593ROUND1(E, A, B, C, D, F1, 14, in( 1), 1); \594ROUND1(D, E, A, B, C, F1, 15, in( 2), 1); \595ROUND1(C, D, E, A, B, F1, 12, in( 3), 1); \596ROUND1(B, C, D, E, A, F1, 5, in( 4), 1); \597ROUND1(A, B, C, D, E, F1, 8, in( 5), 1); \598ROUND1(E, A, B, C, D, F1, 7, in( 6), 1); \599ROUND1(D, E, A, B, C, F1, 9, in( 7), 1); \600ROUND1(C, D, E, A, B, F1, 11, in( 8), 1); \601ROUND1(B, C, D, E, A, F1, 13, in( 9), 1); \602ROUND1(A, B, C, D, E, F1, 14, in(10), 1); \603ROUND1(E, A, B, C, D, F1, 15, in(11), 1); \604ROUND1(D, E, A, B, C, F1, 6, in(12), 1); \605ROUND1(C, D, E, A, B, F1, 7, in(13), 1); \606ROUND1(B, C, D, E, A, F1, 9, in(14), 1); \607ROUND1(A, B, C, D, E, F1, 8, in(15), 1); \608\609ROUND1(E, A, B, C, D, F2, 7, in( 7), 2); \610ROUND1(D, E, A, B, C, F2, 6, in( 4), 2); \611ROUND1(C, D, E, A, B, F2, 8, in(13), 2); \612ROUND1(B, C, D, E, A, F2, 13, in( 1), 2); \613ROUND1(A, B, C, D, E, F2, 11, in(10), 2); \614ROUND1(E, A, B, C, D, F2, 9, in( 6), 2); \615ROUND1(D, E, A, B, C, F2, 7, in(15), 2); \616ROUND1(C, D, E, A, B, F2, 15, in( 3), 2); \617ROUND1(B, C, D, E, A, F2, 7, in(12), 2); \618ROUND1(A, B, C, D, E, F2, 12, in( 0), 2); \619ROUND1(E, A, B, C, D, F2, 15, in( 9), 2); \620ROUND1(D, E, A, B, C, F2, 9, in( 5), 2); \621ROUND1(C, D, E, A, B, F2, 11, in( 2), 2); \622ROUND1(B, C, D, E, A, F2, 7, in(14), 2); \623ROUND1(A, B, C, D, E, F2, 13, in(11), 2); \624ROUND1(E, A, B, C, D, F2, 12, in( 8), 2); \625\626ROUND1(D, E, A, B, C, F3, 11, in( 3), 3); \627ROUND1(C, D, E, A, B, F3, 13, in(10), 3); \628ROUND1(B, C, D, E, A, F3, 6, in(14), 3); \629ROUND1(A, B, C, D, E, F3, 7, in( 4), 3); \630ROUND1(E, A, B, C, D, F3, 14, in( 9), 3); \631ROUND1(D, E, A, B, C, F3, 9, in(15), 3); \632ROUND1(C, D, E, A, B, F3, 13, in( 8), 3); \633ROUND1(B, C, D, E, A, F3, 15, in( 1), 3); \634ROUND1(A, B, C, D, E, F3, 14, in( 2), 3); \635ROUND1(E, A, B, C, D, F3, 8, in( 7), 3); \636ROUND1(D, E, A, B, C, F3, 13, in( 0), 3); \637ROUND1(C, D, E, A, B, F3, 6, in( 6), 3); \638ROUND1(B, C, D, E, A, F3, 5, in(13), 3); \639ROUND1(A, B, C, D, E, F3, 12, in(11), 3); \640ROUND1(E, A, B, C, D, F3, 7, in( 5), 3); \641ROUND1(D, E, A, B, C, F3, 5, in(12), 3); \642\643ROUND1(C, D, E, A, B, F4, 11, in( 1), 4); \644ROUND1(B, C, D, E, A, F4, 12, in( 9), 4); \645ROUND1(A, B, C, D, E, F4, 14, in(11), 4); \646ROUND1(E, A, B, C, D, F4, 15, in(10), 4); \647ROUND1(D, E, A, B, C, F4, 14, in( 0), 4); \648ROUND1(C, D, E, A, B, F4, 15, in( 8), 4); \649ROUND1(B, C, D, E, A, F4, 9, in(12), 4); \650ROUND1(A, B, C, D, E, F4, 8, in( 4), 4); \651ROUND1(E, A, B, C, D, F4, 9, in(13), 4); \652ROUND1(D, E, A, B, C, F4, 14, in( 3), 4); \653ROUND1(C, D, E, A, B, F4, 5, in( 7), 4); \654ROUND1(B, C, D, E, A, F4, 6, in(15), 4); \655ROUND1(A, B, C, D, E, F4, 8, in(14), 4); \656ROUND1(E, A, B, C, D, F4, 6, in( 5), 4); \657ROUND1(D, E, A, B, C, F4, 5, in( 6), 4); \658ROUND1(C, D, E, A, B, F4, 12, in( 2), 4); \659\660ROUND1(B, C, D, E, A, F5, 9, in( 4), 5); \661ROUND1(A, B, C, D, E, F5, 15, in( 0), 5); \662ROUND1(E, A, B, C, D, F5, 5, in( 5), 5); \663ROUND1(D, E, A, B, C, F5, 11, in( 9), 5); \664ROUND1(C, D, E, A, B, F5, 6, in( 7), 5); \665ROUND1(B, C, D, E, A, F5, 8, in(12), 5); \666ROUND1(A, B, C, D, E, F5, 13, in( 2), 5); \667ROUND1(E, A, B, C, D, F5, 12, in(10), 5); \668ROUND1(D, E, A, B, C, F5, 5, in(14), 5); \669ROUND1(C, D, E, A, B, F5, 12, in( 1), 5); \670ROUND1(B, C, D, E, A, F5, 13, in( 3), 5); \671ROUND1(A, B, C, D, E, F5, 14, in( 8), 5); \672ROUND1(E, A, B, C, D, F5, 11, in(11), 5); \673ROUND1(D, E, A, B, C, F5, 8, in( 6), 5); \674ROUND1(C, D, E, A, B, F5, 5, in(15), 5); \675ROUND1(B, C, D, E, A, F5, 6, in(13), 5); \676\677ROUND2(A, B, C, D, E, F5, 8, in( 5), 1); \678ROUND2(E, A, B, C, D, F5, 9, in(14), 1); \679ROUND2(D, E, A, B, C, F5, 9, in( 7), 1); \680ROUND2(C, D, E, A, B, F5, 11, in( 0), 1); \681ROUND2(B, C, D, E, A, F5, 13, in( 9), 1); \682ROUND2(A, B, C, D, E, F5, 15, in( 2), 1); \683ROUND2(E, A, B, C, D, F5, 15, in(11), 1); \684ROUND2(D, E, A, B, C, F5, 5, in( 4), 1); \685ROUND2(C, D, E, A, B, F5, 7, in(13), 1); \686ROUND2(B, C, D, E, A, F5, 7, in( 6), 1); \687ROUND2(A, B, C, D, E, F5, 8, in(15), 1); \688ROUND2(E, A, B, C, D, F5, 11, in( 8), 1); \689ROUND2(D, E, A, B, C, F5, 14, in( 1), 1); \690ROUND2(C, D, E, A, B, F5, 14, in(10), 1); \691ROUND2(B, C, D, E, A, F5, 12, in( 3), 1); \692ROUND2(A, B, C, D, E, F5, 6, in(12), 1); \693\694ROUND2(E, A, B, C, D, F4, 9, in( 6), 2); \695ROUND2(D, E, A, B, C, F4, 13, in(11), 2); \696ROUND2(C, D, E, A, B, F4, 15, in( 3), 2); \697ROUND2(B, C, D, E, A, F4, 7, in( 7), 2); \698ROUND2(A, B, C, D, E, F4, 12, in( 0), 2); \699ROUND2(E, A, B, C, D, F4, 8, in(13), 2); \700ROUND2(D, E, A, B, C, F4, 9, in( 5), 2); \701ROUND2(C, D, E, A, B, F4, 11, in(10), 2); \702ROUND2(B, C, D, E, A, F4, 7, in(14), 2); \703ROUND2(A, B, C, D, E, F4, 7, in(15), 2); \704ROUND2(E, A, B, C, D, F4, 12, in( 8), 2); \705ROUND2(D, E, A, B, C, F4, 7, in(12), 2); \706ROUND2(C, D, E, A, B, F4, 6, in( 4), 2); \707ROUND2(B, C, D, E, A, F4, 15, in( 9), 2); \708ROUND2(A, B, C, D, E, F4, 13, in( 1), 2); \709ROUND2(E, A, B, C, D, F4, 11, in( 2), 2); \710\711ROUND2(D, E, A, B, C, F3, 9, in(15), 3); \712ROUND2(C, D, E, A, B, F3, 7, in( 5), 3); \713ROUND2(B, C, D, E, A, F3, 15, in( 1), 3); \714ROUND2(A, B, C, D, E, F3, 11, in( 3), 3); \715ROUND2(E, A, B, C, D, F3, 8, in( 7), 3); \716ROUND2(D, E, A, B, C, F3, 6, in(14), 3); \717ROUND2(C, D, E, A, B, F3, 6, in( 6), 3); \718ROUND2(B, C, D, E, A, F3, 14, in( 9), 3); \719ROUND2(A, B, C, D, E, F3, 12, in(11), 3); \720ROUND2(E, A, B, C, D, F3, 13, in( 8), 3); \721ROUND2(D, E, A, B, C, F3, 5, in(12), 3); \722ROUND2(C, D, E, A, B, F3, 14, in( 2), 3); \723ROUND2(B, C, D, E, A, F3, 13, in(10), 3); \724ROUND2(A, B, C, D, E, F3, 13, in( 0), 3); \725ROUND2(E, A, B, C, D, F3, 7, in( 4), 3); \726ROUND2(D, E, A, B, C, F3, 5, in(13), 3); \727\728ROUND2(C, D, E, A, B, F2, 15, in( 8), 4); \729ROUND2(B, C, D, E, A, F2, 5, in( 6), 4); \730ROUND2(A, B, C, D, E, F2, 8, in( 4), 4); \731ROUND2(E, A, B, C, D, F2, 11, in( 1), 4); \732ROUND2(D, E, A, B, C, F2, 14, in( 3), 4); \733ROUND2(C, D, E, A, B, F2, 14, in(11), 4); \734ROUND2(B, C, D, E, A, F2, 6, in(15), 4); \735ROUND2(A, B, C, D, E, F2, 14, in( 0), 4); \736ROUND2(E, A, B, C, D, F2, 6, in( 5), 4); \737ROUND2(D, E, A, B, C, F2, 9, in(12), 4); \738ROUND2(C, D, E, A, B, F2, 12, in( 2), 4); \739ROUND2(B, C, D, E, A, F2, 9, in(13), 4); \740ROUND2(A, B, C, D, E, F2, 12, in( 9), 4); \741ROUND2(E, A, B, C, D, F2, 5, in( 7), 4); \742ROUND2(D, E, A, B, C, F2, 15, in(10), 4); \743ROUND2(C, D, E, A, B, F2, 8, in(14), 4); \744\745ROUND2(B, C, D, E, A, F1, 8, in(12), 5); \746ROUND2(A, B, C, D, E, F1, 5, in(15), 5); \747ROUND2(E, A, B, C, D, F1, 12, in(10), 5); \748ROUND2(D, E, A, B, C, F1, 9, in( 4), 5); \749ROUND2(C, D, E, A, B, F1, 12, in( 1), 5); \750ROUND2(B, C, D, E, A, F1, 5, in( 5), 5); \751ROUND2(A, B, C, D, E, F1, 14, in( 8), 5); \752ROUND2(E, A, B, C, D, F1, 6, in( 7), 5); \753ROUND2(D, E, A, B, C, F1, 8, in( 6), 5); \754ROUND2(C, D, E, A, B, F1, 13, in( 2), 5); \755ROUND2(B, C, D, E, A, F1, 6, in(13), 5); \756ROUND2(A, B, C, D, E, F1, 5, in(14), 5); \757ROUND2(E, A, B, C, D, F1, 15, in( 0), 5); \758ROUND2(D, E, A, B, C, F1, 13, in( 3), 5); \759ROUND2(C, D, E, A, B, F1, 11, in( 9), 5); \760ROUND2(B, C, D, E, A, F1, 11, in(11), 5); \761\762tmp = SPH_T32((h)[1] + C1 + D2); \763(h)[1] = SPH_T32((h)[2] + D1 + E2); \764(h)[2] = SPH_T32((h)[3] + E1 + A2); \765(h)[3] = SPH_T32((h)[4] + A1 + B2); \766(h)[4] = SPH_T32((h)[0] + B1 + C2); \767(h)[0] = tmp; \768} while (0)769770/*771* One round of RIPEMD-160. The data must be aligned for 32-bit access.772*/773static void774ripemd160_round(const unsigned char *data, sph_u32 r[5])775{776#if SPH_LITTLE_FAST777778#define RIPEMD160_IN(x) sph_dec32le_aligned(data + (4 * (x)))779780#else781782sph_u32 X_var[16];783int i;784785for (i = 0; i < 16; i ++)786X_var[i] = sph_dec32le_aligned(data + 4 * i);787#define RIPEMD160_IN(x) X_var[x]788789#endif790RIPEMD160_ROUND_BODY(RIPEMD160_IN, r);791#undef RIPEMD160_IN792}793794/* see sph_ripemd.h */795void796sph_ripemd160_init(void *cc)797{798sph_ripemd160_context *sc;799800sc = (sph_ripemd160_context*)cc;801memcpy(sc->val, IV, sizeof sc->val);802#if SPH_64803sc->count = 0;804#else805sc->count_high = sc->count_low = 0;806#endif807}808809#define RFUN ripemd160_round810#define HASH ripemd160811#define LE32 1812#include "md_helper.c"813#undef RFUN814#undef HASH815#undef LE32816817/* see sph_ripemd.h */818void819sph_ripemd160_close(void *cc, void *dst)820{821ripemd160_close(cc, dst, 5);822sph_ripemd160_init(cc);823}824825/* see sph_ripemd.h */826void827sph_ripemd160_comp(const sph_u32 msg[16], sph_u32 val[5])828{829#define RIPEMD160_IN(x) msg[x]830RIPEMD160_ROUND_BODY(RIPEMD160_IN, val);831#undef RIPEMD160_IN832}833834835836