1
8 import com.sekati.crypt.IHash;
9
10
14 class com.sekati.crypt.SHA256 implements IHash {
15
16
17
18
19
20
21
26 public static function calculate(str:String):String {
27 return hex_sha256( str );
28 }
29
30 private static function safe_add(x:Number, y:Number):Number {
31 var lsw:Number = (x & 0xFFFF) + (y & 0xFFFF);
32 var msw:Number = (x >> 16) + (y >> 16) + (lsw >> 16);
33 return (msw << 16) | (lsw & 0xFFFF);
34 }
35
36 private static function S(X:Number, n:Number):Number {
37 return (X >>> n) | (X << (32 - n));
38 }
39
40 private static function R(X:Number, n:Number):Number {
41 return (X >>> n);
42 }
43
44 private static function Ch(x:Number, y:Number, z:Number):Number {
45 return ((x & y) ^ ((~x) & z));
46 }
47
48 private static function Maj(x:Number, y:Number, z:Number):Number {
49 return ((x & y) ^ (x & z) ^ (y & z));
50 }
51
52 private static function Sigma0256(x:Number):Number {
53 return (S( x, 2 ) ^ S( x, 13 ) ^ S( x, 22 ));
54 }
55
56 private static function Sigma1256(x:Number):Number {
57 return (S( x, 6 ) ^ S( x, 11 ) ^ S( x, 25 ));
58 }
59
60 private static function Gamma0256(x:Number):Number {
61 return (S( x, 7 ) ^ S( x, 18 ) ^ R( x, 3 ));
62 }
63
64 private static function Gamma1256(x:Number):Number {
65 return (S( x, 17 ) ^ S( x, 19 ) ^ R( x, 10 ));
66 }
67
68 private static function Sigma0512(x:Number):Number {
69 return (S( x, 28 ) ^ S( x, 34 ) ^ S( x, 39 ));
70 }
71
72 private static function Sigma1512(x:Number):Number {
73 return (S( x, 14 ) ^ S( x, 18 ) ^ S( x, 41 ));
74 }
75
76 private static function Gamma0512(x:Number):Number {
77 return (S( x, 1 ) ^ S( x, 8 ) ^ R( x, 7 ));
78 }
79
80 private static function Gamma1512(x:Number):Number {
81 return (S( x, 19 ) ^ S( x, 61 ) ^ R( x, 6 ));
82 }
83
84 private static function core_sha256(m:Array, l:Number):Array {
85 var K:Array = [ 0x428A2F98, 0x71374491, 0xB5C0FBCF, 0xE9B5DBA5, 0x3956C25B, 0x59F111F1, 0x923F82A4, 0xAB1C5ED5, 0xD807AA98, 0x12835B01, 0x243185BE, 0x550C7DC3, 0x72BE5D74, 0x80DEB1FE, 0x9BDC06A7, 0xC19BF174, 0xE49B69C1, 0xEFBE4786, 0xFC19DC6, 0x240CA1CC, 0x2DE92C6F, 0x4A7484AA, 0x5CB0A9DC, 0x76F988DA, 0x983E5152, 0xA831C66D, 0xB00327C8, 0xBF597FC7, 0xC6E00BF3, 0xD5A79147, 0x6CA6351, 0x14292967, 0x27B70A85, 0x2E1B2138, 0x4D2C6DFC, 0x53380D13, 0x650A7354, 0x766A0ABB, 0x81C2C92E, 0x92722C85, 0xA2BFE8A1, 0xA81A664B, 0xC24B8B70, 0xC76C51A3, 0xD192E819, 0xD6990624, 0xF40E3585, 0x106AA070, 0x19A4C116, 0x1E376C08, 0x2748774C, 0x34B0BCB5, 0x391C0CB3, 0x4ED8AA4A, 0x5B9CCA4F, 0x682E6FF3, 0x748F82EE, 0x78A5636F, 0x84C87814, 0x8CC70208, 0x90BEFFFA, 0xA4506CEB, 0xBEF9A3F7, 0xC67178F2 ];
86 var HASH:Array = [ 0x6A09E667, 0xBB67AE85, 0x3C6EF372, 0xA54FF53A, 0x510E527F, 0x9B05688C, 0x1F83D9AB, 0x5BE0CD19 ];
87 var W:Array = new Array( 64 );
88 var a:Number, b:Number, c:Number, d:Number, e:Number, f:Number, g:Number, h:Number, i:Number, j:Number;
89 var T1:Number, T2:Number;
90
91 m[l >> 5] |= 0x80 << (24 - l % 32);
92 m[((l + 64 >> 9) << 4) + 15] = l;
93 for (i = 0; i < m.length ; i += 16) {
94 a = HASH[0];
95 b = HASH[1];
96 c = HASH[2];
97 d = HASH[3];
98 e = HASH[4];
99 f = HASH[5];
100 g = HASH[6];
101 h = HASH[7];
102 for (j = 0; j < 64 ; j++) {
103 if (j < 16) {
104 W[j] = m[j + i];
105 } else {
106 W[j] = safe_add( safe_add( safe_add( Gamma1256( W[j - 2] ), W[j - 7] ), Gamma0256( W[j - 15] ) ), W[j - 16] );
107 }
108 T1 = safe_add( safe_add( safe_add( safe_add( h, Sigma1256( e ) ), Ch( e, f, g ) ), K[j] ), W[j] );
109 T2 = safe_add( Sigma0256( a ), Maj( a, b, c ) );
110 h = g;
111 g = f;
112 f = e;
113 e = safe_add( d, T1 );
114 d = c;
115 c = b;
116 b = a;
117 a = safe_add( T1, T2 );
118 }
119 HASH[0] = safe_add( a, HASH[0] );
120 HASH[1] = safe_add( b, HASH[1] );
121 HASH[2] = safe_add( c, HASH[2] );
122 HASH[3] = safe_add( d, HASH[3] );
123 HASH[4] = safe_add( e, HASH[4] );
124 HASH[5] = safe_add( f, HASH[5] );
125 HASH[6] = safe_add( g, HASH[6] );
126 HASH[7] = safe_add( h, HASH[7] );
127 }
128 return HASH;
129 }
130
131
140 private static function str2binb(str:String):Array {
141 var bin:Array = new Array( );
142 var mask:Number = (1 << 8) - 1;
143 for (var i:Number = 0; i < str.length * 8 ; i += 8) {
144 bin[i >> 5] |= (str.charCodeAt( i / 8 ) & mask) << (24 - i % 32);
145 }
146 return bin;
147 }
148
149 private static function binb2str(bin:Array):String {
150 var str:String = "";
151 var mask:Number = (1 << 8) - 1;
152 for (var i:Number = 0; i < bin.length * 32 ; i += 8) {
153 str += String.fromCharCode( (bin[i >> 5] >>> (24 - i % 32)) & mask );
154 }
155 return str;
156 }
157
158 private static function binb2hex(binarray:Array):String {
159 var hex_tab:String = 0 ? "0123456789ABCDEF" : "0123456789abcdef";
160 var str:String = "";
161 for (var i:Number = 0; i < binarray.length * 4 ; i++) {
162 str += hex_tab.charAt( (binarray[i >> 2] >> ((3 - i % 4) * 8 + 4)) & 0xF ) + hex_tab.charAt( (binarray[i >> 2] >> ((3 - i % 4) * 8)) & 0xF );
163 }
164 return str;
165 }
166
167
180 private static function hex_sha256(s:String):String {
181 return binb2hex( core_sha256( str2binb( s ), s.length * 8 ) );
182 }
183
184 private static function str_sha256(s:String):String {
185 return binb2str( core_sha256( str2binb( s ), s.length * 8 ) );
186 }
187
188 private function SHA256() {
189 }
190 }