Skip to content

Commit

Permalink
Update PKCS#1 v1.5 padding flags
Browse files Browse the repository at this point in the history
  • Loading branch information
xhanulik authored and Jakuje committed Feb 5, 2024
1 parent df58bfc commit d732681
Show file tree
Hide file tree
Showing 7 changed files with 48 additions and 41 deletions.
15 changes: 10 additions & 5 deletions src/libopensc/padding.c
Original file line number Diff line number Diff line change
Expand Up @@ -613,7 +613,7 @@ int sc_pkcs1_encode(sc_context_t *ctx, unsigned long flags,
pad_algo = SC_ALGORITHM_RSA_PAD_NONE;
sc_log(ctx, "hash algorithm 0x%X, pad algorithm 0x%X", hash_algo, pad_algo);

if ((pad_algo == SC_ALGORITHM_RSA_PAD_PKCS1 || pad_algo == SC_ALGORITHM_RSA_PAD_NONE) &&
if ((pad_algo == SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 || pad_algo == SC_ALGORITHM_RSA_PAD_NONE) &&
hash_algo != SC_ALGORITHM_RSA_HASH_NONE) {
i = sc_pkcs1_add_digest_info_prefix(hash_algo, in, in_len, out, &tmp_len);
if (i != SC_SUCCESS) {
Expand All @@ -632,7 +632,7 @@ int sc_pkcs1_encode(sc_context_t *ctx, unsigned long flags,
memcpy(out, tmp, tmp_len);
*out_len = tmp_len;
LOG_FUNC_RETURN(ctx, SC_SUCCESS);
case SC_ALGORITHM_RSA_PAD_PKCS1:
case SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01:
/* add pkcs1 bt01 padding */
rv = sc_pkcs1_add_01_padding(tmp, tmp_len, out, out_len, mod_len);
LOG_FUNC_RETURN(ctx, rv);
Expand Down Expand Up @@ -718,11 +718,16 @@ int sc_get_encoding_flags(sc_context_t *ctx,
*sflags = SC_ALGORITHM_RSA_PAD_NONE;
*pflags = iflags;

} else if ((caps & (SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_NONE)) &&
(iflags & SC_ALGORITHM_RSA_PAD_PKCS1)) {
} else if ((caps & (SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_NONE)) &&
(iflags & SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01)) {
/* A corner case - the card can partially do PKCS1, if we prepend the
* DigestInfo bit it will do the rest. */
*sflags = SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_NONE;
*sflags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_NONE;
*pflags = iflags & SC_ALGORITHM_RSA_HASHES;

} else if ((caps & (SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02 | SC_ALGORITHM_RSA_HASH_NONE)) &&
(iflags & SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02)) {
*sflags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02 | SC_ALGORITHM_RSA_HASH_NONE;
*pflags = iflags & SC_ALGORITHM_RSA_HASHES;

} else if ((iflags & SC_ALGORITHM_AES) == SC_ALGORITHM_AES) { /* TODO: seems like this constant does not belong to the same set of flags used form asymmetric algos. Fix this! */
Expand Down
10 changes: 5 additions & 5 deletions src/libopensc/pkcs15-sec.c
Original file line number Diff line number Diff line change
Expand Up @@ -307,7 +307,7 @@ int sc_pkcs15_decipher(struct sc_pkcs15_card *p15card,
LOG_TEST_RET(ctx, r, "use_key() failed");

/* Strip any padding */
if (pad_flags & SC_ALGORITHM_RSA_PAD_PKCS1) {
if (pad_flags & SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02) {
unsigned int s = r;
unsigned int key_size = (unsigned int)alg_info->key_length;
r = sc_pkcs1_strip_02_padding_constant_time(ctx, key_size / 8, out, s, out, &s);
Expand Down Expand Up @@ -693,10 +693,10 @@ int sc_pkcs15_compute_signature(struct sc_pkcs15_card *p15card,
* succeed by stripping padding if the card only offers higher-level
* signature operations. The only thing we can strip is the DigestInfo
* block from PKCS1 padding. */
if ((flags == (SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_NONE)) &&
!(alg_info->flags & SC_ALGORITHM_RSA_RAW) &&
!(alg_info->flags & SC_ALGORITHM_RSA_HASH_NONE) &&
(alg_info->flags & SC_ALGORITHM_RSA_PAD_PKCS1)) {
if ((flags == (SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_NONE)) &&
!(alg_info->flags & SC_ALGORITHM_RSA_RAW) &&
!(alg_info->flags & SC_ALGORITHM_RSA_HASH_NONE) &&
(alg_info->flags & SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01)) {
unsigned int algo;
size_t tmplen = buflen;

Expand Down
8 changes: 4 additions & 4 deletions src/minidriver/minidriver.c
Original file line number Diff line number Diff line change
Expand Up @@ -4675,9 +4675,9 @@ DWORD WINAPI CardRSADecrypt(__in PCARD_DATA pCardData,
}
}
}
else if (alg_info->flags & SC_ALGORITHM_RSA_PAD_PKCS1) {
else if (alg_info->flags & SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02) {
logprintf(pCardData, 2, "sc_pkcs15_decipher: using RSA_PAD_PKCS1 mechanism\n");
r = sc_pkcs15_decipher(vs->p15card, pkey, opt_crypt_flags | SC_ALGORITHM_RSA_PAD_PKCS1,
r = sc_pkcs15_decipher(vs->p15card, pkey, opt_crypt_flags | SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02,
pbuf, pInfo->cbData, pbuf2, pInfo->cbData, NULL);
logprintf(pCardData, 2, "sc_pkcs15_decipher returned %d\n", r);
if (r > 0) {
Expand Down Expand Up @@ -4844,7 +4844,7 @@ DWORD WINAPI CardSignData(__in PCARD_DATA pCardData, __inout PCARD_SIGNING_INFO
* padding and use the value in aiHashAlg. */
logprintf(pCardData, 3, "CARD_PADDING_INFO_PRESENT not set\n");

opt_crypt_flags = SC_ALGORITHM_RSA_PAD_PKCS1; /* turn off later if key is EC */
opt_crypt_flags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01; /* turn off later if key is EC */
if (hashAlg == CALG_MD5)
opt_crypt_flags |= SC_ALGORITHM_RSA_HASH_MD5;
else if (hashAlg == CALG_SHA1)
Expand All @@ -4871,7 +4871,7 @@ DWORD WINAPI CardSignData(__in PCARD_DATA pCardData, __inout PCARD_SIGNING_INFO
break;

case CARD_PADDING_PKCS1:
opt_crypt_flags = SC_ALGORITHM_RSA_PAD_PKCS1;
opt_crypt_flags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01;
BCRYPT_PKCS1_PADDING_INFO *pkcs1_pinf = (BCRYPT_PKCS1_PADDING_INFO *)pInfo->pPaddingInfo;

if (!pkcs1_pinf->pszAlgId || wcscmp(pkcs1_pinf->pszAlgId, L"SHAMD5") == 0) {
Expand Down
20 changes: 10 additions & 10 deletions src/pkcs11/framework-pkcs15.c
Original file line number Diff line number Diff line change
Expand Up @@ -4289,28 +4289,28 @@ pkcs15_prkey_sign(struct sc_pkcs11_session *session, void *obj,

switch (pMechanism->mechanism) {
case CKM_RSA_PKCS:
flags = SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_NONE;
flags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_NONE;
break;
case CKM_MD5_RSA_PKCS:
flags = SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_MD5;
flags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_MD5;
break;
case CKM_SHA1_RSA_PKCS:
flags = SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_SHA1;
flags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_SHA1;
break;
case CKM_SHA224_RSA_PKCS:
flags = SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_SHA224;
flags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_SHA224;
break;
case CKM_SHA256_RSA_PKCS:
flags = SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_SHA256;
flags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_SHA256;
break;
case CKM_SHA384_RSA_PKCS:
flags = SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_SHA384;
flags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_SHA384;
break;
case CKM_SHA512_RSA_PKCS:
flags = SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_SHA512;
flags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_SHA512;
break;
case CKM_RIPEMD160_RSA_PKCS:
flags = SC_ALGORITHM_RSA_PAD_PKCS1 | SC_ALGORITHM_RSA_HASH_RIPEMD160;
flags = SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01 | SC_ALGORITHM_RSA_HASH_RIPEMD160;
break;
case CKM_RSA_X_509:
flags = SC_ALGORITHM_RSA_RAW;
Expand Down Expand Up @@ -4485,7 +4485,7 @@ pkcs15_prkey_unwrap(struct sc_pkcs11_session *session, void *obj,
/* Select the proper padding mechanism */
switch (pMechanism->mechanism) {
case CKM_RSA_PKCS:
flags |= SC_ALGORITHM_RSA_PAD_PKCS1;
flags |= SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02;
break;
case CKM_RSA_X_509:
flags |= SC_ALGORITHM_RSA_RAW;
Expand Down Expand Up @@ -4562,7 +4562,7 @@ pkcs15_prkey_decrypt(struct sc_pkcs11_session *session, void *obj,
/* Select the proper padding mechanism */
switch (pMechanism->mechanism) {
case CKM_RSA_PKCS:
flags |= SC_ALGORITHM_RSA_PAD_PKCS1;
flags |= SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02;
break;
case CKM_RSA_X_509:
flags |= SC_ALGORITHM_RSA_RAW;
Expand Down
4 changes: 2 additions & 2 deletions src/tests/fuzzing/fuzz_pkcs15_reader.c
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size)
size_t i;

int decipher_flags[] = {SC_ALGORITHM_RSA_RAW,
SC_ALGORITHM_RSA_PAD_PKCS1, SC_ALGORITHM_RSA_PAD_ANSI,
SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02, SC_ALGORITHM_RSA_PAD_ANSI,
SC_ALGORITHM_RSA_PAD_ISO9796};
for (i = 0; i < sizeof decipher_flags/sizeof *decipher_flags; i++) {
sc_pkcs15_decipher(p15card, obj, decipher_flags[i],
Expand Down Expand Up @@ -96,7 +96,7 @@ int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size)
}

int signature_flags[] = {SC_ALGORITHM_RSA_RAW,
SC_ALGORITHM_RSA_PAD_PKCS1, SC_ALGORITHM_RSA_PAD_ANSI,
SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01, SC_ALGORITHM_RSA_PAD_ANSI,
SC_ALGORITHM_RSA_PAD_ISO9796,
SC_ALGORITHM_RSA_PAD_PSS|SC_ALGORITHM_MGF1_SHA1,
SC_ALGORITHM_RSA_PAD_PSS|SC_ALGORITHM_MGF1_SHA256,
Expand Down
28 changes: 15 additions & 13 deletions src/tools/opensc-tool.c
Original file line number Diff line number Diff line change
Expand Up @@ -578,19 +578,21 @@ static int list_algorithms(void)
{ 0, NULL }
};
const id2str_t rsa_flag_names[] = {
{ SC_ALGORITHM_RSA_PAD_PKCS1, "pkcs1" },
{ SC_ALGORITHM_RSA_PAD_ANSI, "ansi" },
{ SC_ALGORITHM_RSA_PAD_PSS, "pss" },
{ SC_ALGORITHM_RSA_PAD_OAEP, "oaep" },
{ SC_ALGORITHM_RSA_PAD_ISO9796, "iso9796" },
{ SC_ALGORITHM_RSA_HASH_SHA1, "sha1" },
{ SC_ALGORITHM_RSA_HASH_MD5, "MD5" },
{ SC_ALGORITHM_RSA_HASH_MD5_SHA1, "md5-sha1" },
{ SC_ALGORITHM_RSA_HASH_RIPEMD160, "ripemd160" },
{ SC_ALGORITHM_RSA_HASH_SHA256, "sha256" },
{ SC_ALGORITHM_RSA_HASH_SHA384, "sha384" },
{ SC_ALGORITHM_RSA_HASH_SHA512, "sha512" },
{ SC_ALGORITHM_RSA_HASH_SHA224, "sha224" },
{ SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01, "pkcs1-type1" },
{ SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02, "pkcs1-type2" },
{ SC_ALGORITHM_RSA_PAD_PKCS1, "pkcs1" },
{ SC_ALGORITHM_RSA_PAD_ANSI, "ansi" },
{ SC_ALGORITHM_RSA_PAD_PSS, "pss" },
{ SC_ALGORITHM_RSA_PAD_OAEP, "oaep" },
{ SC_ALGORITHM_RSA_PAD_ISO9796, "iso9796" },
{ SC_ALGORITHM_RSA_HASH_SHA1, "sha1" },
{ SC_ALGORITHM_RSA_HASH_MD5, "MD5" },
{ SC_ALGORITHM_RSA_HASH_MD5_SHA1, "md5-sha1" },
{ SC_ALGORITHM_RSA_HASH_RIPEMD160, "ripemd160" },
{ SC_ALGORITHM_RSA_HASH_SHA256, "sha256" },
{ SC_ALGORITHM_RSA_HASH_SHA384, "sha384" },
{ SC_ALGORITHM_RSA_HASH_SHA512, "sha512" },
{ SC_ALGORITHM_RSA_HASH_SHA224, "sha224" },
{ 0, NULL }
};
// clang-format on
Expand Down
4 changes: 2 additions & 2 deletions src/tools/pkcs15-crypt.c
Original file line number Diff line number Diff line change
Expand Up @@ -227,7 +227,7 @@ static int sign(struct sc_pkcs15_object *obj)
return 2;
len = sizeof(out);
if (obj->type == SC_PKCS15_TYPE_PRKEY_RSA
&& !(opt_crypt_flags & SC_ALGORITHM_RSA_PAD_PKCS1)
&& !(opt_crypt_flags & SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_01)
&& (size_t)c != key->modulus_length/8) {
fprintf(stderr, "Input has to be exactly %lu bytes, when using no padding.\n",
(unsigned long) key->modulus_length/8);
Expand Down Expand Up @@ -286,7 +286,7 @@ static int decipher(struct sc_pkcs15_object *obj)
return SC_ERROR_NOT_SUPPORTED;
}

r = sc_pkcs15_decipher(p15card, obj, opt_crypt_flags & SC_ALGORITHM_RSA_PAD_PKCS1, buf, c, out, len, NULL);
r = sc_pkcs15_decipher(p15card, obj, opt_crypt_flags & SC_ALGORITHM_RSA_PAD_PKCS1_TYPE_02, buf, c, out, len, NULL);
if (r < 0) {
fprintf(stderr, "Decrypt failed: %s\n", sc_strerror(r));
return 1;
Expand Down

0 comments on commit d732681

Please sign in to comment.