📄 ubsmath.c
字号:
/* * Broadcom Cryptonet Driver software is distributed as is, without any warranty * of any kind, either express or implied as further specified in the GNU Public * License. This software may be used and distributed according to the terms of * the GNU Public License. * * Cryptonet is a registered trademark of Broadcom Corporation. *//****************************************************************************** * * Copyright 2000 * Broadcom Corporation * 16215 Alton Parkway * PO Box 57013 * Irvine CA 92619-7013 * *****************************************************************************//* * Broadcom Corporation uBSec SDK *//* * ubsmath.c: Math function acceleration functions * * Revision History: * * 03/17/2000 SOR Created * 07/06/2000 DPA Fixes for SMP operation * 07/26/00 SOR Virtual/Physical Memory manipulation modifications * 04/20/2001 RJT Added support for CPU-DMA memory synchronization * 07/16/2001 RJT Added support for BCM5821 * 10/09/2001 SRM 64 bit port */#include "ubsincl.h"/* * ubsec_MathCommand: Process a list of Math commands. * * Immediate Status is returned. Completion status is returned * on a per command callback */ubsec_Status_t ubsec_MathCommand(ubsec_DeviceContext_t Context, ubsec_MathCommandInfo_pt pCommand, int *NumCommands){ DeviceInfo_pt pDevice=(DeviceInfo_pt)Context; VOLATILE MasterCommand_t *pMCR; VOLATILE Packet_t *pPacket; VOLATILE KeyContext_t *pContext; VOLATILE int PacketIndex; int CommandIndex=0; int CommandCount=*NumCommands; ubsec_Status_t Status; unsigned long SaveConfig; ubsec_MathCommandParams_pt pParams; VOLATILE Math_CtxCmdBuf_t *pMathContext; int offset; VOLATILE DataBufChainList_t *FragPtr, *NextFragPtr; int DataLength; int NormalizeLen,NrmBits=0; int element; UBS_UINT32 *longkey; ubsec_MemAddress_t PhysAddr; CallBackInfo_pt pCompletionContext; if (!UBSEC_IS_KEY_DEVICE(pDevice)) { Dbg_Print(DBG_FATAL,( "ubsec: Math Command for a crypto device\n " )); return(UBSEC_STATUS_NO_DEVICE ); } Dbg_Print(DBG_MATH,( "ubsec: Math command %d ",*NumCommands )); /* * Check some parameters */ if(pDevice==NULL_DEVICE_INFO) { Dbg_Print(DBG_FATAL,( "NO DEV\n " )); return(UBSEC_STATUS_NO_DEVICE ); } Dbg_Print(DBG_MATH,( "\n")); if (OS_EnterCriticalSection(pDevice,SaveConfig)) { return(UBSEC_STATUS_DEVICE_BUSY); } /* Get the next MCR to load */ Get_New_MCR: *NumCommands=CommandIndex; /* Update number completed */ if ((pMCR=GetFreeMCR(pDevice,UBSEC_KEY_LIST,&Status))== NULL_MASTER_COMMAND) goto Error_Return; /* Add packets to this MCR. */ Dbg_Print(DBG_MATH,( "ubsec: mcr_index %d MCR <%0x,%0x>\n",pMCR->Index,pMCR,pMCR->MCRPhysicalAddress)); /* Initialize the packet information */ PacketIndex = pMCR->NumberOfPackets; pPacket = &(pMCR->PacketArray[PacketIndex]); /* Set up the current packet. */ pContext = pMCR->KeyContextList[PacketIndex]; pMathContext=&pContext->CtxCmdBuf.Math_CtxCmdBuf; Status=UBSEC_STATUS_SUCCESS; /* Wishful thinking? */ Dbg_Print(DBG_MATH,( "ubsec: PacketIndex %d \n",pMCR->NumberOfPackets)); /* Process all the commands in the command list. */ for (; CommandIndex < CommandCount ; CommandIndex++) { /* Add all the packets to the MCR*/ if( PacketIndex >= MCR_MAXIMUM_PACKETS ) { Dbg_Print(DBG_MATH,( "ubsec: overran mcr buffer. %d\n",PacketIndex,CommandIndex )); /* * We have filled this MCR. * Advance next free. Wrap around if necessary */ pDevice->NextFreeMCR[UBSEC_KEY_LIST]=(MasterCommand_pt)pMCR->pNextMCR; Dbg_Print(DBG_MATH,( "ubsec: PushMCR ..." )); PushMCR(pDevice); /* Get it going (pipeline) */ goto Get_New_MCR; /* Try to add to the next MCR */ } pCompletionContext=(CallBackInfo_pt)&pMCR->CompletionArray[PacketIndex]; /* First set up the command type and parameters. */ Dbg_Print(DBG_MATH,( "ubsec: Math Command packet_Index %d, Context Buf <%0x,%0x>\n",PacketIndex,pContext,pContext->PhysicalAddress )); pPacket->PacketContextBuffer=pContext->PhysicalAddress; switch (pCommand->Command) { case UBSEC_MATH_MODADD : pContext->operation_type = OPERATION_MOD_ADD; break; case UBSEC_MATH_MODSUB : pContext->operation_type = OPERATION_MOD_SUB; break; case UBSEC_MATH_MODMUL : pContext->operation_type = OPERATION_MOD_MULT; break; case UBSEC_MATH_MODEXP : pContext->operation_type = OPERATION_MOD_EXPON; break; case UBSEC_MATH_MODREM : pContext->operation_type = OPERATION_MOD_REDUCT; break;#if defined(UBSEC_582x) case UBSEC_MATH_DBLMODEXP : /* DBLMODEXP supported in "582x mode" driver for BCM5821 and later chips only */ if (pDevice->DeviceID < BROADCOM_DEVICE_ID_5821) { Status=(UBSEC_STATUS_INVALID_PARAMETER); goto Error_Return; } pContext->operation_type = OPERATION_MOD_DBLEXP; break;#endif /* UBSEC_582x */ default: Status=(UBSEC_STATUS_INVALID_PARAMETER); goto Error_Return; } pParams=&pCommand->Parameters; /* Clear the context. */ RTL_MemZero(pMathContext,sizeof(Math_CtxCmdBuf_t)); pContext->cmd_structure_length= MATH_STATIC_CONTEXT_SIZE; if ( pCommand->Command != UBSEC_MATH_DBLMODEXP) { /* The modulus needs to be aligned on a 512/768 or 1024 bit boundary. */ /* * Save amount to normalize/renormalize. */ if (pParams->ModN.KeyLength <=512) NormalizeLen=512; else if (pParams->ModN.KeyLength <=768) NormalizeLen=768; else if (pParams->ModN.KeyLength <=1024) NormalizeLen=1024;#ifdef UBSEC_582x_CLASS_DEVICE else if (pParams->ModN.KeyLength <=1536) NormalizeLen=1536; else NormalizeLen=2048;#else else return(UBSEC_STATUS_INVALID_PARAMETER);#endif } /* end non-DBLMODEXP modulus size alignment block */ else { /* DBLMODEXP operation */ NormalizeLen=512; /* The DBLMODEXP moduli must both be 512 bits (or fewer) long */ }#ifndef UBSEC_HW_NORMALIZE if ((NrmBits = ubsec_NormalizeDataTo(&pParams->ModN,NormalizeLen))) { Dbg_Print(DBG_FATAL,("ubsec: MATH NrmBits %d\n",NrmBits)); ubsec_ShiftData(&pParams->ParamA, NrmBits); } pMCR->KeyContextList[PacketIndex]->NormBits=NrmBits;#else NrmBits=0;#endif pMCR->KeyContextList[PacketIndex]->ResultKey[0]=&pParams->Result; /* Save here for post-command finishing */ if (pCommand->Command == UBSEC_MATH_DBLMODEXP) { pMCR->KeyContextList[PacketIndex]->ResultKey[1]=&pParams->Result2; /* Save here for post-command finishing */ } else { pMCR->KeyContextList[PacketIndex]->ResultKey[1]=NULL; /* Not used */ } pMCR->KeyContextList[PacketIndex]->ResultRNG=NULL; /* Not used */ /* * Output value may need to be rounded up to represent an integral * number of 32 bit words, same total length as modulus N. */ /* N Copy the modulo value modulo */ pMathContext->modulus_length = (unsigned short)CPU_TO_CTRL_SHORT(pParams->ModN.KeyLength); offset=NormalizeLen/8;#ifndef UBSEC_HW_NORMALIZE #if defined(UBS_ENABLE_KEY_SWAP) copywords((UBS_UINT32 *)&pMathContext->NE[0], (UBS_UINT32 *)OS_GetVirtualAddress(pParams->ModN.KeyValue), offset/4); #else RTL_Memcpy(&pMathContext->NE[0],OS_GetVirtualAddress(pParams->ModN.KeyValue),offset); #endif /* UBS_ENABLE_KEY_SWAP */#else #if defined(UBS_ENABLE_KEY_SWAP) copywords((UBS_UINT32 *)&pMathContext->NE[0], (UBS_UINT32 *)OS_GetVirtualAddress(pParams->ModN.KeyValue), ROUNDUP_TO_32_BIT(pParams->ModN.KeyLength)/32); #else RTL_Memcpy(&pMathContext->NE[0],OS_GetVirtualAddress(pParams->ModN.KeyValue), ROUNDUP_TO_32_BIT(pParams->ModN.KeyLength)/8); #endif /* UBS_ENABLE_KEY_SWAP */#endif /* Update the total context length to reflect the modulus. */ pContext->cmd_structure_length+=(offset); if (pCommand->Command==UBSEC_MATH_DBLMODEXP) { /* Second modulus needs to be copied to the context for dblmodexp */#ifndef UBSEC_HW_NORMALIZE #if defined(UBS_ENABLE_KEY_SWAP) copywords((UBS_UINT32 *)&pMathContext->NE[NormalizeLen/32], (UBS_UINT32 *)OS_GetVirtualAddress(pParams->ModN2.KeyValue), offset/4); #else RTL_Memcpy(&pMathContext->NE[NormalizeLen/32],OS_GetVirtualAddress(pParams->ModN2.KeyValue),offset); #endif /* UBS_ENABLE_KEY_SWAP */#else #if defined(UBS_ENABLE_KEY_SWAP) copywords((UBS_UINT32 *)&pMathContext->NE[NormalizeLen/32], (UBS_UINT32 *)OS_GetVirtualAddress(pParams->ModN2.KeyValue), ROUNDUP_TO_32_BIT(pParams->ModN2.KeyLength)/32); #else RTL_Memcpy(&pMathContext->NE[NormalizeLen/32],OS_GetVirtualAddress(pParams->ModN2.KeyValue), ROUNDUP_TO_32_BIT(pParams->ModN2.KeyLength)/8); #endif /* UBS_ENABLE_KEY_SWAP */#endif /* Update the total context length to reflect the second modulus. */ pContext->cmd_structure_length+=(offset); /* Second modulus' length needs to be present in context for dblmodexp */ /* Place the two lengths in their proper context fields (see datasheet) */ pMathContext->exponent_length = pMathContext->modulus_length; pMathContext->modulus_length = (unsigned short)CPU_TO_CTRL_SHORT(pParams->ModN2.KeyLength); } /* end second modulus copy for dblmodexp */ if (pCommand->Command==UBSEC_MATH_MODREM) { /* Message length needs to be present in context for modrem */ pMathContext->exponent_length= (unsigned short)CPU_TO_CTRL_SHORT(pParams->ParamA.KeyLength); } else if (pCommand->Command==UBSEC_MATH_MODEXP) { /* Exponent length needs to be present in context for modexp */ pMathContext->exponent_length= (unsigned short)CPU_TO_CTRL_SHORT(pParams->ParamB.KeyLength); } /* Otherwise leave pMathContext->exponent_length field 0 (reserved) */ #ifdef UBSDBG /* Print out the context information if required */ { int WordLen,i; WordLen=(pContext->cmd_structure_length-MATH_STATIC_CONTEXT_SIZE)/4; Dbg_Print(DBG_MATH,( "ubsec: ---- DH Math Modulus Length = %d, Exponent Length = %d\n", CTRL_TO_CPU_SHORT(pMathContext->modulus_length), CTRL_TO_CPU_SHORT(pMathContext->exponent_length))); Dbg_Print(DBG_MATH,( "Context Len %d Context Value=[", (pContext->cmd_structure_length))); for ( i=0 ; i < WordLen ; i++) { Dbg_Print(DBG_MATH,( "%08x ",SYS_TO_BE_LONG(pMathContext->NE[i]))); } Dbg_Print(DBG_MATH,( "]\n")); }#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -