Skip to content

Commit 6c7eb81

Browse files
Add some missing tests
- Interrupting a Digest operation - Interrupting a Verify operation - Signing with CKA_ALWAYS_AUTHENTICATE
1 parent f63a59a commit 6c7eb81

3 files changed

Lines changed: 110 additions & 29 deletions

File tree

pkcs11/_pkcs11.pyx

Lines changed: 10 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -775,9 +775,8 @@ cdef class DigestOperation(OperationWithBinaryOutput):
775775
def _finalize(self, silent=False):
776776
cdef Session session = self.session
777777
if self.active:
778-
self.active = False
779-
session.operation_lock.release()
780778
self.execute_resizing_output(session.funclist.C_DigestFinal)
779+
super()._finalize(silent=silent)
781780

782781

783782
def merge_templates(default_template, *user_templates):
@@ -1326,9 +1325,7 @@ class GenerateWithParametersMixin(types.DomainParameters):
13261325
raise ArgumentsBad("No default capabilities for this key "
13271326
"type. Please specify `capabilities`.")
13281327

1329-
mech = MechanismWithParam(
1330-
self.key_type, DEFAULT_GENERATE_MECHANISMS,
1331-
mechanism, mechanism_param)
1328+
mech = MechanismWithParam(self.key_type, DEFAULT_GENERATE_MECHANISMS, mechanism, mechanism_param)
13321329

13331330
# Build attributes
13341331
public_template_ = session.attribute_mapper.public_key_template(
@@ -1418,9 +1415,8 @@ cdef class KeyOperation(OperationWithBinaryOutput):
14181415

14191416
def _finalize(self, silent=False):
14201417
if self.active:
1421-
self.active = False
1422-
self.session.operation_lock.release()
14231418
self._cancel_operation(silent)
1419+
super()._finalize(silent=silent)
14241420

14251421

14261422
cdef class DataCryptOperation(KeyOperation):
@@ -1487,9 +1483,7 @@ class EncryptMixin(types.EncryptMixin):
14871483

14881484
def __encrypt_operation(self, mechanism, mechanism_param, buffer_size):
14891485

1490-
mech = MechanismWithParam(
1491-
self.key_type, DEFAULT_ENCRYPT_MECHANISMS,
1492-
mechanism, mechanism_param)
1486+
mech = MechanismWithParam(self.key_type, DEFAULT_ENCRYPT_MECHANISMS, mechanism, mechanism_param)
14931487

14941488
return DataCryptOperation.setup_encrypt(self.session, mech, self.handle, buffer_size)
14951489

@@ -1522,9 +1516,7 @@ class DecryptMixin(types.DecryptMixin):
15221516

15231517
def __decrypt_operation(self, mechanism, mechanism_param, buffer_size):
15241518

1525-
mech = MechanismWithParam(
1526-
self.key_type, DEFAULT_ENCRYPT_MECHANISMS,
1527-
mechanism, mechanism_param)
1519+
mech = MechanismWithParam(self.key_type, DEFAULT_ENCRYPT_MECHANISMS, mechanism, mechanism_param)
15281520

15291521
return DataCryptOperation.setup_decrypt(self.session, mech, self.handle, buffer_size)
15301522

@@ -1606,9 +1598,7 @@ class SignMixin(types.SignMixin):
16061598
"""Expand SignMixin with an implementation."""
16071599

16081600
def __sign_operation(self, mechanism, mechanism_param, buffer_size):
1609-
mech = MechanismWithParam(
1610-
self.key_type, DEFAULT_SIGN_MECHANISMS,
1611-
mechanism, mechanism_param)
1601+
mech = MechanismWithParam(self.key_type, DEFAULT_SIGN_MECHANISMS, mechanism, mechanism_param)
16121602
return DataSignOperation.setup(self.session, mech, self.handle, buffer_size)
16131603

16141604
def _sign(self, data,
@@ -1681,9 +1671,7 @@ class VerifyMixin(types.VerifyMixin):
16811671
"""Expand VerifyMixin with an implementation."""
16821672

16831673
def __verify_operation(self, mechanism, mechanism_param):
1684-
mech = MechanismWithParam(
1685-
self.key_type, DEFAULT_SIGN_MECHANISMS,
1686-
mechanism, mechanism_param)
1674+
mech = MechanismWithParam(self.key_type, DEFAULT_SIGN_MECHANISMS, mechanism, mechanism_param)
16871675
return DataVerifyOperation.setup(self.session, mech, self.handle)
16881676

16891677
def _verify(self, data, signature,
@@ -1719,9 +1707,7 @@ class WrapMixin(types.WrapMixin):
17191707
if not isinstance(key, types.Key):
17201708
raise ArgumentsBad("`key` must be a Key.")
17211709

1722-
mech = MechanismWithParam(
1723-
self.key_type, DEFAULT_WRAP_MECHANISMS,
1724-
mechanism, mechanism_param)
1710+
mech = MechanismWithParam(self.key_type, DEFAULT_WRAP_MECHANISMS, mechanism, mechanism_param)
17251711

17261712
cdef Session session = self.session
17271713
cdef CK_MECHANISM *mech_data = mech.data
@@ -1766,9 +1752,7 @@ class UnwrapMixin(types.UnwrapMixin):
17661752
raise ArgumentsBad("No default capabilities for this key "
17671753
"type. Please specify `capabilities`.")
17681754

1769-
mech = MechanismWithParam(
1770-
self.key_type, DEFAULT_WRAP_MECHANISMS,
1771-
mechanism, mechanism_param)
1755+
mech = MechanismWithParam(self.key_type, DEFAULT_WRAP_MECHANISMS, mechanism, mechanism_param)
17721756

17731757
cdef Session session = self.session
17741758

@@ -1822,9 +1806,7 @@ class DeriveMixin(types.DeriveMixin):
18221806
raise ArgumentsBad("No default capabilities for this key "
18231807
"type. Please specify `capabilities`.")
18241808

1825-
mech = MechanismWithParam(
1826-
self.key_type, DEFAULT_DERIVE_MECHANISMS,
1827-
mechanism, mechanism_param)
1809+
mech = MechanismWithParam(self.key_type, DEFAULT_DERIVE_MECHANISMS, mechanism, mechanism_param)
18281810

18291811
cdef Session session = self.session
18301812

tests/test_digest.py

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -73,3 +73,30 @@ def test_digest_key_data(self):
7373
m.update(data[1][Attribute.VALUE])
7474

7575
self.assertEqual(digest, m.digest())
76+
77+
@requires(Mechanism.SHA256)
78+
def test_digest_stream_interrupt_releases_operation(self):
79+
data = (
80+
b"I" * 16,
81+
b"N" * 16,
82+
b"P" * 16,
83+
b"U" * 16,
84+
b"T" * 10,
85+
)
86+
87+
def _data_with_error():
88+
yield data[0]
89+
yield data[1]
90+
yield data[2]
91+
raise ValueError
92+
93+
def attempt_digest():
94+
self.session.digest(_data_with_error(), mechanism=Mechanism.SHA256)
95+
96+
self.assertRaises(ValueError, attempt_digest)
97+
# ...try again
98+
digest = self.session.digest(data, mechanism=Mechanism.SHA256)
99+
m = hashlib.sha256()
100+
for d in data:
101+
m.update(d)
102+
self.assertEqual(digest, m.digest())

tests/test_rsa.py

Lines changed: 73 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
import pkcs11
66
from pkcs11 import MGF, Attribute, KeyType, Mechanism, ObjectClass
77

8-
from . import FIXME, TestCase, requires
8+
from . import FIXME, TOKEN_PIN, TestCase, requires
99

1010

1111
class RSATests(TestCase):
@@ -25,6 +25,18 @@ def test_sign_pkcs_v15(self):
2525
self.assertTrue(self.public.verify(data, signature, mechanism=Mechanism.RSA_PKCS))
2626
self.assertFalse(self.public.verify(data, b"1234", mechanism=Mechanism.RSA_PKCS))
2727

28+
@requires(Mechanism.SHA512_RSA_PKCS)
29+
def test_sign_with_reauthentication(self):
30+
public, private = self.session.generate_keypair(
31+
KeyType.RSA, 1024, private_template={Attribute.ALWAYS_AUTHENTICATE: True}
32+
)
33+
data = "INPUT"
34+
35+
signature = private.sign(data, pin=TOKEN_PIN)
36+
self.assertIsNotNone(signature)
37+
self.assertIsInstance(signature, bytes)
38+
self.assertTrue(public.verify(data, signature))
39+
2840
@requires(Mechanism.SHA512_RSA_PKCS)
2941
def test_sign_default(self):
3042
data = b"HELLO WORLD" * 1024
@@ -50,6 +62,41 @@ def test_sign_stream(self):
5062
self.assertIsInstance(signature, bytes)
5163
self.assertTrue(self.public.verify(data, signature))
5264

65+
@requires(Mechanism.SHA512_RSA_PKCS)
66+
def test_sign_stream_with_reauthentication(self):
67+
public, private = self.session.generate_keypair(
68+
KeyType.RSA, 1024, private_template={Attribute.ALWAYS_AUTHENTICATE: True}
69+
)
70+
data = (
71+
b"I" * 16,
72+
b"N" * 16,
73+
b"P" * 16,
74+
b"U" * 16,
75+
b"T" * 10,
76+
)
77+
78+
signature = private.sign(data, pin=TOKEN_PIN)
79+
self.assertIsNotNone(signature)
80+
self.assertIsInstance(signature, bytes)
81+
self.assertTrue(public.verify(data, signature))
82+
83+
@requires(Mechanism.SHA512_RSA_PKCS)
84+
def test_sign_stream_with_empty_blocks(self):
85+
data = (
86+
b"I" * 16,
87+
b"N" * 16,
88+
b"",
89+
b"P" * 16,
90+
b"" * 10,
91+
b"U" * 16,
92+
b"T" * 10,
93+
)
94+
95+
signature = self.private.sign(data)
96+
self.assertIsNotNone(signature)
97+
self.assertIsInstance(signature, bytes)
98+
self.assertTrue(self.public.verify(data, signature))
99+
53100
@requires(Mechanism.SHA512_RSA_PKCS)
54101
def test_sign_stream_undersized_buffer(self):
55102
data = (
@@ -91,6 +138,31 @@ def attempt_sign():
91138
self.assertIsInstance(signature, bytes)
92139
self.assertTrue(self.public.verify(data, signature))
93140

141+
@requires(Mechanism.SHA512_RSA_PKCS)
142+
def test_verify_stream_interrupt_releases_operation(self):
143+
data = (
144+
b"I" * 16,
145+
b"N" * 16,
146+
b"P" * 16,
147+
b"U" * 16,
148+
b"T" * 10,
149+
)
150+
151+
def _data_with_error():
152+
yield data[0]
153+
yield data[1]
154+
yield data[2]
155+
raise ValueError
156+
157+
signature = self.private.sign(data)
158+
159+
def attempt_verify():
160+
self.public.verify(_data_with_error(), signature)
161+
162+
self.assertRaises(ValueError, attempt_verify)
163+
# ...try again
164+
self.assertTrue(self.public.verify(data, signature))
165+
94166
@requires(Mechanism.RSA_PKCS_OAEP)
95167
@FIXME.opencryptoki # can't set key attributes
96168
def test_key_wrap(self):

0 commit comments

Comments
 (0)