Main Page   Modules   Data Structures   File List   Data Fields   Globals   Related Pages  

beecrypt/sha256.c

Go to the documentation of this file.
00001 
00007 /*
00008  * Copyright (c) 2000, 2001 Virtual Unlimited B.V.
00009  *
00010  * Author: Bob Deblier <bob@virtualunlimited.com>
00011  *
00012  * This library is free software; you can redistribute it and/or
00013  * modify it under the terms of the GNU Lesser General Public
00014  * License as published by the Free Software Foundation; either
00015  * version 2.1 of the License, or (at your option) any later version.
00016  *
00017  * This library is distributed in the hope that it will be useful,
00018  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00019  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00020  * Lesser General Public License for more details.
00021  *
00022  * You should have received a copy of the GNU Lesser General Public
00023  * License along with this library; if not, write to the Free Software
00024  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00025  *
00026  */
00027  
00028 #include "system.h"
00029 #include "sha256.h"
00030 #include "mp32.h"
00031 #include "endianness.h"
00032 #include "debug.h"
00033 
00036 /*@observer@*/ /*@unchecked@*/
00037 static const uint32 k[64] = {
00038         0x428a2f98, 0x71374491, 0xb5c0fbcf, 0xe9b5dba5, 0x3956c25b, 0x59f111f1, 0x923f82a4, 0xab1c5ed5,
00039         0xd807aa98, 0x12835b01, 0x243185be, 0x550c7dc3, 0x72be5d74, 0x80deb1fe, 0x9bdc06a7, 0xc19bf174,
00040         0xe49b69c1, 0xefbe4786, 0x0fc19dc6, 0x240ca1cc, 0x2de92c6f, 0x4a7484aa, 0x5cb0a9dc, 0x76f988da,
00041         0x983e5152, 0xa831c66d, 0xb00327c8, 0xbf597fc7, 0xc6e00bf3, 0xd5a79147, 0x06ca6351, 0x14292967,
00042         0x27b70a85, 0x2e1b2138, 0x4d2c6dfc, 0x53380d13, 0x650a7354, 0x766a0abb, 0x81c2c92e, 0x92722c85,
00043         0xa2bfe8a1, 0xa81a664b, 0xc24b8b70, 0xc76c51a3, 0xd192e819, 0xd6990624, 0xf40e3585, 0x106aa070,
00044         0x19a4c116, 0x1e376c08, 0x2748774c, 0x34b0bcb5, 0x391c0cb3, 0x4ed8aa4a, 0x5b9cca4f, 0x682e6ff3,
00045         0x748f82ee, 0x78a5636f, 0x84c87814, 0x8cc70208, 0x90befffa, 0xa4506ceb, 0xbef9a3f7, 0xc67178f2
00046 };
00047 
00050 /*@observer@*/ /*@unchecked@*/
00051 static const uint32 hinit[8] = {
00052         0x6a09e667, 0xbb67ae85, 0x3c6ef372, 0xa54ff53a, 0x510e527f, 0x9b05688c, 0x1f83d9ab, 0x5be0cd19
00053 };
00054 
00055 /*@-sizeoftype@*/
00056 const hashFunction sha256 = { "SHA-256", sizeof(sha256Param), 64, 8 * sizeof(uint32), (hashFunctionReset) sha256Reset, (hashFunctionUpdate) sha256Update, (hashFunctionDigest) sha256Digest };
00057 /*@=sizeoftype@*/
00058 
00059 /*@-boundswrite@*/
00060 int sha256Reset(register sha256Param *p)
00061 {
00062         mp32copy(8, p->h, hinit);
00063         mp32zero(64, p->data);
00064         p->length = 0;
00065         p->offset = 0;
00066         return 0;
00067 }
00068 /*@=boundswrite@*/
00069 
00070 #define R(x,s)  ((x) >> (s))
00071 #define S(x,s) ROTR32(x, s)
00072 
00073 #define CH(x,y,z) ((x&(y^z))^z)
00074 #define MAJ(x,y,z) (((x|y)&z)|(x&y))
00075 #define SIG0(x) (S(x,2) ^ S(x,13) ^ S(x,22))
00076 #define SIG1(x) (S(x,6) ^ S(x,11) ^ S(x,25))
00077 #define sig0(x) (S(x,7) ^ S(x,18) ^ R(x,3))
00078 #define sig1(x) (S(x,17) ^ S(x,19) ^ R(x,10))
00079 
00080 #define ROUND(a,b,c,d,e,f,g,h,w,k)      \
00081         temp = h + SIG1(e) + CH(e,f,g) + k + w; \
00082         h = temp + SIG0(a) + MAJ(a,b,c);        \
00083         d += temp
00084 
00085 #ifndef ASM_SHA256PROCESS
00086 /*@-boundsread@*/
00087 void sha256Process(register sha256Param *p)
00088 {
00089         register uint32 a, b, c, d, e, f, g, h, temp;
00090         register uint32 *w;
00091         register byte t;
00092         
00093         #if WORDS_BIGENDIAN
00094         w = p->data + 16;
00095         #else
00096         w = p->data;
00097         t = 16;
00098         while (t--)
00099         {
00100                 register uint32 ttemp = swapu32(*w);
00101                 *(w++) = ttemp;
00102         }
00103         #endif
00104 
00105         t = 48;
00106         while (t--)
00107         {
00108                 register uint32 ttemp = sig1(w[-2]) + w[-7] + sig0(w[-15]) + w[-16];
00109                 *(w++) = ttemp;
00110         }
00111 
00112         w = p->data;
00113 
00114         a = p->h[0]; b = p->h[1]; c = p->h[2]; d = p->h[3];
00115         e = p->h[4]; f = p->h[5]; g = p->h[6]; h = p->h[7];
00116 
00117         ROUND(a,b,c,d,e,f,g,h,w[ 0],k[ 0]);
00118         ROUND(h,a,b,c,d,e,f,g,w[ 1],k[ 1]);
00119         ROUND(g,h,a,b,c,d,e,f,w[ 2],k[ 2]);
00120         ROUND(f,g,h,a,b,c,d,e,w[ 3],k[ 3]);
00121         ROUND(e,f,g,h,a,b,c,d,w[ 4],k[ 4]);
00122         ROUND(d,e,f,g,h,a,b,c,w[ 5],k[ 5]);
00123         ROUND(c,d,e,f,g,h,a,b,w[ 6],k[ 6]);
00124         ROUND(b,c,d,e,f,g,h,a,w[ 7],k[ 7]);
00125         ROUND(a,b,c,d,e,f,g,h,w[ 8],k[ 8]);
00126         ROUND(h,a,b,c,d,e,f,g,w[ 9],k[ 9]);
00127         ROUND(g,h,a,b,c,d,e,f,w[10],k[10]);
00128         ROUND(f,g,h,a,b,c,d,e,w[11],k[11]);
00129         ROUND(e,f,g,h,a,b,c,d,w[12],k[12]);
00130         ROUND(d,e,f,g,h,a,b,c,w[13],k[13]);
00131         ROUND(c,d,e,f,g,h,a,b,w[14],k[14]);
00132         ROUND(b,c,d,e,f,g,h,a,w[15],k[15]);
00133         ROUND(a,b,c,d,e,f,g,h,w[16],k[16]);
00134         ROUND(h,a,b,c,d,e,f,g,w[17],k[17]);
00135         ROUND(g,h,a,b,c,d,e,f,w[18],k[18]);
00136         ROUND(f,g,h,a,b,c,d,e,w[19],k[19]);
00137         ROUND(e,f,g,h,a,b,c,d,w[20],k[20]);
00138         ROUND(d,e,f,g,h,a,b,c,w[21],k[21]);
00139         ROUND(c,d,e,f,g,h,a,b,w[22],k[22]);
00140         ROUND(b,c,d,e,f,g,h,a,w[23],k[23]);
00141         ROUND(a,b,c,d,e,f,g,h,w[24],k[24]);
00142         ROUND(h,a,b,c,d,e,f,g,w[25],k[25]);
00143         ROUND(g,h,a,b,c,d,e,f,w[26],k[26]);
00144         ROUND(f,g,h,a,b,c,d,e,w[27],k[27]);
00145         ROUND(e,f,g,h,a,b,c,d,w[28],k[28]);
00146         ROUND(d,e,f,g,h,a,b,c,w[29],k[29]);
00147         ROUND(c,d,e,f,g,h,a,b,w[30],k[30]);
00148         ROUND(b,c,d,e,f,g,h,a,w[31],k[31]);
00149         ROUND(a,b,c,d,e,f,g,h,w[32],k[32]);
00150         ROUND(h,a,b,c,d,e,f,g,w[33],k[33]);
00151         ROUND(g,h,a,b,c,d,e,f,w[34],k[34]);
00152         ROUND(f,g,h,a,b,c,d,e,w[35],k[35]);
00153         ROUND(e,f,g,h,a,b,c,d,w[36],k[36]);
00154         ROUND(d,e,f,g,h,a,b,c,w[37],k[37]);
00155         ROUND(c,d,e,f,g,h,a,b,w[38],k[38]);
00156         ROUND(b,c,d,e,f,g,h,a,w[39],k[39]);
00157         ROUND(a,b,c,d,e,f,g,h,w[40],k[40]);
00158         ROUND(h,a,b,c,d,e,f,g,w[41],k[41]);
00159         ROUND(g,h,a,b,c,d,e,f,w[42],k[42]);
00160         ROUND(f,g,h,a,b,c,d,e,w[43],k[43]);
00161         ROUND(e,f,g,h,a,b,c,d,w[44],k[44]);
00162         ROUND(d,e,f,g,h,a,b,c,w[45],k[45]);
00163         ROUND(c,d,e,f,g,h,a,b,w[46],k[46]);
00164         ROUND(b,c,d,e,f,g,h,a,w[47],k[47]);
00165         ROUND(a,b,c,d,e,f,g,h,w[48],k[48]);
00166         ROUND(h,a,b,c,d,e,f,g,w[49],k[49]);
00167         ROUND(g,h,a,b,c,d,e,f,w[50],k[50]);
00168         ROUND(f,g,h,a,b,c,d,e,w[51],k[51]);
00169         ROUND(e,f,g,h,a,b,c,d,w[52],k[52]);
00170         ROUND(d,e,f,g,h,a,b,c,w[53],k[53]);
00171         ROUND(c,d,e,f,g,h,a,b,w[54],k[54]);
00172         ROUND(b,c,d,e,f,g,h,a,w[55],k[55]);
00173         ROUND(a,b,c,d,e,f,g,h,w[56],k[56]);
00174         ROUND(h,a,b,c,d,e,f,g,w[57],k[57]);
00175         ROUND(g,h,a,b,c,d,e,f,w[58],k[58]);
00176         ROUND(f,g,h,a,b,c,d,e,w[59],k[59]);
00177         ROUND(e,f,g,h,a,b,c,d,w[60],k[60]);
00178         ROUND(d,e,f,g,h,a,b,c,w[61],k[61]);
00179         ROUND(c,d,e,f,g,h,a,b,w[62],k[62]);
00180         ROUND(b,c,d,e,f,g,h,a,w[63],k[63]);
00181 
00182         p->h[0] += a;
00183         p->h[1] += b;
00184         p->h[2] += c;
00185         p->h[3] += d;
00186         p->h[4] += e;
00187         p->h[5] += f;
00188         p->h[6] += g;
00189         p->h[7] += h;
00190 }
00191 /*@=boundsread@*/
00192 #endif
00193 
00194 /*@-boundswrite@*/
00195 int sha256Update(register sha256Param *p, const byte *data, int size)
00196 {
00197         register int proclength;
00198 
00199         p->length += size;
00200         while (size > 0)
00201         {
00202                 proclength = ((p->offset + size) > 64) ? (64 - p->offset) : size;
00203                 memmove(((byte *) p->data) + p->offset, data, proclength);
00204                 size -= proclength;
00205                 data += proclength;
00206                 p->offset += proclength;
00207 
00208                 if (p->offset == 64)
00209                 {
00210                         sha256Process(p);
00211                         p->offset = 0;
00212                 }
00213         }
00214         return 0;
00215 }
00216 /*@=boundswrite@*/
00217 
00220 /*@-boundswrite@*/
00221 static void sha256Finish(register sha256Param *p)
00222         /*@globals internalState @*/
00223         /*@modifies p, internalState @*/
00224 {
00225         register byte *ptr = ((byte *) p->data) + p->offset++;
00226 
00227         *(ptr++) = 0x80;
00228 
00229         if (p->offset > 56)
00230         {
00231                 while (p->offset++ < 64)
00232                         *(ptr++) = 0;
00233 
00234                 sha256Process(p);
00235                 p->offset = 0;
00236         }
00237 
00238         ptr = ((byte *) p->data) + p->offset;
00239         while (p->offset++ < 56)
00240                 *(ptr++) = 0;
00241 
00242         #if WORDS_BIGENDIAN
00243         p->data[14] = ((uint32)(p->length >> 29));
00244         p->data[15] = ((uint32)((p->length << 3) & 0xffffffff));
00245         #else
00246         p->data[14] = swapu32((uint32)(p->length >> 29));
00247         p->data[15] = swapu32((uint32)((p->length << 3) & 0xffffffff));
00248         #endif
00249 
00250         sha256Process(p);
00251         p->offset = 0;
00252 }
00253 /*@=boundswrite@*/
00254 
00255 /*@-boundswrite@*/
00256 int sha256Digest(register sha256Param *p, uint32 *data)
00257 {
00258         sha256Finish(p);
00259         mp32copy(8, data, p->h);
00260         (void) sha256Reset(p);
00261         return 0;
00262 }
00263 /*@=boundswrite@*/

Generated on Tue Sep 17 15:59:46 2002 for rpm by doxygen1.2.14 written by Dimitri van Heesch, © 1997-2002