def sign(self, datau, session, cert, cert_value, algomd, sig_attributes, timestamp): log.info('get certificate in format x509 to build signer attributes') x509 = Certificate.load(cert_value) sign_name = sig_attributes['position']['signature_name'] if sign_name == "": sign_name = MyConfigLoader().get_pdf_config()['position']['signatureName'] dct = { b'sigflags': 3, b'name': b'%b' % x509.subject.native['common_name'].encode(), b'signingdate': b'%b' % timestamp.encode(), b'sign_name': sign_name.encode() } # Variabile segnaposto per i bytes che conterranno il file firmato riferimenti della firma zeros = self.aligned(b'\0') log.info('start building the new pdf') try: pdfdata2 = self.makepdf(datau, dct, zeros, sig_attributes) log.info('pdf generated correctly') except PDFLinearizedError as e: raise PDFLinearizedError(e) except Exception: raise PDFCreationError('Exception on creating pdf') log.info('preparing data to be signed') startxref = len(datau) pdfbr1 = pdfdata2.find(zeros) pdfbr2 = pdfbr1 + len(zeros) br = [0, startxref + pdfbr1 - 1, startxref + pdfbr2 + 1, len(pdfdata2) - pdfbr2 - 1] brfrom = b'[0000000000 0000000000 0000000000 0000000000]' brto = b'[%010d %010d %010d %010d]' % tuple(br) pdfdata2 = pdfdata2.replace(brfrom, brto, 1) b1 = pdfdata2[:br[1] - startxref] b2 = pdfdata2[br[2] - startxref:] md = session.digestSession(Mechanism(LowLevel.CKM_SHA256)) md.update(datau) md.update(b1) md.update(b2) md = bytes(md.final()) log.info('start pdf signing') try: contents = pdf_signer.sign(None, session, cert, cert_value, algomd, True, md) contents = self.aligned(contents) pdfdata2 = pdfdata2.replace(zeros, contents, 1) log.info('pdf signed') except Exception: raise PDFSigningError('error in the sign procedure') return pdfdata2
def digest(session, content): """ Return `content` hash Params: session: smart card session content: content to hash """ log.info("hashing content") try: digest = session.digest(content, Mechanism(LowLevel.CKM_SHA256)) except: raise SmartCardConnectionError("Failed on digest content") return bytes(digest)
def signature(session, priv_key, content): """ Sign `content` with `privKey` reference Reurn: signature in bytearray Params: session: smart card session. privKey: reference to the smart card private key. content: bytes to hash and sign """ log.info("signing content") try: signature = session.sign( priv_key, content, Mechanism(LowLevel.CKM_SHA256_RSA_PKCS, None)) except: raise SmartCardConnectionError("Failed on sign content") return bytes(signature)
def sign(datau, session, cert, cert_value, hashalgo, attrs=True, signed_value=None): if signed_value is None: signed_value = getattr(hashlib, hashalgo)(datau).digest() signed_time = datetime.now() x509 = Certificate.load(cert_value) certificates = [] certificates.append(x509) cert_value_digest = bytes( session.digest(cert_value, Mechanism(LowLevel.CKM_SHA256))) MyLogger().my_logger().info('building signed attributes...') signer = { 'version': 'v1', 'sid': cms.SignerIdentifier({ 'issuer_and_serial_number': cms.IssuerAndSerialNumber({ 'issuer': x509.issuer, 'serial_number': x509.serial_number, }), }), 'digest_algorithm': algos.DigestAlgorithm({'algorithm': hashalgo}), 'signature_algorithm': algos.SignedDigestAlgorithm({'algorithm': 'rsassa_pkcs1v15'}), 'signature': signed_value, } if attrs: signer['signed_attrs'] = [ cms.CMSAttribute({ 'type': cms.CMSAttributeType('content_type'), 'values': ('data', ), }), cms.CMSAttribute({ 'type': cms.CMSAttributeType('message_digest'), 'values': (signed_value, ), }), cms.CMSAttribute({ 'type': cms.CMSAttributeType('signing_time'), 'values': (cms.Time({'utc_time': core.UTCTime(signed_time)}), ) }), cms.CMSAttribute({ 'type': cms.CMSAttributeType('1.2.840.113549.1.9.16.2.47'), 'values': (tsp.SigningCertificateV2({ 'certs': (tsp.ESSCertIDv2({ 'hash_algorithm': algos.DigestAlgorithm({ 'algorithm': hashalgo, 'parameters': None }), 'cert_hash': cert_value_digest, }), ), }), ) }), ] config = { 'version': 'v1', 'digest_algorithms': cms.DigestAlgorithms((algos.DigestAlgorithm({'algorithm': hashalgo}), )), 'encap_content_info': { 'content_type': 'data', }, 'certificates': certificates, # 'crls': [], 'signer_infos': [ signer, ], } datas = cms.ContentInfo({ 'content_type': cms.ContentType('signed_data'), 'content': cms.SignedData(config), }) if attrs: tosign = datas['content']['signer_infos'][0]['signed_attrs'].dump() tosign = b'\x31' + tosign[1:] else: tosign = datau MyLogger().my_logger().info('signed attributes ready') # fetching private key from smart card priv_key = SignatureUtils.fetch_private_key(session, cert) mechanism = Mechanism(LowLevel.CKM_SHA256_RSA_PKCS, None) MyLogger().my_logger().info('signing...') # signing bytes to be signed signature = session.sign(priv_key, tosign, mechanism) datas['content']['signer_infos'][0]['signature'] = bytes(signature) return datas.dump()