1/*- 2 * Copyright (C) 2001-2003 by NBMK Encryption Technologies. 3 * All rights reserved. 4 * 5 * NBMK Encryption Technologies provides no support of any kind for 6 * this software. Questions or concerns about it may be addressed to 7 * the members of the relevant open-source community at 8 * <tech-crypto@netbsd.org>. 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted provided that the following conditions are 12 * met: 13 * 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions and the following disclaimer. 16 * 17 * 2. Redistributions in binary form must reproduce the above 18 * copyright notice, this list of conditions and the following 19 * disclaimer in the documentation and/or other materials provided 20 * with the distribution. 21 * 22 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 23 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 24 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 25 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 26 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 27 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 28 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 29 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 30 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 31 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 32 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 33 */ 34 35static char const n8_id[] = "$Id: n8_cb_dsa.c,v 1.1 2008/10/30 12:02:15 darran Exp $"; 36/*****************************************************************************/ 37/** @file n8_cb_dsa.c 38 * @brief DSA Command Block Generator 39 * 40 * Generates all command blocks for DSA-related functions. 41 * 42 *****************************************************************************/ 43 44/***************************************************************************** 45 * Revision history: 46 * 09/10/02 brr Set command complete bit on last command block. 47 * 02/20/02 brr Removed references to the queue structure. 48 * 11/12/01 hml Fixed some debugging code. 49 * 10/31/01 bac Added support for SKS. 50 * 09/14/01 bac Use new DBG_PRINT_PK_CMD_BLOCKS macros. 51 * 08/24/01 bac Changed all methods to accept the pre-allocated command 52 * buffer. 53 * 07/30/01 bac Pass queue pointer to all length calculation macros. 54 * 07/12/01 bac Removed unused variables. 55 * 07/13/01 mel Fixed bug in cb_dsaVerify: 56 * command loaded wrong number of gR_mod_p bytes. 57 * 06/28/01 mel Fixed bug (kernel memory usage). 58 * Added comments. 59 * 06/28/01 bac Minor typo corrections. 60 * 06/26/01 bac Even more on conversion to use physical memory. 61 * 06/25/01 bac More on conversion to use physical memory. 62 * 06/20/01 mel Corrected use of kernel memory. 63 * 05/22/01 mel Original version. 64 ****************************************************************************/ 65/** @defgroup cb_dsa DSA Command Block Generator 66 */ 67 68#include "n8_common.h" 69#include "n8_pk_common.h" 70#include "n8_pub_errors.h" 71#include "n8_cb_dsa.h" 72#include "n8_util.h" 73 74/* #define ZERO_CMD_BLOCK(X) memset((X), 0, sizeof(PK_CMD_BLOCK_t)) */ 75#define ZERO_CMD_BLOCK(X) 76 77/***************************************************************************** 78 * cb_computeGRmodX 79 *****************************************************************************/ 80/** @ingroup cb_dsa 81 * @brief Creates the command blocks to compute the value for gR mod X 82 * 83 * 84 * @param req_p RW: Pointer to command 85 * blocks. 86 * @param key RO: pointer to phisical addresses of DSAObject. 87 * @param modulusDigits RO: number of digits in modulus p. 88 * 89 * @return 90 * ret - returns N8_STATUS_OK if successful or Error value. 91 * 92 * @par Errors 93 * N8_INVALID_OBJECT - command block pointer is NULL<BR> 94 * N8_MALLOC_FAILED - memory allocation failed<BR> 95 * 96 * @par Assumptions 97 * None.<br> 98 *****************************************************************************/ 99 100N8_Status_t cb_computeGRmodX(API_Request_t *req_p, 101 const int modulusDigits, 102 uint32_t g_a, 103 uint32_t X_a, 104 uint32_t res_a, 105 PK_CMD_BLOCK_t *cmdBuf_p, 106 PK_CMD_BLOCK_t **next_cmdBuf_p) 107{ 108 PK_CMD_BLOCK_t *math_wr_ptr = NULL; 109 PK_LDST_CMD_BLOCK_t *ldst_wr_ptr = NULL; 110 111 uint32_t slot0, slot1, slot2, slot3; 112 113 N8_Status_t ret = N8_STATUS_OK; 114 115 do 116 { 117 CHECK_OBJECT(req_p, ret); 118 119 /* Initialize the slot values. These are to address temporary 120 storage in the BNC. The slots accomodate operand sizes up to 121 the key length */ 122 slot0 = 0; 123 slot1 = modulusDigits; 124 slot2 = modulusDigits * 2; 125 slot3 = modulusDigits * 3; 126 127 /* Compute gR mod p */ 128 /* 1) Construct a command to load p */ 129 /* 130 * slot0 slot1 slot2 slot3 131 * p 132 */ 133 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) cmdBuf_p; 134 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 135 ldst_wr_ptr->r_offset = slot1; 136 ldst_wr_ptr->data_addr_ls = X_a; 137 ldst_wr_ptr->data_length = PK_DSA_P_Byte_Length(modulusDigits); 138 139 /* 2) Construct a command to load g */ 140 /* 141 * slot0 slot1 slot2 slot3 142 * p g 143 */ 144 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 145 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 146 ldst_wr_ptr->r_offset = slot2; 147 ldst_wr_ptr->data_addr_ls = g_a; 148 ldst_wr_ptr->data_length = PK_DSA_G_Byte_Length(modulusDigits); 149 150 /* 3) Construct a command for the operation R mod p */ 151 /* 152 * slot0 slot1 slot2 slot3 153 * p g R mod p 154 */ 155 math_wr_ptr = (PK_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 156 math_wr_ptr->opcode_si = PK_Cmd_R_Mod_M; 157 math_wr_ptr->r_offset = slot3; 158 math_wr_ptr->m_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 159 PK_Cmd_Length_Shift) | slot1; 160 161 /* 4) Construct a command for the operation g * Rmodp mod p */ 162 /* 163 * slot0 slot1 slot2 slot3 164 * gRmodp p g R mod p 165 */ 166 math_wr_ptr = (PK_CMD_BLOCK_t *) (math_wr_ptr + 1); 167 math_wr_ptr->opcode_si = PK_Cmd_AB_Mod_M; 168 math_wr_ptr->r_offset = slot0; 169 math_wr_ptr->m_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 170 PK_Cmd_Length_Shift) | slot1; 171 math_wr_ptr->a_length_offset = (PK_DSA_G_BNC_Length(modulusDigits) << 172 PK_Cmd_Length_Shift) | slot2; 173 math_wr_ptr->b_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 174 PK_Cmd_Length_Shift) | slot3; 175 176 /* 5) Construct a command to store gR mod p */ 177 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (math_wr_ptr + 1); 178 ldst_wr_ptr->opcode_si = PK_Cmd_Store_R; 179 ldst_wr_ptr->r_offset = slot0; 180 ldst_wr_ptr->data_addr_ls = res_a; 181 ldst_wr_ptr->data_length = PK_DSA_GR_MOD_P_Byte_Length(modulusDigits); 182 183 /* save next address for future use */ 184 *next_cmdBuf_p = (PK_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 185 186 DBG(("Compute gR mod X\n")); 187/* DBG_PRINT_CMD_BLOCKS("Compute gR mod X", 188 (PK_CMD_BLOCK_t *) req_p->PK_CommandBlock_ptr, 189 N8_CB_COMPUTE_GRMODX_NUMCMDS); */ 190 } while (FALSE); 191 192 return ret; 193} /* computeGRmodX */ 194 195/***************************************************************************** 196 * cb_dsaSign 197 *****************************************************************************/ 198/** @ingroup cb_dsa 199 * @brief Creates the command blocks to compute DSA signature 200 * 201 * 202 * @param req_p RW: Pointer to command 203 * blocks. 204 * @param key RO: The previously initialized DSAKeyObject 205 * containing the DSA key 206 * materials to be used. 207 * @param n_a RO: Physical address of random number n. 208 * @param paramBlock_a RO: Physical address of parameters block. 209 * @param msgHash_a RO: Physical address of hash. 210 * @param rValue_a RO: Physical address of r value. 211 * @param sValue_a RO: Physical address of s value. 212 * 213 * @return 214 * ret - returns N8_STATUS_OK if successful or Error value. 215 * 216 * @par Errors 217 * N8_INVALID_OBJECT - command block pointer is NULL<BR> 218 * N8_MALLOC_FAILED - memory allocation failed<BR> 219 * 220 * @par Assumptions 221 * None.<br> 222 *****************************************************************************/ 223N8_Status_t cb_dsaSign(API_Request_t *req_p, 224 const N8_DSAKeyObject_t *key_p, 225 uint32_t n_a, 226 uint32_t paramBlock_a, 227 uint32_t msgHash_a, 228 uint32_t rValue_a, 229 uint32_t sValue_a, 230 PK_CMD_BLOCK_t *cmdBuf_p) 231{ 232 PK_RSA_CMD_BLOCK_t *math_wr_ptr = NULL; 233 PK_LDST_CMD_BLOCK_t *ldst_wr_ptr = NULL; 234 uint32_t modulusDigits; 235 uint32_t sks_word; 236 N8_Status_t ret = N8_STATUS_OK; 237 238 do 239 { 240 CHECK_OBJECT(req_p, ret); 241 CHECK_OBJECT(key_p, ret); 242 243 modulusDigits = BYTES_TO_PKDIGITS(key_p->modulusLength); 244 245 DBG(("constructing sign command blocks\n")); 246 247 /* 1) Construct a command to load random number n */ 248 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) cmdBuf_p; 249 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 250 ldst_wr_ptr->r_offset = PK_DSA_N_BNC_Offset; 251 ldst_wr_ptr->data_addr_ls = n_a; 252 ldst_wr_ptr->data_length = PK_DSA_N_Byte_Length; 253 254 /* 2) Construct a command to load hash e1 */ 255 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 256 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 257 ldst_wr_ptr->r_offset = PK_DSA_E1_BNC_Offset; 258 ldst_wr_ptr->data_addr_ls = msgHash_a; 259 ldst_wr_ptr->data_length = PK_DSA_E1_Byte_Length; 260 261 if (key_p->keyType == N8_PRIVATE_SKS) 262 { 263 /* we are using the sks. set the sks_word variable to the correct 264 * offset. We do not need to load the DSA parameter block as it is 265 * already in the SKS. */ 266 sks_word = key_p->SKSKeyHandle.sks_offset; 267 } 268 else 269 { 270 /* 3) Construct a command to load the DSA parameter block */ 271 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 272 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 273 ldst_wr_ptr->r_offset = PK_DSA_P_BNC_Offset; 274 ldst_wr_ptr->data_addr_ls = paramBlock_a; 275 ldst_wr_ptr->data_length = PK_DSA_Param_Byte_Length(modulusDigits); 276 277 sks_word = PK_Cmd_N_Mask; 278 } 279 280 /* 4) Construct a command for the DSA operation */ 281 math_wr_ptr = (PK_RSA_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 282 math_wr_ptr->opcode_si = PK_Cmd_DSA_Sign_Op; 283 math_wr_ptr->sks = sks_word | (modulusDigits << PK_Cmd_Key_Length_Shift); 284 285 /* 5) Construct a command to store r */ 286 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (math_wr_ptr + 1); 287 ldst_wr_ptr->opcode_si = PK_Cmd_Store_R; 288 ldst_wr_ptr->r_offset = PK_DSA_R_BNC_Offset; 289 ldst_wr_ptr->data_addr_ls = rValue_a; 290 ldst_wr_ptr->data_length = PK_DSA_R_Byte_Length; 291 292 /* 6) Construct a command to store s */ 293 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 294 ldst_wr_ptr->opcode_si = PK_Cmd_Store_R | PK_Cmd_SI_Mask; 295 ldst_wr_ptr->r_offset = PK_DSA_S_BNC_Offset; 296 ldst_wr_ptr->data_addr_ls = sValue_a; 297 ldst_wr_ptr->data_length = PK_DSA_S_Byte_Length; 298 299 300 DBG_PRINT_PK_CMD_BLOCKS("DSA sign", 301 req_p->PK_CommandBlock_ptr, 302 N8_CB_DSA_SIGN_NUMCMDS(key_p)); 303 } while (FALSE); 304 return ret; 305} 306 307/***************************************************************************** 308 * cb_dsaVerify 309 *****************************************************************************/ 310/** @ingroup cb_dsa 311 * @brief Creates the command blocks to perform DSA verify operation 312 * 313 * 1) Compute e = e1 mod q 314 * 2) Compute invs = s^1 mod q 315 * 3) Compute u1 = invs * e mod q 316 * 4) Compute u2 = invs * r mod q 317 * 5) Compute v1 = g^u1 mod p 318 * 6) Compute w = y^u2 mod p 319 * 7) Compute v3 = v1 * w mod p 320 * 8) Compute v = v3 mod q 321 * 322 * 323 * Big Number Cache slot allocation 324 * 325 * 1 2 3 4 5 6 7 8 326 * ------------------------------------------------------------------------- 327 * step 1) q e1 328 * . e 329 * step 2) . s 330 * . invs 331 * step 3) . . u1 332 * step 4) . . r . 333 * . . u2 . 334 * step 5) . p[0] . . 2^128 335 * . p[0]^-1 . . . 336 * . -p[0]^-1 . . . 337 * . . . . p g 338 * . . . . . Rmodp . 339 * . . . . . gRmodp . 340 * . . . . . v1 341 * step 6) . . . . Rmodp . y 342 * . . . . yRmodp . 343 * . . . . . w 344 * step 7) . . v3 345 * step 8) v 346 * 347 * 348 * 349 * @param req_p RW: Pointer to command 350 * blocks. 351 * @param key RO: The previously initialized DSAKeyObject 352 * containing the DSA key 353 * materials to be used. 354 * @param q_a RO: Physical address of q value. 355 * @param cp_a RO: Physical address of computed cp. 356 * @param gR_mod_p_a RO: Physical address of computed gRmodp. 357 * @param p_a RO: Physical address of p value. 358 * @param publicKey_a RO: Physical address of public key. 359 * @param mh_a RO: Physical address of hash. 360 * @param r_a RO: Physical address of r value. 361 * @param s_a RO: Physical address of s value. 362 * @param res_a WO: Physical address of result. 363 * 364 * @return 365 * ret - returns N8_STATUS_OK if successful or Error value. 366 * 367 * @par Errors 368 * N8_INVALID_OBJECT - command block pointer is NULL<BR> 369 * N8_MALLOC_FAILED - memory allocation failed<BR> 370 * 371 * @par Assumptions 372 * None.<br> 373 *****************************************************************************/ 374N8_Status_t cb_dsaVerify(API_Request_t *req_p, 375 const N8_DSAKeyObject_t *key_p, 376 uint32_t q_a, 377 uint32_t cp_a, 378 uint32_t gR_mod_p_a, 379 uint32_t p_a, 380 uint32_t publicKey_a, 381 uint32_t mh_a, 382 uint32_t r_a, 383 uint32_t s_a, 384 uint32_t res_a, 385 PK_CMD_BLOCK_t *cmdBuf_p) 386{ 387 PK_CMD_BLOCK_t *math_wr_ptr = NULL; 388 PK_LDST_CMD_BLOCK_t *ldst_wr_ptr = NULL; 389 390 uint32_t modulusDigits; 391 uint32_t slot1, slot2, slot3, slot4; 392 uint32_t slot5, slot6, slot7, slot8; 393 394 N8_Status_t ret = N8_STATUS_OK; 395 396 do 397 { 398 CHECK_OBJECT(req_p, ret); 399 400 modulusDigits = BYTES_TO_PKDIGITS(key_p->modulusLength); 401 402 /* Initialize the slot values. These are to address temporary 403 storage in the BNC. Slots 1-4 hold 2-digit operands. 404 Slots 5-8 hold operands up to the key size in length. */ 405 slot1 = 0; /* q */ 406 slot2 = slot1 + PK_DSA_N_BNC_Length; /* invs */ 407 slot3 = slot2 + PK_DSA_N_BNC_Length; /* e1 */ 408 slot4 = slot3 + PK_DSA_N_BNC_Length; /* */ 409 slot5 = slot4 + modulusDigits; 410 slot6 = slot5 + modulusDigits; 411 slot7 = slot6 + modulusDigits; 412 slot8 = slot7 + modulusDigits; 413 414 /* 415 Compute e = e1 mod q 416 */ 417 /* 1) Construct a command to load q */ 418 /* 1 2 3 4 5 6 7 8 419 420 */ 421 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) cmdBuf_p; 422 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 423 ldst_wr_ptr->r_offset = slot1; 424 ldst_wr_ptr->data_addr_ls = (unsigned int) q_a; 425 ldst_wr_ptr->data_length = PK_DSA_Q_Byte_Length; 426 427 428 /* 2)Construct a command to load e1 */ 429 /* 1 2 3 4 5 6 7 8 430 q 431 */ 432 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 433 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 434 ldst_wr_ptr->r_offset = slot3; 435 ldst_wr_ptr->data_addr_ls = mh_a; 436 ldst_wr_ptr->data_length = PK_DSA_E1_Byte_Length; 437 438 /* 3) Construct a command for the operation e1 mod q */ 439 /* 1 2 3 4 5 6 7 8 440 q e1 441 */ 442 math_wr_ptr = (PK_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 443 math_wr_ptr->opcode_si = PK_Cmd_A_Mod_M; 444 math_wr_ptr->r_offset = slot4; 445 math_wr_ptr->m_length_offset = (PK_DSA_Q_BNC_Length << 446 PK_Cmd_Length_Shift) | slot1; 447 math_wr_ptr->a_length_offset = (PK_DSA_E1_BNC_Length << 448 PK_Cmd_Length_Shift) | slot3; 449 450 /* Compute invs = s^-1 mod q */ 451 /* 4) Construct a command to load s */ 452 /* 1 2 3 4 5 6 7 8 453 q e1 e1 mod q 454 */ 455 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) math_wr_ptr + 1; 456 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 457 ldst_wr_ptr->r_offset = slot3; 458 ldst_wr_ptr->data_addr_ls = s_a; 459 ldst_wr_ptr->data_length = PK_DSA_S_Byte_Length; 460 461 /* 5) Construct a command for the operation invs = s^-1 mod q */ 462 /* 1 2 3 4 5 6 7 8 463 q s e1 mod q 464 */ 465 math_wr_ptr = (PK_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 466 math_wr_ptr->opcode_si = PK_Cmd_Inverse_A_Mod_M; 467 math_wr_ptr->r_offset = slot2; 468 math_wr_ptr->m_length_offset = (PK_DSA_Q_BNC_Length << 469 PK_Cmd_Length_Shift) | slot1; 470 math_wr_ptr->a_length_offset = (PK_DSA_S_BNC_Length << 471 PK_Cmd_Length_Shift) | slot3; 472 473 /* Compute u1 = invs * e mod q */ 474 /* 6) Construct a command for the operation u1 = invs * e mod q */ 475 /* 1 2 3 4 5 6 7 8 476 q invs s e1 mod q 477 */ 478 math_wr_ptr = (PK_CMD_BLOCK_t *) (math_wr_ptr + 1); 479 math_wr_ptr->opcode_si = PK_Cmd_AB_Mod_M; 480 math_wr_ptr->r_offset = slot4; 481 math_wr_ptr->m_length_offset = (PK_DSA_Q_BNC_Length << 482 PK_Cmd_Length_Shift) | slot1; 483 math_wr_ptr->a_length_offset = (PK_DSA_Q_BNC_Length << 484 PK_Cmd_Length_Shift) | slot2; 485 math_wr_ptr->b_length_offset = (PK_DSA_Q_BNC_Length << 486 PK_Cmd_Length_Shift) | slot4; 487 488 /* Compute u2 = invs * r mod q */ 489 /* 7) Construct a command to load r */ 490 /* 1 2 3 4 5 6 7 8 491 q invs s u1 492 */ 493 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (math_wr_ptr + 1); 494 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 495 ldst_wr_ptr->r_offset = slot3; 496 ldst_wr_ptr->data_addr_ls = r_a; 497 ldst_wr_ptr->data_length = PK_DSA_R_Byte_Length; 498 499 /* 8) Construct a command for the operation u2 = invs * r mod q */ 500 /* 1 2 3 4 5 6 7 8 501 q invs r u1 502 */ 503 math_wr_ptr = (PK_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 504 math_wr_ptr->opcode_si = PK_Cmd_AB_Mod_M; 505 math_wr_ptr->r_offset = slot3; 506 math_wr_ptr->m_length_offset = (PK_DSA_Q_BNC_Length << 507 PK_Cmd_Length_Shift) | slot1; 508 math_wr_ptr->a_length_offset = (PK_DSA_Q_BNC_Length << 509 PK_Cmd_Length_Shift) | slot2; 510 math_wr_ptr->b_length_offset = (PK_DSA_R_BNC_Length << 511 PK_Cmd_Length_Shift) | slot3; 512 513 /* Compute v1 = g^u1 mod p */ 514 515 /* 9) Construct a command to load cp = -t mod 2^128 */ 516 /* 1 2 3 4 5 6 7 8 517 q invs u2 u1 518 */ 519 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (math_wr_ptr + 1); 520 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 521 ldst_wr_ptr->r_offset = slot2; 522 ldst_wr_ptr->data_addr_ls = (unsigned int) cp_a; 523 ldst_wr_ptr->data_length = PK_DSA_CP_Byte_Length; 524 525 /* 10) Construct a command to load g * R mod p */ 526 /* 1 2 3 4 5 6 7 8 527 q cp u2 u1 528 */ 529 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 530 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 531 ldst_wr_ptr->r_offset = slot6; 532 ldst_wr_ptr->data_addr_ls = gR_mod_p_a; 533 ldst_wr_ptr->data_length = PK_DSA_GR_MOD_P_Byte_Length(modulusDigits); 534 535 /* 11) Construct a command to load p */ 536 /* 1 2 3 4 5 6 7 8 537 q cp u2 u1 gR_mod_p 538 */ 539 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 540 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 541 ldst_wr_ptr->r_offset = slot5; 542 ldst_wr_ptr->data_addr_ls = (unsigned int) p_a; 543 ldst_wr_ptr->data_length = PK_DSA_P_Byte_Length(modulusDigits); 544 545 /* 12) Construct a command for the operation v1 = g^u1 mod p */ 546 /* 1 2 3 4 5 6 7 8 547 q cp u2 u1 p gR_mod_p 548 */ 549 math_wr_ptr = (PK_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 550 math_wr_ptr->opcode_si = PK_Cmd_Exp_G_Mod_M; 551 math_wr_ptr->r_offset = slot7; 552 math_wr_ptr->m_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 553 PK_Cmd_Length_Shift) | slot5; 554 math_wr_ptr->a_length_offset = (PK_DSA_GR_MOD_P_BNC_Length(modulusDigits) << 555 PK_Cmd_Length_Shift) | slot6; 556 math_wr_ptr->b_length_offset = (PK_DSA_Q_BNC_Length << 557 PK_Cmd_Length_Shift) | slot4; 558 math_wr_ptr->c_offset = slot2; 559 560 561 /* Compute w = y^u2 mod p */ 562 /* 13) Construct a command to load y */ 563 /* 1 2 3 4 5 6 7 8 564 q cp u2 u1 p gR_mod_p v1 565 */ 566 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (math_wr_ptr + 1); 567 ldst_wr_ptr->opcode_si = PK_Cmd_Load_R; 568 ldst_wr_ptr->r_offset = slot8; 569 ldst_wr_ptr->data_addr_ls = (unsigned int) publicKey_a; 570 ldst_wr_ptr->data_length = PK_DSA_Y_Byte_Length(modulusDigits); 571 572 /* 14) Construct a command for the operation R mod p */ 573 /* 1 2 3 4 5 6 7 8 574 q cp u2 u1 p gR_mod_p v1 publicKey 575 */ 576 math_wr_ptr = (PK_CMD_BLOCK_t *) (ldst_wr_ptr + 1); 577 math_wr_ptr->opcode_si = PK_Cmd_R_Mod_M; 578 math_wr_ptr->r_offset = slot6; 579 math_wr_ptr->m_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 580 PK_Cmd_Length_Shift) | slot5; 581 582 /* 15) Construct a command for the operation yR mod p */ 583 /* 1 2 3 4 5 6 7 8 584 q cp u2 u1 p R_mod_p v1 publicKey(y) 585 */ 586 math_wr_ptr = (PK_CMD_BLOCK_t *) (math_wr_ptr + 1); 587 math_wr_ptr->opcode_si = PK_Cmd_AB_Mod_M; 588 math_wr_ptr->r_offset = slot6; 589 math_wr_ptr->m_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 590 PK_Cmd_Length_Shift) | slot5; 591 math_wr_ptr->a_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 592 PK_Cmd_Length_Shift) | slot8; 593 math_wr_ptr->b_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 594 PK_Cmd_Length_Shift) | slot6; 595 596 /* 16) Construct a command for the operation w = y^u2 mod p */ 597 /* 1 2 3 4 5 6 7 8 598 q cp u2 u1 p yR_mod_p v1 publicKey(y) 599 */ 600 math_wr_ptr = (PK_CMD_BLOCK_t *) (math_wr_ptr + 1); 601 math_wr_ptr->opcode_si = PK_Cmd_Exp_G_Mod_M; 602 math_wr_ptr->r_offset = slot8; 603 math_wr_ptr->m_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 604 PK_Cmd_Length_Shift) | slot5; 605 math_wr_ptr->a_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 606 PK_Cmd_Length_Shift) | slot6; 607 math_wr_ptr->b_length_offset = (PK_DSA_Q_BNC_Length << 608 PK_Cmd_Length_Shift) | slot3; 609 math_wr_ptr->c_offset = slot2; 610 611 /* Compute v3 = v1 * w mod p */ 612 /* 17) Construct a command for the operation v3 = v1 * w mod p */ 613 /* 1 2 3 4 5 6 7 8 614 q cp u2 u1 p yR_mod_p v1 w 615 */ 616 math_wr_ptr = (PK_CMD_BLOCK_t *) (math_wr_ptr + 1); 617 math_wr_ptr->opcode_si = PK_Cmd_AB_Mod_M; 618 math_wr_ptr->r_offset = slot7; 619 math_wr_ptr->m_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 620 PK_Cmd_Length_Shift) | slot5; 621 math_wr_ptr->a_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 622 PK_Cmd_Length_Shift) | slot7; 623 math_wr_ptr->b_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 624 PK_Cmd_Length_Shift) | slot8; 625 626 /* Compute v = v3 mod q */ 627 /* 18) Construct a command for the operation v = v3 mod q */ 628 /* 1 2 3 4 5 6 7 8 629 q cp u2 u1 p yR_mod_p v3 w 630 */ 631 math_wr_ptr = (PK_CMD_BLOCK_t *) (math_wr_ptr + 1); 632 math_wr_ptr->opcode_si = PK_Cmd_A_Mod_M; 633 math_wr_ptr->r_offset = slot1; 634 math_wr_ptr->m_length_offset = (PK_DSA_Q_BNC_Length << 635 PK_Cmd_Length_Shift) | slot1; 636 math_wr_ptr->a_length_offset = (PK_DSA_P_BNC_Length(modulusDigits) << 637 PK_Cmd_Length_Shift) | slot7; 638 639 /* 19) Construct a command to store v */ 640 /* 1 2 3 4 5 6 7 8 641 v cp u2 u1 p yR_mod_p v3 w 642 */ 643 ldst_wr_ptr = (PK_LDST_CMD_BLOCK_t *) (math_wr_ptr + 1); 644 ldst_wr_ptr->opcode_si = PK_Cmd_Store_R | PK_Cmd_SI_Mask; 645 ldst_wr_ptr->r_offset = slot1; 646 ldst_wr_ptr->data_addr_ls = res_a; 647 ldst_wr_ptr->data_length = PK_DSA_Q_Byte_Length; 648 649 650 DBG_PRINT_PK_CMD_BLOCKS("DSA verify", 651 (PK_CMD_BLOCK_t *) req_p->PK_CommandBlock_ptr, 652 N8_CB_DSA_VERIFY_NUMCMDS); 653 } while (FALSE); 654 655 return ret; 656 657} /* cb_dsaVerify */ 658 659/***************************************************************************** 660 * cb_DSASignOperations 661 *****************************************************************************/ 662/** @ingroup cb_rsa 663 * @brief Calculate the number of operations required for an DSA Sign. 664 * 665 * The operations used to perform an DSA Sign depend upon the key type. If the 666 * type is N8_PRIVATE_SKS, then the DSA Sign Operation will use the parameter 667 * block taken from the SKS, saving a load. If it is not SKS then the parameter 668 * block must be manually loaded and used. 669 * 670 * @param key_p RO: Pointer to the key object. 671 * 672 * @par Externals 673 * None 674 * 675 * @return 676 * number of commands necessary 677 * 678 * @par Errors 679 * None 680 * 681 * @par Assumptions 682 * The key pointer is valid. We assume this has been checked by the API. 683 *****************************************************************************/ 684unsigned int cb_DSASignOperations(const N8_DSAKeyObject_t *key_p) 685{ 686 unsigned int ret = 0; 687 const int NOT_USING_SKS_NUM_COMMANDS = 6; 688 689 if (key_p->keyType == N8_PRIVATE_SKS) 690 { 691 ret = NOT_USING_SKS_NUM_COMMANDS - 1; 692 } 693 else 694 { 695 ret = NOT_USING_SKS_NUM_COMMANDS; 696 } 697 return ret; 698} /* cb_RSADecryptOperations */ 699 700