cms.py 25 KB

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