1#
2# This file is part of pyasn1-modules software.
3#
4# Copyright (c) 2019, Vigil Security, LLC
5# License: http://snmplabs.com/pyasn1/license.html
6#
7import sys
8
9from pyasn1.codec.der.decoder import decode as der_decode
10from pyasn1.codec.der.encoder import encode as der_encode
11
12from pyasn1_modules import pem
13from pyasn1_modules import rfc5480
14from pyasn1_modules import rfc5652
15from pyasn1_modules import rfc5751
16from pyasn1_modules import rfc6664
17
18try:
19    import unittest2 as unittest
20except ImportError:
21    import unittest
22
23
24class SMIMECapabilitiesTestCase(unittest.TestCase):
25    smime_capabilities_pem_text = """\
26MIICOjAJBgUrDgMCGgUAMA0GCWCGSAFlAwQCBAUAMA0GCWCGSAFlAwQCAQUAMA0G
27CWCGSAFlAwQCAgUAMA0GCWCGSAFlAwQCAwUAMBUGCSqGSIb3DQEBATAIAgIEAAIC
28EAAwFQYJKoZIhvcNAQEHMAgCAgQAAgIQADAVBgkqhkiG9w0BAQowCAICBAACAhAA
29MBUGByqGSM44BAGgCjAIAgIEAAICDAAwggEvBgcqhkjOPgIBoYIBIjCCAR4CgYEA
30i6Ued8R33vkopJwCvy/ZZv2TtddPXPYmJK4jyFv+TDJTPqnP7XUZCqRuhCyKX10z
317SgiZs6qlSMk5gCa8shPF8NCHtps2D1OVC7yppZUJI07FoDxoEAZHImdAFvYIA/V
32cGYpYOKod4kju0/e4VUBZ6Qoer5vKTh+lD/+ZKa/WSUCFQDc3W87QSZSX6ggdbeI
33fzb0rsAhbwKBgCEz/o4WJPUZ4HffJfuXHIGrkPnCxFAYDRtlqueswV0Gy6LunipE
34Iu3nCzYkZhMatyFNyzo+NusEsS+9isOhT8jhL93nSBZCSRBy+GfmSXlXv/3c8mtH
35XTie5JOqjRdonPr4g/+VZvMkcioooNrhx/zICHrC3WZ72871/n/z9M+dMCMGByqG
36SM49AgEwGAYIKoZIzj0DAQcGBSuBBAAiBgUrgQQAIzAhBgUrgQQBDTAYBggqhkjO
37PQMBBwYFK4EEACIGBSuBBAAjMBoGCSqGSIb3DQEBCDANBglghkgBZQMEAgEFAA==
38"""
39
40    def setUp(self):
41        self.asn1Spec = rfc5751.SMIMECapabilities()
42
43    def testDerCodec(self):
44        substrate = pem.readBase64fromText(self.smime_capabilities_pem_text)
45        asn1Object, rest = der_decode (substrate, asn1Spec=self.asn1Spec)
46        assert not rest
47        assert asn1Object.prettyPrint()
48        assert der_encode(asn1Object) == substrate
49
50        count = 0
51        for cap in asn1Object:
52            if cap['capabilityID'] in rfc5751.smimeCapabilityMap.keys():
53                substrate = cap['parameters']
54                cap_p, rest = der_decode (substrate,
55                    asn1Spec=rfc5751.smimeCapabilityMap[cap['capabilityID']])
56                assert not rest
57                assert cap_p.prettyPrint()
58                assert der_encode(cap_p) == substrate
59                count += 1
60
61        assert count == 8
62
63    def testOpenTypes(self):
64        substrate = pem.readBase64fromText(self.smime_capabilities_pem_text)
65        asn1Object, rest = der_decode(substrate,
66            asn1Spec=self.asn1Spec,
67            decodeOpenTypes=True)
68        assert not rest
69        assert asn1Object.prettyPrint()
70        assert der_encode(asn1Object) == substrate
71
72        parameterValue = {
73            rfc6664.rsaEncryption:  lambda x: x['maxKeySize'],
74            rfc6664.id_RSAES_OAEP:  lambda x: x['maxKeySize'],
75            rfc6664.id_RSASSA_PSS:  lambda x: x['minKeySize'],
76            rfc6664.id_dsa:         lambda x: x['keySizes']['maxKeySize'],
77            rfc6664.dhpublicnumber: lambda x: x['keyParams']['q'] % 1023,
78            rfc6664.id_ecPublicKey: lambda x: x[0]['namedCurve'],
79            rfc6664.id_ecMQV:       lambda x: x[1]['namedCurve'],
80        }
81
82        expectedValue = {
83            rfc6664.rsaEncryption:  4096,
84            rfc6664.id_RSAES_OAEP:  4096,
85            rfc6664.id_RSASSA_PSS:  1024,
86            rfc6664.id_dsa:         3072,
87            rfc6664.dhpublicnumber: 257,
88            rfc6664.id_ecPublicKey: rfc5480.secp256r1,
89            rfc6664.id_ecMQV:       rfc5480.secp384r1,
90        }
91
92        count = 0
93        for cap in asn1Object:
94            if cap['capabilityID'] in parameterValue.keys():
95                pValue = parameterValue[cap['capabilityID']](cap['parameters'])
96                eValue = expectedValue[cap['capabilityID']]
97                assert pValue == eValue
98                count += 1
99
100        assert count == 7
101
102
103suite = unittest.TestLoader().loadTestsFromModule(sys.modules[__name__])
104
105if __name__ == '__main__':
106    import sys
107
108    result = unittest.TextTestRunner(verbosity=2).run(suite)
109    sys.exit(not result.wasSuccessful())
110