pkcs11c.c

来自「支持SSL v2/v3, TLS, PKCS #5, PKCS #7, PKCS」· C语言 代码 · 共 2,203 行 · 第 1/5 页

C
2,203
字号
    pk11_FreeContext(context);    pk11_SetContextByType(session, PK11_ENCRYPT, NULL);    pk11_FreeSession(session);    return (rv == SECSuccess) ? CKR_OK : CKR_DEVICE_ERROR;}/* ************** Crypto Functions:     Decrypt ************************ *//* NSC_DecryptInit initializes a decryption operation. */static CK_RV pk11_DecryptInit( CK_SESSION_HANDLE hSession,  CK_MECHANISM_PTR pMechanism, CK_OBJECT_HANDLE hKey, CK_ATTRIBUTE_TYPE dtype,				PK11ContextType contextType){    PK11Session *session;    PK11Object *key;    PK11Attribute *att;    PK11SessionContext *context;    CK_RC2_CBC_PARAMS *rc2_param;#if NSS_SOFTOKEN_DOES_RC5    CK_RC5_CBC_PARAMS *rc5_param;    SECItem rc5Key;#endif    CK_KEY_TYPE key_type;    CK_RV crv = CKR_OK;    unsigned effectiveKeyLength;    SECKEYLowPrivateKey *privKey;    unsigned char newdeskey[8];    PRBool useNewKey=PR_FALSE;    int t;    session = pk11_SessionFromHandle(hSession);    if (session == NULL) return CKR_SESSION_HANDLE_INVALID;    crv = pk11_InitGeneric(session,&context,contextType,&key,hKey,&key_type,						CKO_PRIVATE_KEY,dtype);    if (crv != CKR_OK) {	pk11_FreeSession(session);	return crv;    }    /*     * now handle each mechanism     */    switch(pMechanism->mechanism) {    case CKM_RSA_PKCS:    case CKM_RSA_X_509:	if (key_type != CKK_RSA) {	    crv = CKR_KEY_TYPE_INCONSISTENT;	    break;	}	context->multi = PR_FALSE;	privKey = pk11_GetPrivKey(key,CKK_RSA);	if (privKey == NULL) {	    crv = CKR_HOST_MEMORY;	    break;	}	context->cipherInfo = privKey;	context->update = (PK11Cipher) (pMechanism->mechanism == CKM_RSA_X_509			? RSA_DecryptRaw : RSA_DecryptBlock);	context->destroy = (context->cipherInfo == key->objectInfo) ?		(PK11Destroy) pk11_Null : (PK11Destroy) pk11_FreePrivKey;	break;    case CKM_RC2_CBC_PAD:	context->doPad = PR_TRUE;	context->blockSize = 8;	/* fall thru */    case CKM_RC2_ECB:    case CKM_RC2_CBC:	if (key_type != CKK_RC2) {	    crv = CKR_KEY_TYPE_INCONSISTENT;	    break;	}	att = pk11_FindAttribute(key,CKA_VALUE);	rc2_param = (CK_RC2_CBC_PARAMS *)pMechanism->pParameter;	effectiveKeyLength = (rc2_param->ulEffectiveBits+7)/8;	context->cipherInfo = RC2_CreateContext((unsigned char*)att->attrib.pValue,		att->attrib.ulValueLen, rc2_param->iv,		 pMechanism->mechanism == CKM_RC2_ECB ? NSS_RC2 :					 NSS_RC2_CBC, effectiveKeyLength);	pk11_FreeAttribute(att);	if (context->cipherInfo == NULL) {	    crv = CKR_HOST_MEMORY;	    break;	}	context->update = (PK11Cipher) RC2_Decrypt;	context->destroy = (PK11Destroy) RC2_DestroyContext;	break;#if NSS_SOFTOKEN_DOES_RC5    case CKM_RC5_CBC_PAD:	context->doPad = PR_TRUE;	/* fall thru */    case CKM_RC5_ECB:    case CKM_RC5_CBC:	if (key_type != CKK_RC5) {	    crv = CKR_KEY_TYPE_INCONSISTENT;	    break;	}	att = pk11_FindAttribute(key,CKA_VALUE);	if (att == NULL) {	    crv = CKR_KEY_HANDLE_INVALID;	    break;	}	rc5_param = (CK_RC5_CBC_PARAMS *)pMechanism->pParameter;	if (context->doPad) {	   context->blockSize = rc5_param->ulWordsize*2;	}	rc5Key.data = (unsigned char*)att->attrib.pValue;	rc5Key.len = att->attrib.ulValueLen;	context->cipherInfo = RC5_CreateContext(&rc5Key,rc5_param->ulRounds,	   rc5_param->ulWordsize,rc5_param->pIv,		 pMechanism->mechanism == CKM_RC5_ECB ? NSS_RC5 : NSS_RC5_CBC);	pk11_FreeAttribute(att);	if (context->cipherInfo == NULL) {	    crv = CKR_HOST_MEMORY;	    break;	}	context->update = (PK11Cipher) RC5_Decrypt;	context->destroy = (PK11Destroy) RC5_DestroyContext;	break;#endif    case CKM_RC4:	if (key_type != CKK_RC4) {	    crv = CKR_KEY_TYPE_INCONSISTENT;	    break;	}	att = pk11_FindAttribute(key,CKA_VALUE);	context->cipherInfo = 	    RC4_CreateContext((unsigned char*)att->attrib.pValue,			      att->attrib.ulValueLen);	pk11_FreeAttribute(att);	if (context->cipherInfo == NULL) {	    crv = CKR_HOST_MEMORY;	    break;	}	context->update = (PK11Cipher) RC4_Decrypt;	context->destroy = (PK11Destroy) RC4_DestroyContext;	break;    case CKM_CDMF_CBC_PAD:	context->doPad = PR_TRUE;	context->blockSize = 8;	/* fall thru */    case CKM_CDMF_ECB:    case CKM_CDMF_CBC:	if (key_type != CKK_CDMF) {	    crv = CKR_KEY_TYPE_INCONSISTENT;	    break;	}	t = (pMechanism->mechanism == CKM_CDMF_ECB) ? NSS_DES : NSS_DES_CBC;	useNewKey = PR_TRUE;	if (crv != CKR_OK) break;	goto finish_des;    case CKM_DES_ECB:	if (key_type != CKK_DES) {	    crv = CKR_KEY_TYPE_INCONSISTENT;	    break;	}	t = NSS_DES;	goto finish_des;    case CKM_DES_CBC_PAD:	context->doPad = PR_TRUE;	context->blockSize = 8;	/* fall thru */    case CKM_DES_CBC:	if (key_type != CKK_DES) {	    crv = CKR_KEY_TYPE_INCONSISTENT;	    break;	}	t = NSS_DES_CBC;	goto finish_des;    case CKM_DES3_ECB:	if ((key_type != CKK_DES2) && (key_type != CKK_DES3)) {	    crv = CKR_KEY_TYPE_INCONSISTENT;	    break;	}	t = NSS_DES_EDE3;	goto finish_des;    case CKM_DES3_CBC_PAD:	context->doPad = PR_TRUE;	context->blockSize = 8;	/* fall thru */    case CKM_DES3_CBC:	if ((key_type != CKK_DES2) && (key_type != CKK_DES3)) {	    crv = CKR_KEY_TYPE_INCONSISTENT;	    break;	}	t = NSS_DES_EDE3_CBC;finish_des:	att = pk11_FindAttribute(key,CKA_VALUE);	if (att == NULL) {	    crv = CKR_KEY_HANDLE_INVALID;	    break;	}	if (useNewKey) {	    crv = pk11_cdmf2des((unsigned char*)att->attrib.pValue,newdeskey);	    if (crv != CKR_OK) {		pk11_FreeAttribute(att);		break;	     }	}	context->cipherInfo = DES_CreateContext(		useNewKey ? newdeskey : (unsigned char*)att->attrib.pValue,		(unsigned char*)pMechanism->pParameter,t, PR_FALSE);	pk11_FreeAttribute(att);	if (context->cipherInfo == NULL) {	    crv = CKR_HOST_MEMORY;	    break;	}	context->update = (PK11Cipher) DES_Decrypt;	context->destroy = (PK11Destroy) DES_DestroyContext;	break;    default:	crv = CKR_MECHANISM_INVALID;	break;    }    pk11_FreeObject(key);    if (crv != CKR_OK) {        pk11_FreeContext(context);	pk11_FreeSession(session);	return crv;    }    pk11_SetContextByType(session, contextType, context);    pk11_FreeSession(session);    return CKR_OK;}/* NSC_DecryptInit initializes a decryption operation. */CK_RV NSC_DecryptInit( CK_SESSION_HANDLE hSession,			 CK_MECHANISM_PTR pMechanism, CK_OBJECT_HANDLE hKey){    return pk11_DecryptInit(hSession,pMechanism,hKey,CKA_DECRYPT,PK11_DECRYPT);}/* NSC_DecryptUpdate continues a multiple-part decryption operation. */CK_RV NSC_DecryptUpdate(CK_SESSION_HANDLE hSession,    CK_BYTE_PTR pEncryptedPart, CK_ULONG ulEncryptedPartLen,    				CK_BYTE_PTR pPart, CK_ULONG_PTR pulPartLen){    PK11SessionContext *context;    unsigned int padoutlen = 0;    unsigned int outlen;    unsigned int maxout = *pulPartLen;    CK_RV crv;    SECStatus rv;    /* make sure we're legal */    crv = pk11_GetContext(hSession,&context,PK11_DECRYPT,PR_TRUE,NULL);    if (crv != CKR_OK) return crv;    if (context->doPad) {	/* first decrypt our saved buffer */	if (context->padDataLength != 0) {    	    rv = (*context->update)(context->cipherInfo, pPart, &padoutlen,		 maxout, context->padBuf, context->blockSize);    	    if (rv != SECSuccess)  return CKR_DEVICE_ERROR;	    pPart += padoutlen;	    maxout -= padoutlen;	}	/* now save the final block for the next decrypt or the final */	PORT_Memcpy(context->padBuf,&pEncryptedPart[ulEncryptedPartLen -				context->blockSize], context->blockSize);	context->padDataLength = context->blockSize;	ulEncryptedPartLen -= context->padDataLength;    }    /* do it: NOTE: this assumes buf size in is >= buf size out! */    rv = (*context->update)(context->cipherInfo,pPart, &outlen,		 maxout, pEncryptedPart, ulEncryptedPartLen);    *pulPartLen = (CK_ULONG) (outlen + padoutlen);    return (rv == SECSuccess)  ? CKR_OK : CKR_DEVICE_ERROR;}/* NSC_DecryptFinal finishes a multiple-part decryption operation. */CK_RV NSC_DecryptFinal(CK_SESSION_HANDLE hSession,    CK_BYTE_PTR pLastPart, CK_ULONG_PTR pulLastPartLen){    PK11Session *session;    PK11SessionContext *context;    unsigned int outlen;    unsigned int maxout = *pulLastPartLen;    CK_RV crv;    SECStatus rv = SECSuccess;    /* make sure we're legal */    crv = pk11_GetContext(hSession,&context,PK11_DECRYPT,PR_TRUE,&session);    if (crv != CKR_OK) return crv;    *pulLastPartLen = 0;    if (context->doPad) {	/* decrypt our saved buffer */	if (context->padDataLength != 0) {	    /* this assumes that pLastPart is big enough to hold the *whole*	     * buffer!!! */    	    rv = (*context->update)(context->cipherInfo, pLastPart, &outlen,		 maxout, context->padBuf, context->blockSize);    	    if (rv == SECSuccess) {		unsigned int padSize = 			    (unsigned int) pLastPart[context->blockSize-1];		*pulLastPartLen = outlen - padSize;	    }	}    }    /* do it */    pk11_SetContextByType(session, PK11_DECRYPT, NULL);    pk11_FreeContext(context);    pk11_FreeSession(session);    return (rv == SECSuccess) ? CKR_OK : CKR_DEVICE_ERROR;}/* NSC_Decrypt decrypts encrypted data in a single part. */CK_RV NSC_Decrypt(CK_SESSION_HANDLE hSession,    CK_BYTE_PTR pEncryptedData,CK_ULONG ulEncryptedDataLen,CK_BYTE_PTR pData,    						CK_ULONG_PTR pulDataLen){    PK11Session *session;    PK11SessionContext *context;    unsigned int outlen;    unsigned int maxoutlen = *pulDataLen;    CK_RV crv;    CK_RV crv2;    SECStatus rv;    /* make sure we're legal */    crv = pk11_GetContext(hSession,&context,PK11_DECRYPT,PR_FALSE,&session);    if (crv != CKR_OK) return crv;    if (context->doPad) {	CK_ULONG finalLen;	/* padding is fairly complicated, have the update and final 	 * code deal with it */        pk11_FreeSession(session);	crv = NSC_DecryptUpdate(hSession,pEncryptedData,ulEncryptedDataLen,							pData, pulDataLen);	if (crv != CKR_OK) *pulDataLen = 0;	maxoutlen -= *pulDataLen;	pData += *pulDataLen;	finalLen = maxoutlen;	crv2 = NSC_DecryptFinal(hSession, pData, &finalLen);	if (crv2 == CKR_OK) { *pulDataLen += finalLen; }	return crv == CKR_OK ? crv2 :crv;    }    rv = (*context->update)(context->cipherInfo, pData, &outlen, maxoutlen, 					pEncryptedData, ulEncryptedDataLen);    *pulDataLen = (CK_ULONG) outlen;    pk11_FreeContext(context);    pk11_SetContextByType(session, PK11_DECRYPT, NULL);    pk11_FreeSession(session);    return (rv == SECSuccess)  ? CKR_OK : CKR_DEVICE_ERROR;}/* ************** Crypto Functions:     Digest (HASH)  ************************ *//* NSC_DigestInit initializes a message-digesting operation. */CK_RV NSC_DigestInit(CK_SESSION_HANDLE hSession,    					CK_MECHANISM_PTR pMechanism){    PK11Session *session;    PK11SessionContext *context;    MD2Context *md2_context;    MD5Context *md5_context;    SHA1Context *sha1_context;    CK_RV crv = CKR_OK;    session = pk11_SessionFromHandle(hSession);    if (session == NULL) return CKR_SESSION_HANDLE_INVALID;    crv = pk11_InitGeneric(session,&context,PK11_HASH,NULL,0,NULL, 0, 0);    if (crv != CKR_OK) {	pk11_FreeSession(session);	return crv;    }    switch(pMechanism->mechanism) {    case CKM_MD2:	md2_context = MD2_NewContext();	context->cipherInfo = (void *)md2_context;	context->cipherInfoLen = MD2_FlattenSize(md2_context);	context->currentMech = CKM_MD2;        if (context->cipherInfo == NULL) {	    crv= CKR_HOST_MEMORY;	    	}	context->hashUpdate = (PK11Hash) MD2_Update;	context->end = (PK11End) MD2_End;	context->destroy = (PK11Destroy) MD2_DestroyContext;	MD2_Begin(md2_context);	break;    case CKM_MD5:	md5_context = MD5_NewContext();	context->cipherInfo = (void *)md5_context;	context->cipherInfoLen = MD5_FlattenSize(md5_context);	context->currentMech = CKM_MD5;        if (context->cipherInfo == NULL) {	    crv= CKR_HOST_MEMORY;	    	}	context->hashUpdate = (PK11Hash) MD5_Update;	context->end = (PK11End) MD5_End;	context->destroy = (PK11Destroy) MD5_DestroyContext;	MD5_Begin(md5_context);	break;    case CKM_SHA_1:	sha1_context = SHA1_NewContext();	context->cipherInfo = (void *)sha1_context;	context->cipherInfoLen = SHA1_FlattenSize(sha1_context);	context->currentMech = CKM_SHA_1;        if (context->cipherInfo == NULL) {	    crv= CKR_HOST_MEMORY;	    break;	}	context->hashUpdate = (PK11Hash) SHA1_Update;	context->end = (PK11End) SHA1_End;	context->destroy = (PK11Destroy) SHA1_DestroyContext;	SHA1_Begin(sha1_context);	break;    default:	crv = CKR_MECHANISM_INVALID;	break;    }    if (crv != CKR_OK) {        pk11_FreeContext(context);	pk11_FreeSession(session);	return crv;    }    pk11_SetContextByType(session, PK11_HASH, context);    pk11_FreeSession(session);    return CKR_OK;}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?