I386_ONLY is defined in opensslconf.h, so we need to include it.
[openssl.git] / crypto / sha / sha_locl.h
1 /* crypto/sha/sha_locl.h */
2 /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3  * All rights reserved.
4  *
5  * This package is an SSL implementation written
6  * by Eric Young (eay@cryptsoft.com).
7  * The implementation was written so as to conform with Netscapes SSL.
8  * 
9  * This library is free for commercial and non-commercial use as long as
10  * the following conditions are aheared to.  The following conditions
11  * apply to all code found in this distribution, be it the RC4, RSA,
12  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
13  * included with this distribution is covered by the same copyright terms
14  * except that the holder is Tim Hudson (tjh@cryptsoft.com).
15  * 
16  * Copyright remains Eric Young's, and as such any Copyright notices in
17  * the code are not to be removed.
18  * If this package is used in a product, Eric Young should be given attribution
19  * as the author of the parts of the library used.
20  * This can be in the form of a textual message at program startup or
21  * in documentation (online or textual) provided with the package.
22  * 
23  * Redistribution and use in source and binary forms, with or without
24  * modification, are permitted provided that the following conditions
25  * are met:
26  * 1. Redistributions of source code must retain the copyright
27  *    notice, this list of conditions and the following disclaimer.
28  * 2. Redistributions in binary form must reproduce the above copyright
29  *    notice, this list of conditions and the following disclaimer in the
30  *    documentation and/or other materials provided with the distribution.
31  * 3. All advertising materials mentioning features or use of this software
32  *    must display the following acknowledgement:
33  *    "This product includes cryptographic software written by
34  *     Eric Young (eay@cryptsoft.com)"
35  *    The word 'cryptographic' can be left out if the rouines from the library
36  *    being used are not cryptographic related :-).
37  * 4. If you include any Windows specific code (or a derivative thereof) from 
38  *    the apps directory (application code) you must include an acknowledgement:
39  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
40  * 
41  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
42  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
43  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
44  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
45  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
46  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
47  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
48  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
49  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
50  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
51  * SUCH DAMAGE.
52  * 
53  * The licence and distribution terms for any publically available version or
54  * derivative of this code cannot be changed.  i.e. this code cannot simply be
55  * copied and put under another distribution licence
56  * [including the GNU Public Licence.]
57  */
58
59 #include <stdlib.h>
60 #include <string.h>
61
62 #include <openssl/opensslconf.h>
63
64 #ifdef undef
65 /* one or the other needs to be defined */
66 #ifndef SHA_1 /* FIPE 180-1 */
67 #define SHA_0 /* FIPS 180   */
68 #endif
69 #endif
70
71 #undef c2nl
72 #define c2nl(c,l)       (l =(((unsigned long)(*((c)++)))<<24), \
73                          l|=(((unsigned long)(*((c)++)))<<16), \
74                          l|=(((unsigned long)(*((c)++)))<< 8), \
75                          l|=(((unsigned long)(*((c)++)))    ))
76
77 #undef p_c2nl
78 #define p_c2nl(c,l,n)   { \
79                         switch (n) { \
80                         case 0: l =((unsigned long)(*((c)++)))<<24; \
81                         case 1: l|=((unsigned long)(*((c)++)))<<16; \
82                         case 2: l|=((unsigned long)(*((c)++)))<< 8; \
83                         case 3: l|=((unsigned long)(*((c)++))); \
84                                 } \
85                         }
86
87 #undef c2nl_p
88 /* NOTE the pointer is not incremented at the end of this */
89 #define c2nl_p(c,l,n)   { \
90                         l=0; \
91                         (c)+=n; \
92                         switch (n) { \
93                         case 3: l =((unsigned long)(*(--(c))))<< 8; \
94                         case 2: l|=((unsigned long)(*(--(c))))<<16; \
95                         case 1: l|=((unsigned long)(*(--(c))))<<24; \
96                                 } \
97                         }
98
99 #undef p_c2nl_p
100 #define p_c2nl_p(c,l,sc,len) { \
101                         switch (sc) \
102                                 { \
103                         case 0: l =((unsigned long)(*((c)++)))<<24; \
104                                 if (--len == 0) break; \
105                         case 1: l|=((unsigned long)(*((c)++)))<<16; \
106                                 if (--len == 0) break; \
107                         case 2: l|=((unsigned long)(*((c)++)))<< 8; \
108                                 } \
109                         }
110
111 #undef nl2c
112 #define nl2c(l,c)       (*((c)++)=(unsigned char)(((l)>>24)&0xff), \
113                          *((c)++)=(unsigned char)(((l)>>16)&0xff), \
114                          *((c)++)=(unsigned char)(((l)>> 8)&0xff), \
115                          *((c)++)=(unsigned char)(((l)    )&0xff))
116
117 #undef c2l
118 #define c2l(c,l)        (l =(((unsigned long)(*((c)++)))    ), \
119                          l|=(((unsigned long)(*((c)++)))<< 8), \
120                          l|=(((unsigned long)(*((c)++)))<<16), \
121                          l|=(((unsigned long)(*((c)++)))<<24))
122
123 #undef p_c2l
124 #define p_c2l(c,l,n)    { \
125                         switch (n) { \
126                         case 0: l =((unsigned long)(*((c)++))); \
127                         case 1: l|=((unsigned long)(*((c)++)))<< 8; \
128                         case 2: l|=((unsigned long)(*((c)++)))<<16; \
129                         case 3: l|=((unsigned long)(*((c)++)))<<24; \
130                                 } \
131                         }
132
133 #undef c2l_p
134 /* NOTE the pointer is not incremented at the end of this */
135 #define c2l_p(c,l,n)    { \
136                         l=0; \
137                         (c)+=n; \
138                         switch (n) { \
139                         case 3: l =((unsigned long)(*(--(c))))<<16; \
140                         case 2: l|=((unsigned long)(*(--(c))))<< 8; \
141                         case 1: l|=((unsigned long)(*(--(c)))); \
142                                 } \
143                         }
144
145 #undef p_c2l_p
146 #define p_c2l_p(c,l,sc,len) { \
147                         switch (sc) \
148                                 { \
149                         case 0: l =((unsigned long)(*((c)++))); \
150                                 if (--len == 0) break; \
151                         case 1: l|=((unsigned long)(*((c)++)))<< 8; \
152                                 if (--len == 0) break; \
153                         case 2: l|=((unsigned long)(*((c)++)))<<16; \
154                                 } \
155                         }
156
157 #undef l2c
158 #define l2c(l,c)        (*((c)++)=(unsigned char)(((l)    )&0xff), \
159                          *((c)++)=(unsigned char)(((l)>> 8)&0xff), \
160                          *((c)++)=(unsigned char)(((l)>>16)&0xff), \
161                          *((c)++)=(unsigned char)(((l)>>24)&0xff))
162
163 #ifndef SHA_LONG_LOG2
164 #define SHA_LONG_LOG2   2       /* default to 32 bits */
165 #endif
166
167 #undef ROTATE
168 #undef Endian_Reverse32
169 #if defined(WIN32)
170 #define ROTATE(a,n)     _lrotl(a,n)
171 #elif defined(__GNUC__) && !defined(PEDANTIC)
172 /* some inline assembler templates by <appro@fy.chalmers.se> */
173 #if defined(__i386)
174 #define ROTATE(a,n)     ({ register unsigned int ret;   \
175                                 asm ("roll %1,%0"       \
176                                 : "=r"(ret)             \
177                                 : "I"(n), "0"(a)        \
178                                 : "cc");                \
179                            ret;                         \
180                         })
181 #ifndef I386_ONLY
182 #define Endian_Reverse32(a) \
183                         { register unsigned int ltmp=(a);       \
184                                 asm ("bswapl %0"        \
185                                 : "=r"(ltmp) : "0"(ltmp));      \
186                           (a)=ltmp;                     \
187                         }
188 #endif
189 #elif defined(__powerpc)
190 #define ROTATE(a,n)     ({ register unsigned int ret;           \
191                                 asm ("rlwinm %0,%1,%2,0,31"     \
192                                 : "=r"(ret)                     \
193                                 : "r"(a), "I"(n));              \
194                            ret;                                 \
195                         })
196 /* Endian_Reverse32 is not needed for PowerPC */
197 #endif
198 #endif
199
200 /* A nice byte order reversal from Wei Dai <weidai@eskimo.com> */
201 #ifdef ROTATE
202 #ifndef Endian_Reverse32
203 /* 5 instructions with rotate instruction, else 9 */
204 #define Endian_Reverse32(a) \
205         { \
206         unsigned long t=(a); \
207         (a)=((ROTATE(t,8)&0x00FF00FF)|(ROTATE((t&0x00FF00FF),24))); \
208         }
209 #endif
210 #else
211 #define ROTATE(a,n)     (((a)<<(n))|(((a)&0xffffffff)>>(32-(n))))
212 #ifndef Endian_Reverse32
213 /* 6 instructions with rotate instruction, else 8 */
214 #define Endian_Reverse32(a) \
215         { \
216         unsigned long t=(a); \
217         t=(((t>>8)&0x00FF00FF)|((t&0x00FF00FF)<<8)); \
218         (a)=ROTATE(t,16); \
219         }
220 #endif
221 /*
222  * Originally the middle line started with l=(((l&0xFF00FF00)>>8)|...
223  * It's rewritten as above for two reasons:
224  *      - RISCs aren't good at long constants and have to explicitely
225  *        compose 'em with several (well, usually 2) instructions in a
226  *        register before performing the actual operation and (as you
227  *        already realized:-) having same constant should inspire the
228  *        compiler to permanently allocate the only register for it;
229  *      - most modern CPUs have two ALUs, but usually only one has
230  *        circuitry for shifts:-( this minor tweak inspires compiler
231  *        to schedule shift instructions in a better way...
232  *
233  *                              <appro@fy.chalmers.se>
234  */
235 #endif
236
237 /* As  pointed out by Wei Dai <weidai@eskimo.com>, F() below can be
238  * simplified to the code in F_00_19.  Wei attributes these optimisations
239  * to Peter Gutmann's SHS code, and he attributes it to Rich Schroeppel.
240  * #define F(x,y,z) (((x) & (y))  |  ((~(x)) & (z)))
241  * I've just become aware of another tweak to be made, again from Wei Dai,
242  * in F_40_59, (x&a)|(y&a) -> (x|y)&a
243  */
244 #define F_00_19(b,c,d)  ((((c) ^ (d)) & (b)) ^ (d)) 
245 #define F_20_39(b,c,d)  ((b) ^ (c) ^ (d))
246 #define F_40_59(b,c,d)  (((b) & (c)) | (((b)|(c)) & (d))) 
247 #define F_60_79(b,c,d)  F_20_39(b,c,d)
248
249 #undef Xupdate
250 #ifdef SHA_0
251 #define Xupdate(a,i,ia,ib,ic,id) X[(i)&0x0f]=(a)=\
252         (ia[(i)&0x0f]^ib[((i)+2)&0x0f]^ic[((i)+8)&0x0f]^id[((i)+13)&0x0f]);
253 #endif
254 #ifdef SHA_1
255 #define Xupdate(a,i,ia,ib,ic,id) (a)=\
256         (ia[(i)&0x0f]^ib[((i)+2)&0x0f]^ic[((i)+8)&0x0f]^id[((i)+13)&0x0f]);\
257         X[(i)&0x0f]=(a)=ROTATE((a),1);
258 #endif
259
260 #define BODY_00_15(i,a,b,c,d,e,f,xa) \
261         (f)=xa[i]+(e)+K_00_19+ROTATE((a),5)+F_00_19((b),(c),(d)); \
262         (b)=ROTATE((b),30);
263
264 #define BODY_16_19(i,a,b,c,d,e,f,xa,xb,xc,xd) \
265         Xupdate(f,i,xa,xb,xc,xd); \
266         (f)+=(e)+K_00_19+ROTATE((a),5)+F_00_19((b),(c),(d)); \
267         (b)=ROTATE((b),30);
268
269 #define BODY_20_31(i,a,b,c,d,e,f,xa,xb,xc,xd) \
270         Xupdate(f,i,xa,xb,xc,xd); \
271         (f)+=(e)+K_20_39+ROTATE((a),5)+F_20_39((b),(c),(d)); \
272         (b)=ROTATE((b),30);
273
274 #define BODY_32_39(i,a,b,c,d,e,f,xa) \
275         Xupdate(f,i,xa,xa,xa,xa); \
276         (f)+=(e)+K_20_39+ROTATE((a),5)+F_20_39((b),(c),(d)); \
277         (b)=ROTATE((b),30);
278
279 #define BODY_40_59(i,a,b,c,d,e,f,xa) \
280         Xupdate(f,i,xa,xa,xa,xa); \
281         (f)+=(e)+K_40_59+ROTATE((a),5)+F_40_59((b),(c),(d)); \
282         (b)=ROTATE((b),30);
283
284 #define BODY_60_79(i,a,b,c,d,e,f,xa) \
285         Xupdate(f,i,xa,xa,xa,xa); \
286         (f)=X[(i)&0x0f]+(e)+K_60_79+ROTATE((a),5)+F_60_79((b),(c),(d)); \
287         (b)=ROTATE((b),30);
288