Skip to content

Commit c496092

Browse files
committed
GR support
1 parent fc8ada6 commit c496092

File tree

1 file changed

+346
-0
lines changed

1 file changed

+346
-0
lines changed

xmrig/crypto/ghostrider/md_helper.c

Lines changed: 346 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,346 @@
1+
/* $Id: md_helper.c 216 2010-06-08 09:46:57Z tp $ */
2+
/*
3+
* This file contains some functions which implement the external data
4+
* handling and padding for Merkle-Damgard hash functions which follow
5+
* the conventions set out by MD4 (little-endian) or SHA-1 (big-endian).
6+
*
7+
* API: this file is meant to be included, not compiled as a stand-alone
8+
* file. Some macros must be defined:
9+
* RFUN name for the round function
10+
* HASH "short name" for the hash function
11+
* BE32 defined for big-endian, 32-bit based (e.g. SHA-1)
12+
* LE32 defined for little-endian, 32-bit based (e.g. MD5)
13+
* BE64 defined for big-endian, 64-bit based (e.g. SHA-512)
14+
* LE64 defined for little-endian, 64-bit based (no example yet)
15+
* PW01 if defined, append 0x01 instead of 0x80 (for Tiger)
16+
* BLEN if defined, length of a message block (in bytes)
17+
* PLW1 if defined, length is defined on one 64-bit word only (for Tiger)
18+
* PLW4 if defined, length is defined on four 64-bit words (for WHIRLPOOL)
19+
* SVAL if defined, reference to the context state information
20+
*
21+
* BLEN is used when a message block is not 16 (32-bit or 64-bit) words:
22+
* this is used for instance for Tiger, which works on 64-bit words but
23+
* uses 512-bit message blocks (eight 64-bit words). PLW1 and PLW4 are
24+
* ignored if 32-bit words are used; if 64-bit words are used and PLW1 is
25+
* set, then only one word (64 bits) will be used to encode the input
26+
* message length (in bits), otherwise two words will be used (as in
27+
* SHA-384 and SHA-512). If 64-bit words are used and PLW4 is defined (but
28+
* not PLW1), four 64-bit words will be used to encode the message length
29+
* (in bits). Note that regardless of those settings, only 64-bit message
30+
* lengths are supported (in bits): messages longer than 2 Exabytes will be
31+
* improperly hashed (this is unlikely to happen soon: 2 Exabytes is about
32+
* 2 millions Terabytes, which is huge).
33+
*
34+
* If CLOSE_ONLY is defined, then this file defines only the sph_XXX_close()
35+
* function. This is used for Tiger2, which is identical to Tiger except
36+
* when it comes to the padding (Tiger2 uses the standard 0x80 byte instead
37+
* of the 0x01 from original Tiger).
38+
*
39+
* The RFUN function is invoked with two arguments, the first pointing to
40+
* aligned data (as a "const void *"), the second being state information
41+
* from the context structure. By default, this state information is the
42+
* "val" field from the context, and this field is assumed to be an array
43+
* of words ("sph_u32" or "sph_u64", depending on BE32/LE32/BE64/LE64).
44+
* from the context structure. The "val" field can have any type, except
45+
* for the output encoding which assumes that it is an array of "sph_u32"
46+
* values. By defining NO_OUTPUT, this last step is deactivated; the
47+
* includer code is then responsible for writing out the hash result. When
48+
* NO_OUTPUT is defined, the third parameter to the "close()" function is
49+
* ignored.
50+
*
51+
* ==========================(LICENSE BEGIN)============================
52+
*
53+
* Copyright (c) 2007-2010 Projet RNRT SAPHIR
54+
*
55+
* Permission is hereby granted, free of charge, to any person obtaining
56+
* a copy of this software and associated documentation files (the
57+
* "Software"), to deal in the Software without restriction, including
58+
* without limitation the rights to use, copy, modify, merge, publish,
59+
* distribute, sublicense, and/or sell copies of the Software, and to
60+
* permit persons to whom the Software is furnished to do so, subject to
61+
* the following conditions:
62+
*
63+
* The above copyright notice and this permission notice shall be
64+
* included in all copies or substantial portions of the Software.
65+
*
66+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
67+
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
68+
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
69+
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
70+
* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
71+
* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
72+
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
73+
*
74+
* ===========================(LICENSE END)=============================
75+
*
76+
* @author Thomas Pornin <thomas.pornin@cryptolog.com>
77+
*/
78+
79+
#ifdef _MSC_VER
80+
#pragma warning (disable: 4146)
81+
#endif
82+
83+
#undef SPH_XCAT
84+
#define SPH_XCAT(a, b) SPH_XCAT_(a, b)
85+
#undef SPH_XCAT_
86+
#define SPH_XCAT_(a, b) a ## b
87+
88+
#undef SPH_BLEN
89+
#undef SPH_WLEN
90+
#if defined BE64 || defined LE64
91+
#define SPH_BLEN 128U
92+
#define SPH_WLEN 8U
93+
#else
94+
#define SPH_BLEN 64U
95+
#define SPH_WLEN 4U
96+
#endif
97+
98+
#ifdef BLEN
99+
#undef SPH_BLEN
100+
#define SPH_BLEN BLEN
101+
#endif
102+
103+
#undef SPH_MAXPAD
104+
#if defined PLW1
105+
#define SPH_MAXPAD (SPH_BLEN - SPH_WLEN)
106+
#elif defined PLW4
107+
#define SPH_MAXPAD (SPH_BLEN - (SPH_WLEN << 2))
108+
#else
109+
#define SPH_MAXPAD (SPH_BLEN - (SPH_WLEN << 1))
110+
#endif
111+
112+
#undef SPH_VAL
113+
#undef SPH_NO_OUTPUT
114+
#ifdef SVAL
115+
#define SPH_VAL SVAL
116+
#define SPH_NO_OUTPUT 1
117+
#else
118+
#define SPH_VAL sc->val
119+
#endif
120+
121+
#ifndef CLOSE_ONLY
122+
123+
#ifdef SPH_UPTR
124+
static void
125+
SPH_XCAT(HASH, _short)(void *cc, const void *data, size_t len)
126+
#else
127+
void
128+
SPH_XCAT(sph_, HASH)(void *cc, const void *data, size_t len)
129+
#endif
130+
{
131+
SPH_XCAT(sph_, SPH_XCAT(HASH, _context)) *sc;
132+
size_t current;
133+
134+
sc = cc;
135+
#if SPH_64
136+
current = (unsigned)sc->count & (SPH_BLEN - 1U);
137+
#else
138+
current = (unsigned)sc->count_low & (SPH_BLEN - 1U);
139+
#endif
140+
while (len > 0) {
141+
size_t clen;
142+
#if !SPH_64
143+
sph_u32 clow, clow2;
144+
#endif
145+
146+
clen = SPH_BLEN - current;
147+
if (clen > len)
148+
clen = len;
149+
memcpy(sc->buf + current, data, clen);
150+
data = (const unsigned char *)data + clen;
151+
current += clen;
152+
len -= clen;
153+
if (current == SPH_BLEN) {
154+
RFUN(sc->buf, SPH_VAL);
155+
current = 0;
156+
}
157+
#if SPH_64
158+
sc->count += clen;
159+
#else
160+
clow = sc->count_low;
161+
clow2 = SPH_T32(clow + clen);
162+
sc->count_low = clow2;
163+
if (clow2 < clow)
164+
sc->count_high ++;
165+
#endif
166+
}
167+
}
168+
169+
#ifdef SPH_UPTR
170+
void
171+
SPH_XCAT(sph_, HASH)(void *cc, const void *data, size_t len)
172+
{
173+
SPH_XCAT(sph_, SPH_XCAT(HASH, _context)) *sc;
174+
unsigned current;
175+
size_t orig_len;
176+
#if !SPH_64
177+
sph_u32 clow, clow2;
178+
#endif
179+
180+
if (len < (2 * SPH_BLEN)) {
181+
SPH_XCAT(HASH, _short)(cc, data, len);
182+
return;
183+
}
184+
sc = cc;
185+
#if SPH_64
186+
current = (unsigned)sc->count & (SPH_BLEN - 1U);
187+
#else
188+
current = (unsigned)sc->count_low & (SPH_BLEN - 1U);
189+
#endif
190+
if (current > 0) {
191+
unsigned t;
192+
193+
t = SPH_BLEN - current;
194+
SPH_XCAT(HASH, _short)(cc, data, t);
195+
data = (const unsigned char *)data + t;
196+
len -= t;
197+
}
198+
#if !SPH_UNALIGNED
199+
if (((SPH_UPTR)data & (SPH_WLEN - 1U)) != 0) {
200+
SPH_XCAT(HASH, _short)(cc, data, len);
201+
return;
202+
}
203+
#endif
204+
orig_len = len;
205+
while (len >= SPH_BLEN) {
206+
RFUN(data, SPH_VAL);
207+
len -= SPH_BLEN;
208+
data = (const unsigned char *)data + SPH_BLEN;
209+
}
210+
if (len > 0)
211+
memcpy(sc->buf, data, len);
212+
#if SPH_64
213+
sc->count += (sph_u64)orig_len;
214+
#else
215+
clow = sc->count_low;
216+
clow2 = SPH_T32(clow + orig_len);
217+
sc->count_low = clow2;
218+
if (clow2 < clow)
219+
sc->count_high ++;
220+
/*
221+
* This code handles the improbable situation where "size_t" is
222+
* greater than 32 bits, and yet we do not have a 64-bit type.
223+
*/
224+
orig_len >>= 12;
225+
orig_len >>= 10;
226+
orig_len >>= 10;
227+
sc->count_high += orig_len;
228+
#endif
229+
}
230+
#endif
231+
232+
#endif
233+
234+
/*
235+
* Perform padding and produce result. The context is NOT reinitialized
236+
* by this function.
237+
*/
238+
static void
239+
SPH_XCAT(HASH, _addbits_and_close)(void *cc,
240+
unsigned ub, unsigned n, void *dst, unsigned rnum)
241+
{
242+
SPH_XCAT(sph_, SPH_XCAT(HASH, _context)) *sc;
243+
unsigned current, u;
244+
#if !SPH_64
245+
sph_u32 low, high;
246+
#endif
247+
248+
sc = cc;
249+
#if SPH_64
250+
current = (unsigned)sc->count & (SPH_BLEN - 1U);
251+
#else
252+
current = (unsigned)sc->count_low & (SPH_BLEN - 1U);
253+
#endif
254+
#ifdef PW01
255+
sc->buf[current ++] = (0x100 | (ub & 0xFF)) >> (8 - n);
256+
#else
257+
{
258+
unsigned z;
259+
260+
z = 0x80 >> n;
261+
sc->buf[current ++] = ((ub & -z) | z) & 0xFF;
262+
}
263+
#endif
264+
if (current > SPH_MAXPAD) {
265+
memset(sc->buf + current, 0, SPH_BLEN - current);
266+
RFUN(sc->buf, SPH_VAL);
267+
memset(sc->buf, 0, SPH_MAXPAD);
268+
} else {
269+
memset(sc->buf + current, 0, SPH_MAXPAD - current);
270+
}
271+
#if defined BE64
272+
#if defined PLW1
273+
sph_enc64be_aligned(sc->buf + SPH_MAXPAD,
274+
SPH_T64(sc->count << 3) + (sph_u64)n);
275+
#elif defined PLW4
276+
memset(sc->buf + SPH_MAXPAD, 0, 2 * SPH_WLEN);
277+
sph_enc64be_aligned(sc->buf + SPH_MAXPAD + 2 * SPH_WLEN,
278+
sc->count >> 61);
279+
sph_enc64be_aligned(sc->buf + SPH_MAXPAD + 3 * SPH_WLEN,
280+
SPH_T64(sc->count << 3) + (sph_u64)n);
281+
#else
282+
sph_enc64be_aligned(sc->buf + SPH_MAXPAD, sc->count >> 61);
283+
sph_enc64be_aligned(sc->buf + SPH_MAXPAD + SPH_WLEN,
284+
SPH_T64(sc->count << 3) + (sph_u64)n);
285+
#endif
286+
#elif defined LE64
287+
#if defined PLW1
288+
sph_enc64le_aligned(sc->buf + SPH_MAXPAD,
289+
SPH_T64(sc->count << 3) + (sph_u64)n);
290+
#elif defined PLW1
291+
sph_enc64le_aligned(sc->buf + SPH_MAXPAD,
292+
SPH_T64(sc->count << 3) + (sph_u64)n);
293+
sph_enc64le_aligned(sc->buf + SPH_MAXPAD + SPH_WLEN, sc->count >> 61);
294+
memset(sc->buf + SPH_MAXPAD + 2 * SPH_WLEN, 0, 2 * SPH_WLEN);
295+
#else
296+
sph_enc64le_aligned(sc->buf + SPH_MAXPAD,
297+
SPH_T64(sc->count << 3) + (sph_u64)n);
298+
sph_enc64le_aligned(sc->buf + SPH_MAXPAD + SPH_WLEN, sc->count >> 61);
299+
#endif
300+
#else
301+
#if SPH_64
302+
#ifdef BE32
303+
sph_enc64be_aligned(sc->buf + SPH_MAXPAD,
304+
SPH_T64(sc->count << 3) + (sph_u64)n);
305+
#else
306+
sph_enc64le_aligned(sc->buf + SPH_MAXPAD,
307+
SPH_T64(sc->count << 3) + (sph_u64)n);
308+
#endif
309+
#else
310+
low = sc->count_low;
311+
high = SPH_T32((sc->count_high << 3) | (low >> 29));
312+
low = SPH_T32(low << 3) + (sph_u32)n;
313+
#ifdef BE32
314+
sph_enc32be(sc->buf + SPH_MAXPAD, high);
315+
sph_enc32be(sc->buf + SPH_MAXPAD + SPH_WLEN, low);
316+
#else
317+
sph_enc32le(sc->buf + SPH_MAXPAD, low);
318+
sph_enc32le(sc->buf + SPH_MAXPAD + SPH_WLEN, high);
319+
#endif
320+
#endif
321+
#endif
322+
RFUN(sc->buf, SPH_VAL);
323+
#ifdef SPH_NO_OUTPUT
324+
(void)dst;
325+
(void)rnum;
326+
(void)u;
327+
#else
328+
for (u = 0; u < rnum; u ++) {
329+
#if defined BE64
330+
sph_enc64be((unsigned char *)dst + 8 * u, sc->val[u]);
331+
#elif defined LE64
332+
sph_enc64le((unsigned char *)dst + 8 * u, sc->val[u]);
333+
#elif defined BE32
334+
sph_enc32be((unsigned char *)dst + 4 * u, sc->val[u]);
335+
#else
336+
sph_enc32le((unsigned char *)dst + 4 * u, sc->val[u]);
337+
#endif
338+
}
339+
#endif
340+
}
341+
342+
static void
343+
SPH_XCAT(HASH, _close)(void *cc, void *dst, unsigned rnum)
344+
{
345+
SPH_XCAT(HASH, _addbits_and_close)(cc, 0, 0, dst, rnum);
346+
}

0 commit comments

Comments
 (0)