Skip to content

Commit b36591d

Browse files
committed
Refactored additional context parameter processing
Applied RabbitAI suggested fixes
1 parent 6f0d417 commit b36591d

36 files changed

+315
-318
lines changed

.github/workflows/ci.yml

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -76,13 +76,14 @@ jobs:
7676
make check || (find . -name test-suite.log -exec cat {} \; && false)
7777
7878
linux_ossl_35:
79-
name: Linux with OpenSSL 3.5.4
79+
name: Linux with OpenSSL 3.5.5
8080
runs-on: ubuntu-24.04
8181
steps:
8282
- uses: actions/checkout@v4
8383
- name: Prepare
8484
env:
85-
OPENSSL_VERSION: 3.5.4
85+
OPENSSL_VERSION: 3.5.5
86+
OPENSSL_SHA256: "b28c91532a8b65a1f983b4c28b7488174e4a01008e29ce8e69bd789f28bc2a89"
8687
OPENSSL_INSTALL_DIR: /usr/local/openssl-3.5
8788
LDFLAGS: "-Wl,-rpath,/usr/local/openssl-3.5/lib64 -L/usr/local/openssl-3.5/lib64"
8889
PKG_CONFIG_PATH: "/usr/local/openssl-3.5/lib64/pkgconfig"
@@ -91,6 +92,7 @@ jobs:
9192
sudo apt-get install -y libcppunit-dev p11-kit build-essential checkinstall zlib1g-dev sudo autoconf libtool git
9293
# Install OpenSSL 3.5
9394
curl -L -O https://github.com/openssl/openssl/releases/download/openssl-${{ env.OPENSSL_VERSION }}/openssl-${{ env.OPENSSL_VERSION }}.tar.gz
95+
echo "${OPENSSL_SHA256} openssl-${{ env.OPENSSL_VERSION }}.tar.gz" | sha256sum -c -
9496
tar -xf openssl-${{ env.OPENSSL_VERSION }}.tar.gz
9597
cd openssl-${{ env.OPENSSL_VERSION }}
9698
./config shared zlib no-ssl3 no-weak-ssl-ciphers --prefix=${{ env.OPENSSL_INSTALL_DIR }} --openssldir=${{ env.OPENSSL_INSTALL_DIR }}

CMAKE-WIN-NOTES.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ Some options (more can be found in CMakeLists.txt):
5252

5353
-DBUILD_TESTS=ON Compile tests along with libraries
5454
-DENABLE_EDDSA=ON Enable support for EDDSA
55-
-DENABLE_MLDSA=ON Enable support for ML-DSA
55+
-DENABLE_MLDSA=ON Enable support for ML-DSA
5656
-DWITH_MIGRATE=ON Build migration tool
5757
-DWITH_CRYPTO_BACKEND= Select crypto backend (openssl|botan)
5858
-DDISABLE_NON_PAGED_MEMORY=ON Disable non-paged memory for secure storage

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -82,7 +82,7 @@ Options:
8282
--enable-ecc Enable support for ECC (default detect)
8383
--enable-gost Enable support for GOST (default detect)
8484
--enable-eddsa Enable support for EDDSA (default detect)
85-
--enable-mldsa Enable support for ML-DSA (default detect)
85+
--enable-mldsa Enable support for ML-DSA (default detect)
8686
--disable-visibility Disable hidden visibilty link mode [enabled]
8787
--with-crypto-backend Select crypto backend (openssl|botan)
8888
--with-openssl=PATH Specify prefix of path of OpenSSL

src/lib/SoftHSM.cpp

Lines changed: 73 additions & 98 deletions
Original file line numberDiff line numberDiff line change
@@ -62,12 +62,11 @@
6262
#include "DHPrivateKey.h"
6363
#include "GOSTPublicKey.h"
6464
#include "GOSTPrivateKey.h"
65-
#ifdef WITH_ML_DSA
6665
#include "MLDSAParameters.h"
6766
#include "MLDSAPublicKey.h"
6867
#include "MLDSAPrivateKey.h"
6968
#include "MLDSAUtil.h"
70-
#endif
69+
7170
#include "cryptoki.h"
7271
#include "SoftHSM.h"
7372
#include "osmutex.h"
@@ -948,6 +947,7 @@ CK_RV SoftHSM::C_GetMechanismInfo(CK_SLOT_ID slotID, CK_MECHANISM_TYPE type, CK_
948947
unsigned long eddsaMinSize = 0, eddsaMaxSize = 0;
949948
#endif
950949
#ifdef WITH_ML_DSA
950+
// ML‑DSA min/max sizes are bytes (PKCS#11 v3.2).
951951
unsigned long mldsaMinSize = 0, mldsaMaxSize = 0;
952952
#endif
953953

@@ -1050,15 +1050,13 @@ CK_RV SoftHSM::C_GetMechanismInfo(CK_SLOT_ID slotID, CK_MECHANISM_TYPE type, CK_
10501050
#endif
10511051
#ifdef WITH_ML_DSA
10521052
AsymmetricAlgorithm* mldsa = CryptoFactory::i()->getAsymmetricAlgorithm(AsymAlgo::MLDSA);
1053-
if (mldsa != NULL)
1054-
{
1055-
mldsaMinSize = mldsa->getMinKeySize();
1056-
mldsaMaxSize = mldsa->getMaxKeySize();
1057-
}
1058-
else
1053+
if (mldsa == NULL)
10591054
{
10601055
return CKR_GENERAL_ERROR;
10611056
}
1057+
// ML‑DSA min/max sizes are bytes (PKCS#11 v3.2).
1058+
mldsaMinSize = mldsa->getMinKeySize();
1059+
mldsaMaxSize = mldsa->getMaxKeySize();
10621060
CryptoFactory::i()->recycleAsymmetricAlgorithm(mldsa);
10631061
#endif
10641062
pInfo->flags = 0; // initialize flags
@@ -1353,6 +1351,7 @@ CK_RV SoftHSM::C_GetMechanismInfo(CK_SLOT_ID slotID, CK_MECHANISM_TYPE type, CK_
13531351
#endif
13541352
#ifdef WITH_ML_DSA
13551353
case CKM_ML_DSA_KEY_PAIR_GEN:
1354+
// ML‑DSA min/max sizes are bytes (PKCS#11 v3.2).
13561355
pInfo->ulMinKeySize = mldsaMinSize;
13571356
pInfo->ulMaxKeySize = mldsaMaxSize;
13581357
pInfo->flags = CKF_GENERATE_KEY_PAIR;
@@ -4195,7 +4194,9 @@ CK_RV SoftHSM::AsymSignInit(CK_SESSION_HANDLE hSession, CK_MECHANISM_PTR pMechan
41954194
#endif
41964195
#ifdef WITH_ML_DSA
41974196
bool isMLDSA = false;
4198-
SIGN_ADDITIONAL_CONTEXT additionalContext = {};
4197+
SIGN_ADDITIONAL_CONTEXT mldsaParam;
4198+
void* additionalContext = NULL;
4199+
size_t additionalContextLen = 0;
41994200
#endif
42004201
switch(pMechanism->mechanism) {
42014202
case CKM_RSA_PKCS:
@@ -4468,50 +4469,31 @@ CK_RV SoftHSM::AsymSignInit(CK_SESSION_HANDLE hSession, CK_MECHANISM_PTR pMechan
44684469
mechanism = AsymMech::MLDSA;
44694470
bAllowMultiPartOp = false;
44704471
isMLDSA = true;
4471-
if (pMechanism->pParameter != NULL_PTR) {
4472-
if(pMechanism->ulParameterLen != sizeof(CK_SIGN_ADDITIONAL_CONTEXT))
4472+
if (pMechanism->pParameter == NULL_PTR)
4473+
{
4474+
if (pMechanism->ulParameterLen != 0)
44734475
{
44744476
ERROR_MSG("Invalid parameters");
44754477
return CKR_ARGUMENTS_BAD;
44764478
}
4477-
else
4479+
}
4480+
else
4481+
{
4482+
if (pMechanism->ulParameterLen != sizeof(CK_SIGN_ADDITIONAL_CONTEXT))
44784483
{
4479-
const CK_SIGN_ADDITIONAL_CONTEXT* ckSignAdditionalContext = (const CK_SIGN_ADDITIONAL_CONTEXT*) pMechanism->pParameter;
4480-
if (ckSignAdditionalContext->ulContextLen > 255)
4481-
{
4482-
ERROR_MSG("ML-DSA: Invalid parameters, context length > 255");
4483-
return CKR_ARGUMENTS_BAD;
4484-
}
4485-
4486-
// Always initialize context fields
4487-
additionalContext.contextAsChar = NULL;
4488-
additionalContext.contextLength = 0;
4489-
if (ckSignAdditionalContext->ulContextLen > 0)
4490-
{
4491-
if (ckSignAdditionalContext->pContext == NULL)
4492-
{
4493-
ERROR_MSG("ML-DSA: Invalid parameters, pContext is NULL");
4494-
return CKR_ARGUMENTS_BAD;
4495-
}
4496-
additionalContext.contextAsChar = (unsigned char*) ckSignAdditionalContext->pContext;
4497-
additionalContext.contextLength = ckSignAdditionalContext->ulContextLen;
4498-
}
4499-
switch (ckSignAdditionalContext->hedgeVariant) {
4500-
case CKH_HEDGE_REQUIRED:
4501-
additionalContext.hedgeType = Hedge::HEDGE_REQUIRED;
4502-
break;
4503-
case CKH_DETERMINISTIC_REQUIRED:
4504-
additionalContext.hedgeType = Hedge::DETERMINISTIC_REQUIRED;
4505-
break;
4506-
case CKH_HEDGE_PREFERRED:
4507-
// Per PKCS11v3.2 section 6.67.5
4508-
// "If no parameter is supplied the hedgeVariant will be CKH_HEDGE_PREFERRED"
4509-
default:
4510-
additionalContext.hedgeType = Hedge::HEDGE_PREFERRED;
4511-
}
4512-
param = &additionalContext;
4513-
paramLen = sizeof(SIGN_ADDITIONAL_CONTEXT);
4484+
ERROR_MSG("Invalid parameters");
4485+
return CKR_ARGUMENTS_BAD;
45144486
}
4487+
CK_SIGN_ADDITIONAL_CONTEXT* ckSignAdditionalContext = (CK_SIGN_ADDITIONAL_CONTEXT*) pMechanism->pParameter;
4488+
CK_RV rv = MLDSAUtil::setHedge(ckSignAdditionalContext->hedgeVariant, &mldsaParam);
4489+
if (rv != CKR_OK) {
4490+
ERROR_MSG("Invalid parameters");
4491+
return CKR_ARGUMENTS_BAD;
4492+
}
4493+
additionalContext = ckSignAdditionalContext->pContext;
4494+
additionalContextLen = ckSignAdditionalContext->ulContextLen;
4495+
param = &mldsaParam;
4496+
paramLen = sizeof(mldsaParam);
45154497
}
45164498
break;
45174499
#endif
@@ -4664,6 +4646,9 @@ CK_RV SoftHSM::AsymSignInit(CK_SESSION_HANDLE hSession, CK_MECHANISM_PTR pMechan
46644646
session->setAsymmetricCryptoOp(asymCrypto);
46654647
session->setMechanism(mechanism);
46664648
session->setParameters(param, paramLen);
4649+
#ifdef WITH_ML_DSA
4650+
session->setAdditionalContext(additionalContext, additionalContextLen);
4651+
#endif
46674652
session->setAllowMultiPartOp(bAllowMultiPartOp);
46684653
session->setAllowSinglePartOp(true);
46694654
session->setPrivateKey(privateKey);
@@ -4745,6 +4730,8 @@ static CK_RV AsymSign(Session* session, CK_BYTE_PTR pData, CK_ULONG ulDataLen, C
47454730
PrivateKey* privateKey = session->getPrivateKey();
47464731
size_t paramLen;
47474732
void* param = session->getParameters(paramLen);
4733+
size_t additionalContextLen;
4734+
void* additionalContext = session->getAdditionalContext(additionalContextLen);
47484735
if (asymCrypto == NULL || !session->getAllowSinglePartOp() || privateKey == NULL)
47494736
{
47504737
session->resetOp();
@@ -4794,7 +4781,7 @@ static CK_RV AsymSign(Session* session, CK_BYTE_PTR pData, CK_ULONG ulDataLen, C
47944781
return CKR_GENERAL_ERROR;
47954782
}
47964783
}
4797-
else if (!asymCrypto->sign(privateKey,data,signature,mechanism,param,paramLen))
4784+
else if (!asymCrypto->sign(privateKey,data,signature,mechanism,param,paramLen,additionalContext,additionalContextLen))
47984785
{
47994786
session->resetOp();
48004787
return CKR_GENERAL_ERROR;
@@ -5275,7 +5262,9 @@ CK_RV SoftHSM::AsymVerifyInit(CK_SESSION_HANDLE hSession, CK_MECHANISM_PTR pMech
52755262
#endif
52765263
#ifdef WITH_ML_DSA
52775264
bool isMLDSA = false;
5278-
SIGN_ADDITIONAL_CONTEXT additionalContext = {};
5265+
SIGN_ADDITIONAL_CONTEXT mldsaParam;
5266+
void* additionalContext = NULL;
5267+
size_t additionalContextLen = 0;
52795268
#endif
52805269
switch(pMechanism->mechanism) {
52815270
case CKM_RSA_PKCS:
@@ -5546,48 +5535,31 @@ CK_RV SoftHSM::AsymVerifyInit(CK_SESSION_HANDLE hSession, CK_MECHANISM_PTR pMech
55465535
mechanism = AsymMech::MLDSA;
55475536
bAllowMultiPartOp = false;
55485537
isMLDSA = true;
5549-
if (pMechanism->pParameter != NULL_PTR) {
5550-
if(pMechanism->ulParameterLen != sizeof(CK_SIGN_ADDITIONAL_CONTEXT))
5538+
if (pMechanism->pParameter == NULL_PTR)
5539+
{
5540+
if (pMechanism->ulParameterLen != 0)
55515541
{
55525542
ERROR_MSG("Invalid parameters");
55535543
return CKR_ARGUMENTS_BAD;
55545544
}
5555-
else
5545+
}
5546+
else
5547+
{
5548+
if(pMechanism->ulParameterLen != sizeof(CK_SIGN_ADDITIONAL_CONTEXT))
55565549
{
5557-
const CK_SIGN_ADDITIONAL_CONTEXT* ckSignAdditionalContext = (const CK_SIGN_ADDITIONAL_CONTEXT*) pMechanism->pParameter;
5558-
if (ckSignAdditionalContext->ulContextLen > 255) {
5559-
ERROR_MSG("ML-DSA: Invalid parameters, context length > 255");
5560-
return CKR_ARGUMENTS_BAD;
5561-
}
5562-
// Always initialize context fields
5563-
additionalContext.contextAsChar = NULL;
5564-
additionalContext.contextLength = 0;
5565-
if (ckSignAdditionalContext->ulContextLen > 0) {
5566-
if (ckSignAdditionalContext->pContext == NULL)
5567-
{
5568-
ERROR_MSG("ML-DSA: Invalid parameters, pContext is NULL");
5569-
return CKR_ARGUMENTS_BAD;
5570-
}
5571-
additionalContext.contextAsChar = (unsigned char*) ckSignAdditionalContext->pContext;
5572-
additionalContext.contextLength = ckSignAdditionalContext->ulContextLen;
5573-
}
5574-
5575-
switch (ckSignAdditionalContext->hedgeVariant) {
5576-
case CKH_HEDGE_REQUIRED:
5577-
additionalContext.hedgeType = Hedge::HEDGE_REQUIRED;
5578-
break;
5579-
case CKH_DETERMINISTIC_REQUIRED:
5580-
additionalContext.hedgeType = Hedge::DETERMINISTIC_REQUIRED;
5581-
break;
5582-
// Per PKCS11v3.2 section 6.67.5
5583-
// "If no parameter is supplied the hedgeVariant will be CKH_HEDGE_PREFERRED"
5584-
case CKH_HEDGE_PREFERRED:
5585-
default:
5586-
additionalContext.hedgeType = Hedge::HEDGE_PREFERRED;
5587-
}
5588-
param = &additionalContext;
5589-
paramLen = sizeof(SIGN_ADDITIONAL_CONTEXT);
5550+
ERROR_MSG("Invalid parameters");
5551+
return CKR_ARGUMENTS_BAD;
5552+
}
5553+
CK_SIGN_ADDITIONAL_CONTEXT* ckSignAdditionalContext = (CK_SIGN_ADDITIONAL_CONTEXT*) pMechanism->pParameter;
5554+
CK_RV rv = MLDSAUtil::setHedge(ckSignAdditionalContext->hedgeVariant, &mldsaParam);
5555+
if (rv != CKR_OK) {
5556+
ERROR_MSG("Invalid parameters");
5557+
return CKR_ARGUMENTS_BAD;
55905558
}
5559+
additionalContext = ckSignAdditionalContext->pContext;
5560+
additionalContextLen = ckSignAdditionalContext->ulContextLen;
5561+
param = &mldsaParam;
5562+
paramLen = sizeof(mldsaParam);
55915563
}
55925564
break;
55935565
#endif
@@ -5734,6 +5706,9 @@ CK_RV SoftHSM::AsymVerifyInit(CK_SESSION_HANDLE hSession, CK_MECHANISM_PTR pMech
57345706
session->setAsymmetricCryptoOp(asymCrypto);
57355707
session->setMechanism(mechanism);
57365708
session->setParameters(param, paramLen);
5709+
#ifdef WITH_ML_DSA
5710+
session->setAdditionalContext(additionalContext, additionalContextLen);
5711+
#endif
57375712
session->setAllowMultiPartOp(bAllowMultiPartOp);
57385713
session->setAllowSinglePartOp(true);
57395714
session->setPublicKey(publicKey);
@@ -5803,6 +5778,8 @@ static CK_RV AsymVerify(Session* session, CK_BYTE_PTR pData, CK_ULONG ulDataLen,
58035778
PublicKey* publicKey = session->getPublicKey();
58045779
size_t paramLen;
58055780
void* param = session->getParameters(paramLen);
5781+
size_t additionalContextLen;
5782+
void* additionalContext = session->getAdditionalContext(additionalContextLen);
58065783
if (asymCrypto == NULL || !session->getAllowSinglePartOp() || publicKey == NULL)
58075784
{
58085785
session->resetOp();
@@ -5842,7 +5819,7 @@ static CK_RV AsymVerify(Session* session, CK_BYTE_PTR pData, CK_ULONG ulDataLen,
58425819
return CKR_SIGNATURE_INVALID;
58435820
}
58445821
}
5845-
else if (!asymCrypto->verify(publicKey,data,signature,mechanism,param,paramLen))
5822+
else if (!asymCrypto->verify(publicKey,data,signature,mechanism,param,paramLen,additionalContext,additionalContextLen))
58465823
{
58475824
session->resetOp();
58485825
return CKR_SIGNATURE_INVALID;
@@ -7149,7 +7126,7 @@ CK_RV SoftHSM::UnwrapKeySym
71497126
SymWrap::Type mode = SymWrap::Unknown;
71507127
size_t bb = 8;
71517128
size_t blocksize = 0;
7152-
7129+
71537130
switch(pMechanism->mechanism) {
71547131
#ifdef HAVE_AES_KEY_WRAP
71557132
case CKM_AES_KEY_WRAP:
@@ -7195,14 +7172,14 @@ CK_RV SoftHSM::UnwrapKeySym
71957172
ByteString iv;
71967173
ByteString decryptedFinal;
71977174
CK_RV rv = CKR_OK;
7198-
7175+
71997176
switch(pMechanism->mechanism) {
72007177

72017178
case CKM_AES_CBC_PAD:
72027179
case CKM_DES3_CBC_PAD:
72037180
iv.resize(blocksize);
72047181
memcpy(&iv[0], pMechanism->pParameter, blocksize);
7205-
7182+
72067183
if (!cipher->decryptInit(unwrappingkey, SymMode::CBC, iv, false))
72077184
{
72087185
cipher->recycleKey(unwrappingkey);
@@ -7231,7 +7208,7 @@ CK_RV SoftHSM::UnwrapKeySym
72317208
return CKR_GENERAL_ERROR; // TODO should be another error
72327209
}
72337210
break;
7234-
7211+
72357212
default:
72367213
// Unwrap the key
72377214
rv = CKR_OK;
@@ -7522,7 +7499,7 @@ CK_RV SoftHSM::C_UnwrapKey
75227499
pMechanism->ulParameterLen != 8)
75237500
return CKR_ARGUMENTS_BAD;
75247501
break;
7525-
7502+
75267503
default:
75277504
return CKR_MECHANISM_INVALID;
75287505
}
@@ -7566,7 +7543,7 @@ CK_RV SoftHSM::C_UnwrapKey
75667543
if (pMechanism->mechanism == CKM_DES3_CBC && (unwrapKey->getUnsignedLongValue(CKA_KEY_TYPE, CKK_VENDOR_DEFINED) != CKK_DES2 ||
75677544
unwrapKey->getUnsignedLongValue(CKA_KEY_TYPE, CKK_VENDOR_DEFINED) != CKK_DES3))
75687545
return CKR_WRAPPING_KEY_TYPE_INCONSISTENT;
7569-
7546+
75707547
// Check if the unwrapping key can be used for unwrapping
75717548
if (unwrapKey->getBooleanValue(CKA_UNWRAP, false) == false)
75727549
return CKR_KEY_FUNCTION_NOT_PERMITTED;
@@ -8377,11 +8354,11 @@ CK_RV SoftHSM::generateAES
83778354
if (rv == CKR_OK)
83788355
{
83798356
OSObject* osobject = (OSObject*)handleManager->getObject(*phKey);
8380-
if (osobject == NULL_PTR || !osobject->isValid())
8357+
if (osobject == NULL_PTR || !osobject->isValid())
83818358
{
83828359
rv = CKR_FUNCTION_FAILED;
8383-
}
8384-
else if (osobject->startTransaction())
8360+
}
8361+
else if (osobject->startTransaction())
83858362
{
83868363
bool bOK = true;
83878364

@@ -10209,7 +10186,7 @@ CK_RV SoftHSM::generateMLDSA
1020910186

1021010187
// The parameters must be specified to be able to generate a key pair.
1021110188
if (paramSet == 0) {
10212-
INFO_MSG("Missing parameter(s) in pPublicKeyTemplate");
10189+
INFO_MSG("Missing parameter(s) CKA_PARAMETER_SET in pPublicKeyTemplate");
1021310190
return CKR_TEMPLATE_INCOMPLETE;
1021410191
}
1021510192

@@ -13150,8 +13127,6 @@ CK_RV SoftHSM::getEDPublicKey(EDPublicKey* publicKey, Token* token, OSObject* ke
1315013127
return CKR_OK;
1315113128
}
1315213129

13153-
13154-
1315513130
CK_RV SoftHSM::getDHPrivateKey(DHPrivateKey* privateKey, Token* token, OSObject* key)
1315613131
{
1315713132
if (privateKey == NULL) return CKR_ARGUMENTS_BAD;

0 commit comments

Comments
 (0)