cms.py 27 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003
  1. # coding: utf-8
  2. """
  3. ASN.1 type classes for cryptographic message syntax (CMS). Structures are also
  4. compatible with PKCS#7. Exports the following items:
  5. - AuthenticatedData()
  6. - AuthEnvelopedData()
  7. - CompressedData()
  8. - ContentInfo()
  9. - DigestedData()
  10. - EncryptedData()
  11. - EnvelopedData()
  12. - SignedAndEnvelopedData()
  13. - SignedData()
  14. Other type classes are defined that help compose the types listed above.
  15. Most CMS structures in the wild are formatted as ContentInfo encapsulating one of the other types.
  16. """
  17. from __future__ import unicode_literals, division, absolute_import, print_function
  18. try:
  19. import zlib
  20. except (ImportError):
  21. zlib = None
  22. from .algos import (
  23. _ForceNullParameters,
  24. DigestAlgorithm,
  25. EncryptionAlgorithm,
  26. EncryptionAlgorithmId,
  27. HmacAlgorithm,
  28. KdfAlgorithm,
  29. RSAESOAEPParams,
  30. SignedDigestAlgorithm,
  31. )
  32. from .core import (
  33. Any,
  34. BitString,
  35. Choice,
  36. Enumerated,
  37. GeneralizedTime,
  38. Integer,
  39. ObjectIdentifier,
  40. OctetBitString,
  41. OctetString,
  42. ParsableOctetString,
  43. Sequence,
  44. SequenceOf,
  45. SetOf,
  46. UTCTime,
  47. UTF8String,
  48. )
  49. from .crl import CertificateList
  50. from .keys import PublicKeyInfo
  51. from .ocsp import OCSPResponse
  52. from .x509 import Attributes, Certificate, Extensions, GeneralName, GeneralNames, Name
  53. # These structures are taken from
  54. # ftp://ftp.rsasecurity.com/pub/pkcs/ascii/pkcs-6.asc
  55. class ExtendedCertificateInfo(Sequence):
  56. _fields = [
  57. ('version', Integer),
  58. ('certificate', Certificate),
  59. ('attributes', Attributes),
  60. ]
  61. class ExtendedCertificate(Sequence):
  62. _fields = [
  63. ('extended_certificate_info', ExtendedCertificateInfo),
  64. ('signature_algorithm', SignedDigestAlgorithm),
  65. ('signature', OctetBitString),
  66. ]
  67. # These structures are taken from https://tools.ietf.org/html/rfc5652,
  68. # https://tools.ietf.org/html/rfc5083, http://tools.ietf.org/html/rfc2315,
  69. # https://tools.ietf.org/html/rfc5940, https://tools.ietf.org/html/rfc3274,
  70. # https://tools.ietf.org/html/rfc3281
  71. class CMSVersion(Integer):
  72. _map = {
  73. 0: 'v0',
  74. 1: 'v1',
  75. 2: 'v2',
  76. 3: 'v3',
  77. 4: 'v4',
  78. 5: 'v5',
  79. }
  80. class CMSAttributeType(ObjectIdentifier):
  81. _map = {
  82. '1.2.840.113549.1.9.3': 'content_type',
  83. '1.2.840.113549.1.9.4': 'message_digest',
  84. '1.2.840.113549.1.9.5': 'signing_time',
  85. '1.2.840.113549.1.9.6': 'counter_signature',
  86. # https://datatracker.ietf.org/doc/html/rfc2633#section-2.5.2
  87. '1.2.840.113549.1.9.15': 'smime_capabilities',
  88. # https://tools.ietf.org/html/rfc2633#page-26
  89. '1.2.840.113549.1.9.16.2.11': 'encrypt_key_pref',
  90. # https://tools.ietf.org/html/rfc3161#page-20
  91. '1.2.840.113549.1.9.16.2.14': 'signature_time_stamp_token',
  92. # https://tools.ietf.org/html/rfc6211#page-5
  93. '1.2.840.113549.1.9.52': 'cms_algorithm_protection',
  94. # https://docs.microsoft.com/en-us/previous-versions/hh968145(v%3Dvs.85)
  95. '1.3.6.1.4.1.311.2.4.1': 'microsoft_nested_signature',
  96. # Some places refer to this as SPC_RFC3161_OBJID, others szOID_RFC3161_counterSign.
  97. # https://docs.microsoft.com/en-us/windows/win32/api/wincrypt/ns-wincrypt-crypt_algorithm_identifier
  98. # refers to szOID_RFC3161_counterSign as "1.2.840.113549.1.9.16.1.4",
  99. # but that OID is also called szOID_TIMESTAMP_TOKEN. Because of there being
  100. # no canonical source for this OID, we give it our own name
  101. '1.3.6.1.4.1.311.3.3.1': 'microsoft_time_stamp_token',
  102. }
  103. class Time(Choice):
  104. _alternatives = [
  105. ('utc_time', UTCTime),
  106. ('generalized_time', GeneralizedTime),
  107. ]
  108. class ContentType(ObjectIdentifier):
  109. _map = {
  110. '1.2.840.113549.1.7.1': 'data',
  111. '1.2.840.113549.1.7.2': 'signed_data',
  112. '1.2.840.113549.1.7.3': 'enveloped_data',
  113. '1.2.840.113549.1.7.4': 'signed_and_enveloped_data',
  114. '1.2.840.113549.1.7.5': 'digested_data',
  115. '1.2.840.113549.1.7.6': 'encrypted_data',
  116. '1.2.840.113549.1.9.16.1.2': 'authenticated_data',
  117. '1.2.840.113549.1.9.16.1.9': 'compressed_data',
  118. '1.2.840.113549.1.9.16.1.23': 'authenticated_enveloped_data',
  119. }
  120. class CMSAlgorithmProtection(Sequence):
  121. _fields = [
  122. ('digest_algorithm', DigestAlgorithm),
  123. ('signature_algorithm', SignedDigestAlgorithm, {'implicit': 1, 'optional': True}),
  124. ('mac_algorithm', HmacAlgorithm, {'implicit': 2, 'optional': True}),
  125. ]
  126. class SetOfContentType(SetOf):
  127. _child_spec = ContentType
  128. class SetOfOctetString(SetOf):
  129. _child_spec = OctetString
  130. class SetOfTime(SetOf):
  131. _child_spec = Time
  132. class SetOfAny(SetOf):
  133. _child_spec = Any
  134. class SetOfCMSAlgorithmProtection(SetOf):
  135. _child_spec = CMSAlgorithmProtection
  136. class CMSAttribute(Sequence):
  137. _fields = [
  138. ('type', CMSAttributeType),
  139. ('values', None),
  140. ]
  141. _oid_specs = {}
  142. def _values_spec(self):
  143. return self._oid_specs.get(self['type'].native, SetOfAny)
  144. _spec_callbacks = {
  145. 'values': _values_spec
  146. }
  147. class CMSAttributes(SetOf):
  148. _child_spec = CMSAttribute
  149. class IssuerSerial(Sequence):
  150. _fields = [
  151. ('issuer', GeneralNames),
  152. ('serial', Integer),
  153. ('issuer_uid', OctetBitString, {'optional': True}),
  154. ]
  155. class AttCertVersion(Integer):
  156. _map = {
  157. 0: 'v1',
  158. 1: 'v2',
  159. }
  160. class AttCertSubject(Choice):
  161. _alternatives = [
  162. ('base_certificate_id', IssuerSerial, {'explicit': 0}),
  163. ('subject_name', GeneralNames, {'explicit': 1}),
  164. ]
  165. class AttCertValidityPeriod(Sequence):
  166. _fields = [
  167. ('not_before_time', GeneralizedTime),
  168. ('not_after_time', GeneralizedTime),
  169. ]
  170. class AttributeCertificateInfoV1(Sequence):
  171. _fields = [
  172. ('version', AttCertVersion, {'default': 'v1'}),
  173. ('subject', AttCertSubject),
  174. ('issuer', GeneralNames),
  175. ('signature', SignedDigestAlgorithm),
  176. ('serial_number', Integer),
  177. ('att_cert_validity_period', AttCertValidityPeriod),
  178. ('attributes', Attributes),
  179. ('issuer_unique_id', OctetBitString, {'optional': True}),
  180. ('extensions', Extensions, {'optional': True}),
  181. ]
  182. class AttributeCertificateV1(Sequence):
  183. _fields = [
  184. ('ac_info', AttributeCertificateInfoV1),
  185. ('signature_algorithm', SignedDigestAlgorithm),
  186. ('signature', OctetBitString),
  187. ]
  188. class DigestedObjectType(Enumerated):
  189. _map = {
  190. 0: 'public_key',
  191. 1: 'public_key_cert',
  192. 2: 'other_objy_types',
  193. }
  194. class ObjectDigestInfo(Sequence):
  195. _fields = [
  196. ('digested_object_type', DigestedObjectType),
  197. ('other_object_type_id', ObjectIdentifier, {'optional': True}),
  198. ('digest_algorithm', DigestAlgorithm),
  199. ('object_digest', OctetBitString),
  200. ]
  201. class Holder(Sequence):
  202. _fields = [
  203. ('base_certificate_id', IssuerSerial, {'implicit': 0, 'optional': True}),
  204. ('entity_name', GeneralNames, {'implicit': 1, 'optional': True}),
  205. ('object_digest_info', ObjectDigestInfo, {'implicit': 2, 'optional': True}),
  206. ]
  207. class V2Form(Sequence):
  208. _fields = [
  209. ('issuer_name', GeneralNames, {'optional': True}),
  210. ('base_certificate_id', IssuerSerial, {'explicit': 0, 'optional': True}),
  211. ('object_digest_info', ObjectDigestInfo, {'explicit': 1, 'optional': True}),
  212. ]
  213. class AttCertIssuer(Choice):
  214. _alternatives = [
  215. ('v1_form', GeneralNames),
  216. ('v2_form', V2Form, {'implicit': 0}),
  217. ]
  218. class IetfAttrValue(Choice):
  219. _alternatives = [
  220. ('octets', OctetString),
  221. ('oid', ObjectIdentifier),
  222. ('string', UTF8String),
  223. ]
  224. class IetfAttrValues(SequenceOf):
  225. _child_spec = IetfAttrValue
  226. class IetfAttrSyntax(Sequence):
  227. _fields = [
  228. ('policy_authority', GeneralNames, {'implicit': 0, 'optional': True}),
  229. ('values', IetfAttrValues),
  230. ]
  231. class SetOfIetfAttrSyntax(SetOf):
  232. _child_spec = IetfAttrSyntax
  233. class SvceAuthInfo(Sequence):
  234. _fields = [
  235. ('service', GeneralName),
  236. ('ident', GeneralName),
  237. ('auth_info', OctetString, {'optional': True}),
  238. ]
  239. class SetOfSvceAuthInfo(SetOf):
  240. _child_spec = SvceAuthInfo
  241. class RoleSyntax(Sequence):
  242. _fields = [
  243. ('role_authority', GeneralNames, {'implicit': 0, 'optional': True}),
  244. ('role_name', GeneralName, {'explicit': 1}),
  245. ]
  246. class SetOfRoleSyntax(SetOf):
  247. _child_spec = RoleSyntax
  248. class ClassList(BitString):
  249. _map = {
  250. 0: 'unmarked',
  251. 1: 'unclassified',
  252. 2: 'restricted',
  253. 3: 'confidential',
  254. 4: 'secret',
  255. 5: 'top_secret',
  256. }
  257. class SecurityCategory(Sequence):
  258. _fields = [
  259. ('type', ObjectIdentifier, {'implicit': 0}),
  260. ('value', Any, {'explicit': 1}),
  261. ]
  262. class SetOfSecurityCategory(SetOf):
  263. _child_spec = SecurityCategory
  264. class Clearance(Sequence):
  265. _fields = [
  266. ('policy_id', ObjectIdentifier),
  267. ('class_list', ClassList, {'default': set(['unclassified'])}),
  268. ('security_categories', SetOfSecurityCategory, {'optional': True}),
  269. ]
  270. class SetOfClearance(SetOf):
  271. _child_spec = Clearance
  272. class BigTime(Sequence):
  273. _fields = [
  274. ('major', Integer),
  275. ('fractional_seconds', Integer),
  276. ('sign', Integer, {'optional': True}),
  277. ]
  278. class LeapData(Sequence):
  279. _fields = [
  280. ('leap_time', BigTime),
  281. ('action', Integer),
  282. ]
  283. class SetOfLeapData(SetOf):
  284. _child_spec = LeapData
  285. class TimingMetrics(Sequence):
  286. _fields = [
  287. ('ntp_time', BigTime),
  288. ('offset', BigTime),
  289. ('delay', BigTime),
  290. ('expiration', BigTime),
  291. ('leap_event', SetOfLeapData, {'optional': True}),
  292. ]
  293. class SetOfTimingMetrics(SetOf):
  294. _child_spec = TimingMetrics
  295. class TimingPolicy(Sequence):
  296. _fields = [
  297. ('policy_id', SequenceOf, {'spec': ObjectIdentifier}),
  298. ('max_offset', BigTime, {'explicit': 0, 'optional': True}),
  299. ('max_delay', BigTime, {'explicit': 1, 'optional': True}),
  300. ]
  301. class SetOfTimingPolicy(SetOf):
  302. _child_spec = TimingPolicy
  303. class AttCertAttributeType(ObjectIdentifier):
  304. _map = {
  305. '1.3.6.1.5.5.7.10.1': 'authentication_info',
  306. '1.3.6.1.5.5.7.10.2': 'access_identity',
  307. '1.3.6.1.5.5.7.10.3': 'charging_identity',
  308. '1.3.6.1.5.5.7.10.4': 'group',
  309. '2.5.4.72': 'role',
  310. '2.5.4.55': 'clearance',
  311. '1.3.6.1.4.1.601.10.4.1': 'timing_metrics',
  312. '1.3.6.1.4.1.601.10.4.2': 'timing_policy',
  313. }
  314. class AttCertAttribute(Sequence):
  315. _fields = [
  316. ('type', AttCertAttributeType),
  317. ('values', None),
  318. ]
  319. _oid_specs = {
  320. 'authentication_info': SetOfSvceAuthInfo,
  321. 'access_identity': SetOfSvceAuthInfo,
  322. 'charging_identity': SetOfIetfAttrSyntax,
  323. 'group': SetOfIetfAttrSyntax,
  324. 'role': SetOfRoleSyntax,
  325. 'clearance': SetOfClearance,
  326. 'timing_metrics': SetOfTimingMetrics,
  327. 'timing_policy': SetOfTimingPolicy,
  328. }
  329. def _values_spec(self):
  330. return self._oid_specs.get(self['type'].native, SetOfAny)
  331. _spec_callbacks = {
  332. 'values': _values_spec
  333. }
  334. class AttCertAttributes(SequenceOf):
  335. _child_spec = AttCertAttribute
  336. class AttributeCertificateInfoV2(Sequence):
  337. _fields = [
  338. ('version', AttCertVersion),
  339. ('holder', Holder),
  340. ('issuer', AttCertIssuer),
  341. ('signature', SignedDigestAlgorithm),
  342. ('serial_number', Integer),
  343. ('att_cert_validity_period', AttCertValidityPeriod),
  344. ('attributes', AttCertAttributes),
  345. ('issuer_unique_id', OctetBitString, {'optional': True}),
  346. ('extensions', Extensions, {'optional': True}),
  347. ]
  348. class AttributeCertificateV2(Sequence):
  349. # Handle the situation where a V2 cert is encoded as V1
  350. _bad_tag = 1
  351. _fields = [
  352. ('ac_info', AttributeCertificateInfoV2),
  353. ('signature_algorithm', SignedDigestAlgorithm),
  354. ('signature', OctetBitString),
  355. ]
  356. class OtherCertificateFormat(Sequence):
  357. _fields = [
  358. ('other_cert_format', ObjectIdentifier),
  359. ('other_cert', Any),
  360. ]
  361. class CertificateChoices(Choice):
  362. _alternatives = [
  363. ('certificate', Certificate),
  364. ('extended_certificate', ExtendedCertificate, {'implicit': 0}),
  365. ('v1_attr_cert', AttributeCertificateV1, {'implicit': 1}),
  366. ('v2_attr_cert', AttributeCertificateV2, {'implicit': 2}),
  367. ('other', OtherCertificateFormat, {'implicit': 3}),
  368. ]
  369. def validate(self, class_, tag, contents):
  370. """
  371. Ensures that the class and tag specified exist as an alternative. This
  372. custom version fixes parsing broken encodings there a V2 attribute
  373. # certificate is encoded as a V1
  374. :param class_:
  375. The integer class_ from the encoded value header
  376. :param tag:
  377. The integer tag from the encoded value header
  378. :param contents:
  379. A byte string of the contents of the value - used when the object
  380. is explicitly tagged
  381. :raises:
  382. ValueError - when value is not a valid alternative
  383. """
  384. super(CertificateChoices, self).validate(class_, tag, contents)
  385. if self._choice == 2:
  386. if AttCertVersion.load(Sequence.load(contents)[0].dump()).native == 'v2':
  387. self._choice = 3
  388. class CertificateSet(SetOf):
  389. _child_spec = CertificateChoices
  390. class ContentInfo(Sequence):
  391. _fields = [
  392. ('content_type', ContentType),
  393. ('content', Any, {'explicit': 0, 'optional': True}),
  394. ]
  395. _oid_pair = ('content_type', 'content')
  396. _oid_specs = {}
  397. class SetOfContentInfo(SetOf):
  398. _child_spec = ContentInfo
  399. class EncapsulatedContentInfo(Sequence):
  400. _fields = [
  401. ('content_type', ContentType),
  402. ('content', ParsableOctetString, {'explicit': 0, 'optional': True}),
  403. ]
  404. _oid_pair = ('content_type', 'content')
  405. _oid_specs = {}
  406. class IssuerAndSerialNumber(Sequence):
  407. _fields = [
  408. ('issuer', Name),
  409. ('serial_number', Integer),
  410. ]
  411. class SignerIdentifier(Choice):
  412. _alternatives = [
  413. ('issuer_and_serial_number', IssuerAndSerialNumber),
  414. ('subject_key_identifier', OctetString, {'implicit': 0}),
  415. ]
  416. class DigestAlgorithms(SetOf):
  417. _child_spec = DigestAlgorithm
  418. class CertificateRevocationLists(SetOf):
  419. _child_spec = CertificateList
  420. class SCVPReqRes(Sequence):
  421. _fields = [
  422. ('request', ContentInfo, {'explicit': 0, 'optional': True}),
  423. ('response', ContentInfo),
  424. ]
  425. class OtherRevInfoFormatId(ObjectIdentifier):
  426. _map = {
  427. '1.3.6.1.5.5.7.16.2': 'ocsp_response',
  428. '1.3.6.1.5.5.7.16.4': 'scvp',
  429. }
  430. class OtherRevocationInfoFormat(Sequence):
  431. _fields = [
  432. ('other_rev_info_format', OtherRevInfoFormatId),
  433. ('other_rev_info', Any),
  434. ]
  435. _oid_pair = ('other_rev_info_format', 'other_rev_info')
  436. _oid_specs = {
  437. 'ocsp_response': OCSPResponse,
  438. 'scvp': SCVPReqRes,
  439. }
  440. class RevocationInfoChoice(Choice):
  441. _alternatives = [
  442. ('crl', CertificateList),
  443. ('other', OtherRevocationInfoFormat, {'implicit': 1}),
  444. ]
  445. class RevocationInfoChoices(SetOf):
  446. _child_spec = RevocationInfoChoice
  447. class SignerInfo(Sequence):
  448. _fields = [
  449. ('version', CMSVersion),
  450. ('sid', SignerIdentifier),
  451. ('digest_algorithm', DigestAlgorithm),
  452. ('signed_attrs', CMSAttributes, {'implicit': 0, 'optional': True}),
  453. ('signature_algorithm', SignedDigestAlgorithm),
  454. ('signature', OctetString),
  455. ('unsigned_attrs', CMSAttributes, {'implicit': 1, 'optional': True}),
  456. ]
  457. class SignerInfos(SetOf):
  458. _child_spec = SignerInfo
  459. class SignedData(Sequence):
  460. _fields = [
  461. ('version', CMSVersion),
  462. ('digest_algorithms', DigestAlgorithms),
  463. ('encap_content_info', None),
  464. ('certificates', CertificateSet, {'implicit': 0, 'optional': True}),
  465. ('crls', RevocationInfoChoices, {'implicit': 1, 'optional': True}),
  466. ('signer_infos', SignerInfos),
  467. ]
  468. def _encap_content_info_spec(self):
  469. # If the encap_content_info is version v1, then this could be a PKCS#7
  470. # structure, or a CMS structure. CMS wraps the encoded value in an
  471. # Octet String tag.
  472. # If the version is greater than 1, it is definite CMS
  473. if self['version'].native != 'v1':
  474. return EncapsulatedContentInfo
  475. # Otherwise, the ContentInfo spec from PKCS#7 will be compatible with
  476. # CMS v1 (which only allows Data, an Octet String) and PKCS#7, which
  477. # allows Any
  478. return ContentInfo
  479. _spec_callbacks = {
  480. 'encap_content_info': _encap_content_info_spec
  481. }
  482. class OriginatorInfo(Sequence):
  483. _fields = [
  484. ('certs', CertificateSet, {'implicit': 0, 'optional': True}),
  485. ('crls', RevocationInfoChoices, {'implicit': 1, 'optional': True}),
  486. ]
  487. class RecipientIdentifier(Choice):
  488. _alternatives = [
  489. ('issuer_and_serial_number', IssuerAndSerialNumber),
  490. ('subject_key_identifier', OctetString, {'implicit': 0}),
  491. ]
  492. class KeyEncryptionAlgorithmId(ObjectIdentifier):
  493. _map = {
  494. '1.2.840.113549.1.1.1': 'rsaes_pkcs1v15',
  495. '1.2.840.113549.1.1.7': 'rsaes_oaep',
  496. '2.16.840.1.101.3.4.1.5': 'aes128_wrap',
  497. '2.16.840.1.101.3.4.1.8': 'aes128_wrap_pad',
  498. '2.16.840.1.101.3.4.1.25': 'aes192_wrap',
  499. '2.16.840.1.101.3.4.1.28': 'aes192_wrap_pad',
  500. '2.16.840.1.101.3.4.1.45': 'aes256_wrap',
  501. '2.16.840.1.101.3.4.1.48': 'aes256_wrap_pad',
  502. }
  503. _reverse_map = {
  504. 'rsa': '1.2.840.113549.1.1.1',
  505. 'rsaes_pkcs1v15': '1.2.840.113549.1.1.1',
  506. 'rsaes_oaep': '1.2.840.113549.1.1.7',
  507. 'aes128_wrap': '2.16.840.1.101.3.4.1.5',
  508. 'aes128_wrap_pad': '2.16.840.1.101.3.4.1.8',
  509. 'aes192_wrap': '2.16.840.1.101.3.4.1.25',
  510. 'aes192_wrap_pad': '2.16.840.1.101.3.4.1.28',
  511. 'aes256_wrap': '2.16.840.1.101.3.4.1.45',
  512. 'aes256_wrap_pad': '2.16.840.1.101.3.4.1.48',
  513. }
  514. class KeyEncryptionAlgorithm(_ForceNullParameters, Sequence):
  515. _fields = [
  516. ('algorithm', KeyEncryptionAlgorithmId),
  517. ('parameters', Any, {'optional': True}),
  518. ]
  519. _oid_pair = ('algorithm', 'parameters')
  520. _oid_specs = {
  521. 'rsaes_oaep': RSAESOAEPParams,
  522. }
  523. class KeyTransRecipientInfo(Sequence):
  524. _fields = [
  525. ('version', CMSVersion),
  526. ('rid', RecipientIdentifier),
  527. ('key_encryption_algorithm', KeyEncryptionAlgorithm),
  528. ('encrypted_key', OctetString),
  529. ]
  530. class OriginatorIdentifierOrKey(Choice):
  531. _alternatives = [
  532. ('issuer_and_serial_number', IssuerAndSerialNumber),
  533. ('subject_key_identifier', OctetString, {'implicit': 0}),
  534. ('originator_key', PublicKeyInfo, {'implicit': 1}),
  535. ]
  536. class OtherKeyAttribute(Sequence):
  537. _fields = [
  538. ('key_attr_id', ObjectIdentifier),
  539. ('key_attr', Any),
  540. ]
  541. class RecipientKeyIdentifier(Sequence):
  542. _fields = [
  543. ('subject_key_identifier', OctetString),
  544. ('date', GeneralizedTime, {'optional': True}),
  545. ('other', OtherKeyAttribute, {'optional': True}),
  546. ]
  547. class KeyAgreementRecipientIdentifier(Choice):
  548. _alternatives = [
  549. ('issuer_and_serial_number', IssuerAndSerialNumber),
  550. ('r_key_id', RecipientKeyIdentifier, {'implicit': 0}),
  551. ]
  552. class RecipientEncryptedKey(Sequence):
  553. _fields = [
  554. ('rid', KeyAgreementRecipientIdentifier),
  555. ('encrypted_key', OctetString),
  556. ]
  557. class RecipientEncryptedKeys(SequenceOf):
  558. _child_spec = RecipientEncryptedKey
  559. class KeyAgreeRecipientInfo(Sequence):
  560. _fields = [
  561. ('version', CMSVersion),
  562. ('originator', OriginatorIdentifierOrKey, {'explicit': 0}),
  563. ('ukm', OctetString, {'explicit': 1, 'optional': True}),
  564. ('key_encryption_algorithm', KeyEncryptionAlgorithm),
  565. ('recipient_encrypted_keys', RecipientEncryptedKeys),
  566. ]
  567. class KEKIdentifier(Sequence):
  568. _fields = [
  569. ('key_identifier', OctetString),
  570. ('date', GeneralizedTime, {'optional': True}),
  571. ('other', OtherKeyAttribute, {'optional': True}),
  572. ]
  573. class KEKRecipientInfo(Sequence):
  574. _fields = [
  575. ('version', CMSVersion),
  576. ('kekid', KEKIdentifier),
  577. ('key_encryption_algorithm', KeyEncryptionAlgorithm),
  578. ('encrypted_key', OctetString),
  579. ]
  580. class PasswordRecipientInfo(Sequence):
  581. _fields = [
  582. ('version', CMSVersion),
  583. ('key_derivation_algorithm', KdfAlgorithm, {'implicit': 0, 'optional': True}),
  584. ('key_encryption_algorithm', KeyEncryptionAlgorithm),
  585. ('encrypted_key', OctetString),
  586. ]
  587. class OtherRecipientInfo(Sequence):
  588. _fields = [
  589. ('ori_type', ObjectIdentifier),
  590. ('ori_value', Any),
  591. ]
  592. class RecipientInfo(Choice):
  593. _alternatives = [
  594. ('ktri', KeyTransRecipientInfo),
  595. ('kari', KeyAgreeRecipientInfo, {'implicit': 1}),
  596. ('kekri', KEKRecipientInfo, {'implicit': 2}),
  597. ('pwri', PasswordRecipientInfo, {'implicit': 3}),
  598. ('ori', OtherRecipientInfo, {'implicit': 4}),
  599. ]
  600. class RecipientInfos(SetOf):
  601. _child_spec = RecipientInfo
  602. class EncryptedContentInfo(Sequence):
  603. _fields = [
  604. ('content_type', ContentType),
  605. ('content_encryption_algorithm', EncryptionAlgorithm),
  606. ('encrypted_content', OctetString, {'implicit': 0, 'optional': True}),
  607. ]
  608. class EnvelopedData(Sequence):
  609. _fields = [
  610. ('version', CMSVersion),
  611. ('originator_info', OriginatorInfo, {'implicit': 0, 'optional': True}),
  612. ('recipient_infos', RecipientInfos),
  613. ('encrypted_content_info', EncryptedContentInfo),
  614. ('unprotected_attrs', CMSAttributes, {'implicit': 1, 'optional': True}),
  615. ]
  616. class SignedAndEnvelopedData(Sequence):
  617. _fields = [
  618. ('version', CMSVersion),
  619. ('recipient_infos', RecipientInfos),
  620. ('digest_algorithms', DigestAlgorithms),
  621. ('encrypted_content_info', EncryptedContentInfo),
  622. ('certificates', CertificateSet, {'implicit': 0, 'optional': True}),
  623. ('crls', CertificateRevocationLists, {'implicit': 1, 'optional': True}),
  624. ('signer_infos', SignerInfos),
  625. ]
  626. class DigestedData(Sequence):
  627. _fields = [
  628. ('version', CMSVersion),
  629. ('digest_algorithm', DigestAlgorithm),
  630. ('encap_content_info', None),
  631. ('digest', OctetString),
  632. ]
  633. def _encap_content_info_spec(self):
  634. # If the encap_content_info is version v1, then this could be a PKCS#7
  635. # structure, or a CMS structure. CMS wraps the encoded value in an
  636. # Octet String tag.
  637. # If the version is greater than 1, it is definite CMS
  638. if self['version'].native != 'v1':
  639. return EncapsulatedContentInfo
  640. # Otherwise, the ContentInfo spec from PKCS#7 will be compatible with
  641. # CMS v1 (which only allows Data, an Octet String) and PKCS#7, which
  642. # allows Any
  643. return ContentInfo
  644. _spec_callbacks = {
  645. 'encap_content_info': _encap_content_info_spec
  646. }
  647. class EncryptedData(Sequence):
  648. _fields = [
  649. ('version', CMSVersion),
  650. ('encrypted_content_info', EncryptedContentInfo),
  651. ('unprotected_attrs', CMSAttributes, {'implicit': 1, 'optional': True}),
  652. ]
  653. class AuthenticatedData(Sequence):
  654. _fields = [
  655. ('version', CMSVersion),
  656. ('originator_info', OriginatorInfo, {'implicit': 0, 'optional': True}),
  657. ('recipient_infos', RecipientInfos),
  658. ('mac_algorithm', HmacAlgorithm),
  659. ('digest_algorithm', DigestAlgorithm, {'implicit': 1, 'optional': True}),
  660. # This does not require the _spec_callbacks approach of SignedData and
  661. # DigestedData since AuthenticatedData was not part of PKCS#7
  662. ('encap_content_info', EncapsulatedContentInfo),
  663. ('auth_attrs', CMSAttributes, {'implicit': 2, 'optional': True}),
  664. ('mac', OctetString),
  665. ('unauth_attrs', CMSAttributes, {'implicit': 3, 'optional': True}),
  666. ]
  667. class AuthEnvelopedData(Sequence):
  668. _fields = [
  669. ('version', CMSVersion),
  670. ('originator_info', OriginatorInfo, {'implicit': 0, 'optional': True}),
  671. ('recipient_infos', RecipientInfos),
  672. ('auth_encrypted_content_info', EncryptedContentInfo),
  673. ('auth_attrs', CMSAttributes, {'implicit': 1, 'optional': True}),
  674. ('mac', OctetString),
  675. ('unauth_attrs', CMSAttributes, {'implicit': 2, 'optional': True}),
  676. ]
  677. class CompressionAlgorithmId(ObjectIdentifier):
  678. _map = {
  679. '1.2.840.113549.1.9.16.3.8': 'zlib',
  680. }
  681. class CompressionAlgorithm(Sequence):
  682. _fields = [
  683. ('algorithm', CompressionAlgorithmId),
  684. ('parameters', Any, {'optional': True}),
  685. ]
  686. class CompressedData(Sequence):
  687. _fields = [
  688. ('version', CMSVersion),
  689. ('compression_algorithm', CompressionAlgorithm),
  690. ('encap_content_info', EncapsulatedContentInfo),
  691. ]
  692. _decompressed = None
  693. @property
  694. def decompressed(self):
  695. if self._decompressed is None:
  696. if zlib is None:
  697. raise SystemError('The zlib module is not available')
  698. self._decompressed = zlib.decompress(self['encap_content_info']['content'].native)
  699. return self._decompressed
  700. class RecipientKeyIdentifier(Sequence):
  701. _fields = [
  702. ('subjectKeyIdentifier', OctetString),
  703. ('date', GeneralizedTime, {'optional': True}),
  704. ('other', OtherKeyAttribute, {'optional': True}),
  705. ]
  706. class SMIMEEncryptionKeyPreference(Choice):
  707. _alternatives = [
  708. ('issuer_and_serial_number', IssuerAndSerialNumber, {'implicit': 0}),
  709. ('recipientKeyId', RecipientKeyIdentifier, {'implicit': 1}),
  710. ('subjectAltKeyIdentifier', PublicKeyInfo, {'implicit': 2}),
  711. ]
  712. class SMIMEEncryptionKeyPreferences(SetOf):
  713. _child_spec = SMIMEEncryptionKeyPreference
  714. class SMIMECapabilityIdentifier(Sequence):
  715. _fields = [
  716. ('capability_id', EncryptionAlgorithmId),
  717. ('parameters', Any, {'optional': True}),
  718. ]
  719. class SMIMECapabilites(SequenceOf):
  720. _child_spec = SMIMECapabilityIdentifier
  721. class SetOfSMIMECapabilites(SetOf):
  722. _child_spec = SMIMECapabilites
  723. ContentInfo._oid_specs = {
  724. 'data': OctetString,
  725. 'signed_data': SignedData,
  726. 'enveloped_data': EnvelopedData,
  727. 'signed_and_enveloped_data': SignedAndEnvelopedData,
  728. 'digested_data': DigestedData,
  729. 'encrypted_data': EncryptedData,
  730. 'authenticated_data': AuthenticatedData,
  731. 'compressed_data': CompressedData,
  732. 'authenticated_enveloped_data': AuthEnvelopedData,
  733. }
  734. EncapsulatedContentInfo._oid_specs = {
  735. 'signed_data': SignedData,
  736. 'enveloped_data': EnvelopedData,
  737. 'signed_and_enveloped_data': SignedAndEnvelopedData,
  738. 'digested_data': DigestedData,
  739. 'encrypted_data': EncryptedData,
  740. 'authenticated_data': AuthenticatedData,
  741. 'compressed_data': CompressedData,
  742. 'authenticated_enveloped_data': AuthEnvelopedData,
  743. }
  744. CMSAttribute._oid_specs = {
  745. 'content_type': SetOfContentType,
  746. 'message_digest': SetOfOctetString,
  747. 'signing_time': SetOfTime,
  748. 'counter_signature': SignerInfos,
  749. 'signature_time_stamp_token': SetOfContentInfo,
  750. 'cms_algorithm_protection': SetOfCMSAlgorithmProtection,
  751. 'microsoft_nested_signature': SetOfContentInfo,
  752. 'microsoft_time_stamp_token': SetOfContentInfo,
  753. 'encrypt_key_pref': SMIMEEncryptionKeyPreferences,
  754. 'smime_capabilities': SetOfSMIMECapabilites,
  755. }