1 /******************************************************************************* 2 * Copyright 2014-2018 Intel Corporation 3 * All Rights Reserved. 4 * 5 * If this software was obtained under the Intel Simplified Software License, 6 * the following terms apply: 7 * 8 * The source code, information and material ("Material") contained herein is 9 * owned by Intel Corporation or its suppliers or licensors, and title to such 10 * Material remains with Intel Corporation or its suppliers or licensors. The 11 * Material contains proprietary information of Intel or its suppliers and 12 * licensors. The Material is protected by worldwide copyright laws and treaty 13 * provisions. No part of the Material may be used, copied, reproduced, 14 * modified, published, uploaded, posted, transmitted, distributed or disclosed 15 * in any way without Intel's prior express written permission. No license under 16 * any patent, copyright or other intellectual property rights in the Material 17 * is granted to or conferred upon you, either expressly, by implication, 18 * inducement, estoppel or otherwise. Any license under such intellectual 19 * property rights must be express and approved by Intel in writing. 20 * 21 * Unless otherwise agreed by Intel in writing, you may not remove or alter this 22 * notice or any other notice embedded in Materials by Intel or Intel's 23 * suppliers or licensors in any way. 24 * 25 * 26 * If this software was obtained under the Apache License, Version 2.0 (the 27 * "License"), the following terms apply: 28 * 29 * You may not use this file except in compliance with the License. You may 30 * obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 31 * 32 * 33 * Unless required by applicable law or agreed to in writing, software 34 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 35 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 36 * 37 * See the License for the specific language governing permissions and 38 * limitations under the License. 39 *******************************************************************************/ 40 41 /* 42 // 43 // Purpose: 44 // Cryptography Primitive. 45 // Message block processing according to SM5 46 // 47 // Contents: 48 // UpdateSM3() 49 // 50 // 51 */ 52 53 #include "owndefs.h" 54 #include "owncp.h" 55 #include "pcphash.h" 56 #include "pcptool.h" 57 58 #if !defined(_ENABLE_ALG_SM3_) 59 #pragma message("IPP_ALG_HASH_SM3 disabled") 60 61 #else 62 #pragma message("IPP_ALG_HASH_SM3 enabled") 63 64 #if !((_IPP32E>=_IPP32E_U8) || (_IPP32E==_IPP32E_N8) ) 65 66 /* 67 // SM3 Specific Macros 68 // (reference SM3 Cryptographic Hash Algorithm, 69 // Chinese Commercial Cryptography Administration Office, 2010.12) 70 */ 71 72 /* T1 and T2 are base for additive const generation */ 73 #define T1 (0x79CC4519) 74 #define T2 (0x7A879D8A) 75 76 // boolean functions (0<=nr<16) 77 #define FF1(x,y,z) ((x)^(y)^(z)) 78 #define GG1(x,y,z) ((x)^(y)^(z)) 79 // boolean functions (16<=nr<64) 80 #define FF2(x,y,z) (((x)&(y)) | ((x)&(z)) | ((y)&(z))) 81 #define GG2(x,y,z) (((x)&(y)) | (~(x)&(z))) 82 83 // P0 permutation: 84 #define P0(x) ((x) ^ ROL32((x),9) ^ ROL32((x),17)) 85 // P1 permutation: 86 #define P1(x) ((x) ^ ROL32((x),15) ^ ROL32((x),23)) 87 88 // update W 89 #define WUPDATE(nr, W) (P1(W[((nr)-16)&15] ^ W[((nr)-9)&15] ^ ROL32(W[((nr)-3)&15],15)) ^ ROL32(W[((nr)-13)&15],7) ^ W[((nr)-6)&15]) 90 91 // SM3 steps 92 #define SM3_STEP1(nr, A,B,C,D,E,F,G,H, Tj, W) { \ 93 TT1 = FF1(A,B,C) + D + (W[nr&15] ^ W[(nr+4)&15]); \ 94 TT2 = GG1(E,F,G) + H + W[nr&15]; \ 95 H = ROL32(A,12); \ 96 D = ROL32(H + E +Tj, 7); \ 97 H ^= D; \ 98 D += TT2; \ 99 H += TT1; \ 100 B = ROL32(B, 9); \ 101 D = P0(D); \ 102 F = ROL32(F, 19); \ 103 /*Tj = ROL32(Tj, 1);*/ \ 104 W[(nr)&15] = WUPDATE(nr, W); \ 105 } 106 107 #define SM3_STEP2(nr, A,B,C,D,E,F,G,H, Tj, W) { \ 108 TT1 = FF2(A,B,C) + D + (W[nr&15] ^ W[(nr+4)&15]); \ 109 TT2 = GG2(E,F,G) + H + W[nr&15]; \ 110 H = ROL32(A,12); \ 111 D = ROL32(H + E +Tj, 7); \ 112 H ^= D; \ 113 D += TT2; \ 114 H += TT1; \ 115 B = ROL32(B, 9); \ 116 D = P0(D); \ 117 F = ROL32(F, 19); \ 118 /*Tj = ROL32(Tj, 1);*/ \ 119 W[(nr)&15] = WUPDATE(nr, W); \ 120 } 121 122 #define SM3_STEP3(nr, A,B,C,D,E,F,G,H, Tj, W) { \ 123 TT1 = FF2(A,B,C) + D + (W[nr&15] ^ W[(nr+4)&15]); \ 124 TT2 = GG2(E,F,G) + H + W[nr&15]; \ 125 H = ROL32(A,12); \ 126 D = ROL32(H + E +Tj, 7); \ 127 H ^= D; \ 128 D += TT2; \ 129 H += TT1; \ 130 B = ROL32(B, 9); \ 131 D = P0(D); \ 132 F = ROL32(F, 19); \ 133 /*Tj = ROL32(Tj, 1);*/ \ 134 } 135 136 #define COMPACT_SM3_STEP(A,B,C,D,E,F,G,H, FF, GG, W,Tj, r) { \ 137 TT1 = FF((r)&0x30, A,B,C) + D + (W[(r)] ^ W[(r)+4]); \ 138 TT2 = GG((r)&0x30, E,F,G) + H + W[(r)]; \ 139 \ 140 _H = ROL32(A,12); \ 141 _D = ROL32(_H + E +Tj[(r)], 7); \ 142 _H ^= _D; \ 143 _D += TT2; \ 144 _H += TT1; \ 145 _D = P0(_D);\ 146 \ 147 H = G; \ 148 G = ROL32(F,19); \ 149 F = E; \ 150 E =_D; \ 151 D = C; \ 152 C = ROL32(B, 9); \ 153 B = A; \ 154 A =_H; \ 155 } 156 157 158 /*F* 159 // Name: UpdateSM3 160 // 161 // Purpose: Update internal hash according to input message stream. 162 // 163 // Parameters: 164 // uniHash pointer to in/out hash 165 // mblk pointer to message stream 166 // mlen message stream length (multiple by message block size) 167 // uniParam pointer to the optional parameter 168 // 169 *F*/ 170 #if defined(_ALG_SM3_COMPACT_) 171 #pragma message("SM3 compact") 172 173 __INLINE Ipp32u MagicFF(int s, Ipp32u a, Ipp32u b, Ipp32u c) 174 { 175 switch(s) { 176 case 0: return FF1(a,b,c); 177 default:return FF2(a,b,c); 178 } 179 } 180 __INLINE Ipp32u MagicGG(int s, Ipp32u e, Ipp32u f, Ipp32u g) 181 { 182 switch(s) { 183 case 0: return GG1(e,f,g); 184 default:return GG2(e,f,g); 185 } 186 } 187 188 void UpdateSM3(void* uniHash, const Ipp8u* mblk, int mlen, const void* uniParam) 189 { 190 Ipp32u* data = (Ipp32u*)mblk; 191 192 Ipp32u* hash = (Ipp32u*)uniHash; 193 Ipp32u* SM3_cnt_loc = (Ipp32u*)uniParam; 194 195 for(; mlen>=MBS_SM3; data += MBS_SM3/sizeof(Ipp32u), mlen -= MBS_SM3) { 196 int r; 197 198 /* 199 // expand message block 200 */ 201 Ipp32u W[68]; 202 /* initialize the first 16 words in the array W (remember about endian) */ 203 for(r=0; r<16; r++) { 204 #if (IPP_ENDIAN == IPP_BIG_ENDIAN) 205 W[r] = data[r]; 206 #else 207 W[r] = ENDIANNESS( data[r] ); 208 #endif 209 } 210 for(; r<68; r++) 211 W[r] = P1(W[r-16] ^ W[r-9] ^ ROL32(W[r-3],15)) ^ ROL32(W[r-13],7) ^ W[r-6]; 212 213 /* 214 // update hash 215 */ 216 { 217 /* init A, B, C, D, E, F, G, H by the input hash */ 218 Ipp32u A = hash[0]; 219 Ipp32u B = hash[1]; 220 Ipp32u C = hash[2]; 221 Ipp32u D = hash[3]; 222 Ipp32u E = hash[4]; 223 Ipp32u F = hash[5]; 224 Ipp32u G = hash[6]; 225 Ipp32u H = hash[7]; 226 227 Ipp32u TT1, TT2, _H, _D; 228 for(r=0; r<64; r++) 229 COMPACT_SM3_STEP(A,B,C,D,E,F,G,H, MagicFF,MagicGG, W, SM3_cnt_loc, r); 230 231 /* update hash */ 232 hash[0] ^= A; 233 hash[1] ^= B; 234 hash[2] ^= C; 235 hash[3] ^= D; 236 hash[4] ^= E; 237 hash[5] ^= F; 238 hash[6] ^= G; 239 hash[7] ^= H; 240 } 241 } 242 } 243 244 #else 245 void UpdateSM3(void* uniHash, const Ipp8u* mblk, int mlen, const void* uniParam) 246 { 247 Ipp32u* data = (Ipp32u*)mblk; 248 249 Ipp32u* hash = (Ipp32u*)uniHash; 250 Ipp32u* SM3_cnt_loc = (Ipp32u*)uniParam; 251 252 for(; mlen>=MBS_SM3; data += MBS_SM3/sizeof(Ipp32u), mlen -= MBS_SM3) { 253 254 /* copy input hash */ 255 Ipp32u A = hash[0]; 256 Ipp32u B = hash[1]; 257 Ipp32u C = hash[2]; 258 Ipp32u D = hash[3]; 259 Ipp32u E = hash[4]; 260 Ipp32u F = hash[5]; 261 Ipp32u G = hash[6]; 262 Ipp32u H = hash[7]; 263 264 Ipp32u W[16]; 265 int j; 266 267 268 /* initialize the first 16 words in the array W (remember about endian) */ 269 for(j=0; j<16; j++) { 270 #if (IPP_ENDIAN == IPP_BIG_ENDIAN) 271 W[j] = data[j]; 272 #else 273 W[j] = ENDIANNESS( data[j] ); 274 #endif 275 } 276 277 /* apply compression function */ 278 { 279 Ipp32u TT1, TT2; 280 SM3_STEP1( 0, A,B,C,D,E,F,G,H, SM3_cnt_loc[0], W); 281 SM3_STEP1( 1, H,A,B,C,D,E,F,G, SM3_cnt_loc[1], W); 282 SM3_STEP1( 2, G,H,A,B,C,D,E,F, SM3_cnt_loc[2], W); 283 SM3_STEP1( 3, F,G,H,A,B,C,D,E, SM3_cnt_loc[3], W); 284 SM3_STEP1( 4, E,F,G,H,A,B,C,D, SM3_cnt_loc[4], W); 285 SM3_STEP1( 5, D,E,F,G,H,A,B,C, SM3_cnt_loc[5], W); 286 SM3_STEP1( 6, C,D,E,F,G,H,A,B, SM3_cnt_loc[6], W); 287 SM3_STEP1( 7, B,C,D,E,F,G,H,A, SM3_cnt_loc[7], W); 288 289 SM3_STEP1( 8, A,B,C,D,E,F,G,H, SM3_cnt_loc[ 8], W); 290 SM3_STEP1( 9, H,A,B,C,D,E,F,G, SM3_cnt_loc[ 9], W); 291 SM3_STEP1(10, G,H,A,B,C,D,E,F, SM3_cnt_loc[10], W); 292 SM3_STEP1(11, F,G,H,A,B,C,D,E, SM3_cnt_loc[11], W); 293 SM3_STEP1(12, E,F,G,H,A,B,C,D, SM3_cnt_loc[12], W); 294 SM3_STEP1(13, D,E,F,G,H,A,B,C, SM3_cnt_loc[13], W); 295 SM3_STEP1(14, C,D,E,F,G,H,A,B, SM3_cnt_loc[14], W); 296 SM3_STEP1(15, B,C,D,E,F,G,H,A, SM3_cnt_loc[15], W); 297 298 SM3_STEP2(16, A,B,C,D,E,F,G,H, SM3_cnt_loc[16], W); 299 SM3_STEP2(17, H,A,B,C,D,E,F,G, SM3_cnt_loc[17], W); 300 SM3_STEP2(18, G,H,A,B,C,D,E,F, SM3_cnt_loc[18], W); 301 SM3_STEP2(19, F,G,H,A,B,C,D,E, SM3_cnt_loc[19], W); 302 SM3_STEP2(20, E,F,G,H,A,B,C,D, SM3_cnt_loc[20], W); 303 SM3_STEP2(21, D,E,F,G,H,A,B,C, SM3_cnt_loc[21], W); 304 SM3_STEP2(22, C,D,E,F,G,H,A,B, SM3_cnt_loc[22], W); 305 SM3_STEP2(23, B,C,D,E,F,G,H,A, SM3_cnt_loc[23], W); 306 307 SM3_STEP2(24, A,B,C,D,E,F,G,H, SM3_cnt_loc[24], W); 308 SM3_STEP2(25, H,A,B,C,D,E,F,G, SM3_cnt_loc[25], W); 309 SM3_STEP2(26, G,H,A,B,C,D,E,F, SM3_cnt_loc[26], W); 310 SM3_STEP2(27, F,G,H,A,B,C,D,E, SM3_cnt_loc[27], W); 311 SM3_STEP2(28, E,F,G,H,A,B,C,D, SM3_cnt_loc[28], W); 312 SM3_STEP2(29, D,E,F,G,H,A,B,C, SM3_cnt_loc[29], W); 313 SM3_STEP2(30, C,D,E,F,G,H,A,B, SM3_cnt_loc[30], W); 314 SM3_STEP2(31, B,C,D,E,F,G,H,A, SM3_cnt_loc[31], W); 315 316 SM3_STEP2(32, A,B,C,D,E,F,G,H, SM3_cnt_loc[32], W); 317 SM3_STEP2(33, H,A,B,C,D,E,F,G, SM3_cnt_loc[33], W); 318 SM3_STEP2(34, G,H,A,B,C,D,E,F, SM3_cnt_loc[34], W); 319 SM3_STEP2(35, F,G,H,A,B,C,D,E, SM3_cnt_loc[35], W); 320 SM3_STEP2(36, E,F,G,H,A,B,C,D, SM3_cnt_loc[36], W); 321 SM3_STEP2(37, D,E,F,G,H,A,B,C, SM3_cnt_loc[37], W); 322 SM3_STEP2(38, C,D,E,F,G,H,A,B, SM3_cnt_loc[38], W); 323 SM3_STEP2(39, B,C,D,E,F,G,H,A, SM3_cnt_loc[39], W); 324 325 SM3_STEP2(40, A,B,C,D,E,F,G,H, SM3_cnt_loc[40], W); 326 SM3_STEP2(41, H,A,B,C,D,E,F,G, SM3_cnt_loc[41], W); 327 SM3_STEP2(42, G,H,A,B,C,D,E,F, SM3_cnt_loc[42], W); 328 SM3_STEP2(43, F,G,H,A,B,C,D,E, SM3_cnt_loc[43], W); 329 SM3_STEP2(44, E,F,G,H,A,B,C,D, SM3_cnt_loc[44], W); 330 SM3_STEP2(45, D,E,F,G,H,A,B,C, SM3_cnt_loc[45], W); 331 SM3_STEP2(46, C,D,E,F,G,H,A,B, SM3_cnt_loc[46], W); 332 SM3_STEP2(47, B,C,D,E,F,G,H,A, SM3_cnt_loc[47], W); 333 334 SM3_STEP2(48, A,B,C,D,E,F,G,H, SM3_cnt_loc[48], W); 335 SM3_STEP2(49, H,A,B,C,D,E,F,G, SM3_cnt_loc[49], W); 336 SM3_STEP2(50, G,H,A,B,C,D,E,F, SM3_cnt_loc[50], W); 337 SM3_STEP2(51, F,G,H,A,B,C,D,E, SM3_cnt_loc[51], W); 338 SM3_STEP3(52, E,F,G,H,A,B,C,D, SM3_cnt_loc[52], W); 339 SM3_STEP3(53, D,E,F,G,H,A,B,C, SM3_cnt_loc[53], W); 340 SM3_STEP3(54, C,D,E,F,G,H,A,B, SM3_cnt_loc[54], W); 341 SM3_STEP3(55, B,C,D,E,F,G,H,A, SM3_cnt_loc[55], W); 342 343 SM3_STEP3(56, A,B,C,D,E,F,G,H, SM3_cnt_loc[56], W); 344 SM3_STEP3(57, H,A,B,C,D,E,F,G, SM3_cnt_loc[57], W); 345 SM3_STEP3(58, G,H,A,B,C,D,E,F, SM3_cnt_loc[58], W); 346 SM3_STEP3(59, F,G,H,A,B,C,D,E, SM3_cnt_loc[59], W); 347 SM3_STEP3(60, E,F,G,H,A,B,C,D, SM3_cnt_loc[60], W); 348 SM3_STEP3(61, D,E,F,G,H,A,B,C, SM3_cnt_loc[61], W); 349 SM3_STEP3(62, C,D,E,F,G,H,A,B, SM3_cnt_loc[62], W); 350 SM3_STEP3(63, B,C,D,E,F,G,H,A, SM3_cnt_loc[63], W); 351 } 352 /* update hash */ 353 hash[0] ^= A; 354 hash[1] ^= B; 355 hash[2] ^= C; 356 hash[3] ^= D; 357 hash[4] ^= E; 358 hash[5] ^= F; 359 hash[6] ^= G; 360 hash[7] ^= H; 361 } 362 } 363 #endif 364 365 #endif /* _PX/_W7/_T7, _MX/_M7 versions */ 366 #endif /* IPP_ALG_HASH_SM3 */ 367