def decrypt_verify(p7file, recip_key, signer_cert, ca_cert): s = SMIME.SMIME() # Load decryption private key. s.load_key(recip_key) # Extract PKCS#7 blob from input. p7, bio = SMIME.smime_load_pkcs7_bio(p7file) # Decrypt. data = s.decrypt(p7) # Because we passed in a SignAndEnveloped blob, the output # of our decryption is a Signed blob. We now verify it. # Load the signer's cert. sk = X509.X509_Stack() s.set_x509_stack(sk) # Load the CA cert. st = X509.X509_Store() st.load_info(ca_cert) s.set_x509_store(st) # Verify. p7, bio = SMIME.smime_load_pkcs7_bio(BIO.MemoryBuffer(data)) if bio is not None: # Netscape Messenger clear-signs, when also encrypting. data = s.verify(p7, bio) else: # M2Crypto's sendsmime.py opaque-signs, when also encrypting. data = s.verify(p7) print data
def decrypt_verify(p7file, recip_key, signer_cert, ca_cert): s = SMIME.SMIME() # Load decryption private key. s.load_key(recip_key) # Extract PKCS#7 blob from input. p7, bio = SMIME.smime_load_pkcs7_bio(p7file) # Decrypt. data = s.decrypt(p7) # Because we passed in a SignAndEnveloped blob, the output # of our decryption is a Signed blob. We now verify it. # Load the signer's cert. sk = X509.X509_Stack() s.set_x509_stack(sk) # Load the CA cert. st = X509.X509_Store() st.load_info(ca_cert) s.set_x509_store(st) # Verify. p7, bio = SMIME.smime_load_pkcs7_bio(BIO.MemoryBuffer(data)) if bio is not None: # Netscape Messenger clear-signs, when also encrypting. data = s.verify(p7, bio) else: # M2Crypto's sendsmime.py opaque-signs, when also encrypting. data = s.verify(p7) print data
def decrypt_and_verify(self): # Instantiate an SMIME object. s = SMIME.SMIME() # Load private key and cert. s.load_key(recipient_key, recipient_cert) # Load the signed/encrypted data. p7, data = SMIME.smime_load_pkcs7('smime-m2-sign-encrypt.txt') # After the above step, 'data' == None. # Decrypt p7. 'out' now contains a PKCS #7 signed blob. out = s.decrypt(p7) # Load the signer's cert. x509 = X509.load_cert(signer_cert) sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) # Load the signer's CA cert. st = X509.X509_Store() st.load_info(ca_cert) s.set_x509_store(st) # Recall 'out' contains a PKCS #7 blob. # Transform 'out'; verify the resulting PKCS #7 blob. p7_bio = BIO.MemoryBuffer(out) p7, data = SMIME.smime_load_pkcs7_bio(p7_bio) v = s.verify(p7) print v
def decrypt(key_path='/workspace/personal/python_test/keys/myKey.pem', cert_path='/workspace/personal/python_test/keys/myCert.pem'): # Instantiate an SMIME object. s = SMIME.SMIME() # Load private key and cert. s.load_key(key_path, cert_path) # Load the encrypted data. encrypted_data = """MIME-Version: 1.0 Content-Disposition: attachment; filename="smime.p7m" Content-Type: application/pkcs7-mime; smime-type=enveloped-data; name="smime.p7m" Content-Transfer-Encoding: base64 MIIC/AYJKoZIhvcNAQcDoIIC7TCCAukCAQAxggKlMIICoQIBADCBiDB7MQswCQYD VQQGEwJWTjEMMAoGA1UECAwDSENNMQwwCgYDVQQHDANIQ00xDDAKBgNVBAoMA1NF QTEMMAoGA1UECwwDQ09EMQ8wDQYDVQQDDAZBaXJQYXkxIzAhBgkqhkiG9w0BCQEW FGFpcnBheV92bkB2ZWQuY29tLnZuAgkAvMiAJGI+ZHswDQYJKoZIhvcNAQEBBQAE ggIAF8Wx6U5Sf2VXEBkfm8uhPey5tRJeCBLrWmjpkSCq7sm0vZV3CpRaT1LPYyjF ugS1EEAb36MPDZkTAg1NniyLMfVjoio2gUWlrBmdIiB6O8ElaHWYbqmsiFrhszGx XHDCTAQB6pXGqVE5lhjIBD92wqJSwmxlSwD0m4KG5JNv92fDvm3G5CgEGAjUYsWf Y1E2BJUoCDHUsD+4IKItlLJzHMMQc3e2SyGTlSjrayAVZsUbYRfunhr4o9uKsKM6 28h4Hs1I6ekZ1O2COCvM4k/Tv3o+rbLBXdRy27POOI2ksrY0ub96aw9Ks2QZTYoV c4iNCGEXVHr7PRwBgeDZKBH1xM929gsVcQOVCy5IaEUvSrlhg/VSMiOis3rYv1p+ R0Frd4Ep8RdaPMStUNDSU4Ia1FCzTpiWCNfPj9940U3vMoPu1l+q2WBbOPmrknaC pI6hqvFYGBVx4i0zfatoycs1S6p4EPKoe/XAe0Rosi94RKE8H6gQurmhYcKT+zwF boRGPnKs1rxVn2sHJ3KYmCGfgoWUmOzEHpmTelIt/lXHiPd4cIT42tvT1OLne0aU /Qvo1K1KffiEGC+hbHEG5Y/lH/9QYsYp7KiGyYdYj7QOnBv9d0taDXscYbdpTv8z Kbb39iPDQ07F6/MQ1C5GkIK6azMa+YKdMK4grtTHVXaPrLEwOwYJKoZIhvcNAQcB MBQGCCqGSIb3DQMHBAjBmOK7gvkV3oAYjNbjiFIv1Iu4gF+uSKW+zzQrU0Jiabgg """ data = BIO.MemoryBuffer(encrypted_data.encode()) p7, data = SMIME.smime_load_pkcs7_bio(data) # p7, data = SMIME.smime_load_pkcs7('/workspace/personal/python_test/keys/encrypt.txt') # Decrypt p7. out = s.decrypt(p7) return out
def smime_verify(ca_path, message): """Verify S/MIME pkcs7 signed message. You may debug certificate errors with command:: openssl smime -verify -in .tmp/test_verify_signature_file0/signed/signature.sig -CApath .tmp/test_verify_signature_file0/certs :param str ca_path: Path to CA certificate store :param bytes message: Message to verify :returns: Message data on succesful verification :rtype: bytes """ # SSLContext expects a byte string on Python 2 and Unicode on Python 3 ca_path = _to_str_path(ca_path) buf = BIO.MemoryBuffer(message) pkcs7, data = SMIME.smime_load_pkcs7_bio(buf) certificate_x509 = pkcs7.get0_signers(X509.X509_Stack()) context = SSL.Context() context.load_verify_locations(capath=ca_path) ca_store = context.get_cert_store() smime = SMIME.SMIME() smime.set_x509_store(ca_store) smime.set_x509_stack(certificate_x509) return smime.verify(pkcs7, data)
def test_verify_with_static_callback(self): s = SMIME.SMIME() x509 = X509.load_cert('tests/signer.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) st = X509.X509_Store() st.load_info('tests/ca.pem') st.set_verify_cb(verify_cb_rejects_cert_from_heikki_toivonen) s.set_x509_store(st) p7, data = SMIME.smime_load_pkcs7_bio(self.signed) self.assertIsInstance(p7, SMIME.PKCS7, p7) # Should reject certificate issued by Heikki Toivonen: with self.assertRaises(SMIME.PKCS7_Error): s.verify(p7, data) st.set_verify_cb(verify_cb_dummy_function) v = s.verify(p7, data) self.assertEqual(v, self.cleartext) st.set_verify_cb() v = s.verify(p7, data) self.assertEqual(v, self.cleartext)
def sv(): print 'test sign/verify...', buf = makebuf() s = SMIME.SMIME() # Load a private key. s.load_key('client.pem') # Sign. p7 = s.sign(buf, SMIME.PKCS7_DETACHED) # Output the stuff. buf = makebuf() # Recreate buf, because sign() has consumed it. bio = BIO.MemoryBuffer() s.write(bio, p7, buf) # Plumbing for verification: CA's cert. st = X509.X509_Store() st.load_info('ca.pem') s.set_x509_store(st) # Plumbing for verification: Signer's cert. x509 = X509.load_cert('client.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) # Verify. p7, buf = SMIME.smime_load_pkcs7_bio(bio) v = s.verify(p7, buf, flags=SMIME.PKCS7_DETACHED) if v: print 'ok' else: print 'not ok'
def sv(): print 'test sign/verify...', buf = makebuf() s = SMIME.SMIME() # Load a private key. s.load_key('client.pem') # Sign. p7 = s.sign(buf, SMIME.PKCS7_DETACHED) # Output the stuff. buf = makebuf() # Recreate buf, because sign() has consumed it. bio = BIO.MemoryBuffer() s.write(bio, p7, buf) # Plumbing for verification: CA's cert. st = X509.X509_Store() st.load_info('ca.pem') s.set_x509_store(st) # Plumbing for verification: Signer's cert. x509 = X509.load_cert('client.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) # Verify. p7, buf = SMIME.smime_load_pkcs7_bio(bio) v = s.verify(p7, buf, flags=SMIME.PKCS7_DETACHED) if v: print 'ok' else: print 'not ok'
def test_load_bad(self): s = SMIME.SMIME() with self.assertRaises(EVP.EVPError): s.load_key('tests/signer.pem', 'tests/signer.pem') with self.assertRaises(BIO.BIOError): SMIME.load_pkcs7('nosuchfile-dfg456') with self.assertRaises(SMIME.PKCS7_Error): SMIME.load_pkcs7('tests/signer.pem') with self.assertRaises(SMIME.PKCS7_Error): SMIME.load_pkcs7_bio(BIO.MemoryBuffer(b'no pkcs7')) with self.assertRaises(SMIME.SMIME_Error): SMIME.smime_load_pkcs7('tests/signer.pem') with self.assertRaises(SMIME.SMIME_Error): SMIME.smime_load_pkcs7_bio(BIO.MemoryBuffer(b'no pkcs7'))
def test_verify_with_static_callback(self): s = SMIME.SMIME() x509 = X509.load_cert('tests/signer.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) st = X509.X509_Store() st.load_info('tests/ca.pem') st.set_verify_cb(verify_cb_rejects_cert_from_heikki_toivonen) s.set_x509_store(st) p7, data = SMIME.smime_load_pkcs7_bio(self.signed) self.assertIsInstance(p7, SMIME.PKCS7, p7) # Should reject certificate issued by Heikki Toivonen: with self.assertRaises(SMIME.PKCS7_Error): s.verify(p7, data) st.set_verify_cb(verify_cb_dummy_function) v = s.verify(p7, data) self.assertEqual(v, self.cleartext) st.set_verify_cb() v = s.verify(p7, data) self.assertEqual(v, self.cleartext)
def verify_payload(msg, raw_sig, cert, ca_cert, verify_cert): # Load the public certificate of the signer signer = SMIME.SMIME() signer_key = X509.X509_Stack() signer_key.push(X509.load_cert(cert)) signer.set_x509_stack(signer_key) signer_store = X509.X509_Store() signer_store.load_info(ca_cert) signer.set_x509_store(signer_store) # Extract the pkcs7 signature and the data if raw_sig: raw_sig.strip() sig = "-----BEGIN PKCS7-----\n%s\n-----END PKCS7-----\n" % raw_sig.replace('\r\n', '\n') p7 = SMIME.load_pkcs7_bio(BIO.MemoryBuffer(sig)) data_bio = BIO.MemoryBuffer(msg) else: p7, data_bio = SMIME.smime_load_pkcs7_bio(BIO.MemoryBuffer(msg)) # Verify the signature against the message if verify_cert: signer.verify(p7, data_bio) else: # Don't verify the signer certificate if this flag is set signer.verify(p7, data_bio, SMIME.PKCS7_NOVERIFY)
def parse_content_block(content_block, privkey=None, pubkey=None): if content_block.content_binding == 'application/x-pks7-mime': if not privkey and not pubkey: return None inbuf = BIO.MemoryBuffer(BytesIO(content_block.content).read()) s = SMIME.SMIME() try: s.load_key(privkey, pubkey) p7, data = SMIME.smime_load_pkcs7_bio(inbuf) buf = s.decrypt(p7) except SMIME.PKCS7_Error: return None f = BytesIO(buf) new_block = f.read() f.close() return parse_content_block(tm.ContentBlock.from_xml(new_block), privkey, pubkey) elif content_block.content_binding == t.CB_STIX_XML_111: f = BytesIO(content_block.content) data = f.read() f.close() return data else: return None
def decrypt_payload(payload, key, passphrase): global key_pass key_pass = passphrase privkey = SMIME.SMIME() privkey.load_key(key, callback=get_key_passphrase) # Load the encrypted data. p7, data = SMIME.smime_load_pkcs7_bio(BIO.MemoryBuffer(payload)) return privkey.decrypt(p7)
def test_load_smime_bio(self): with open(self.filenameSmime, 'rb') as f: buf = BIO.MemoryBuffer(f.read()) a, b = SMIME.smime_load_pkcs7_bio(buf) self.assertIsInstance(a, SMIME.PKCS7, a) self.assertIsInstance(b, BIO.BIO, b) self.assertEqual(a.type(), SMIME.PKCS7_SIGNED)
def decrypt_payload(payload, key, passphrase): global key_pass key_pass = passphrase privkey = SMIME.SMIME() privkey.load_key(key, callback=getKeyPassphrase) # Load the encrypted data. p7, data = SMIME.smime_load_pkcs7_bio(BIO.MemoryBuffer(payload)) return privkey.decrypt(p7)
def test_signEncryptDecryptVerify(self): # sign buf = BIO.MemoryBuffer(self.cleartext) s = SMIME.SMIME() s.load_key('tests/signer_key.pem', 'tests/signer.pem') p7 = s.sign(buf) # encrypt x509 = X509.load_cert('tests/recipient.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) s.set_cipher(SMIME.Cipher('des_ede3_cbc')) tmp = BIO.MemoryBuffer() s.write(tmp, p7) p7 = s.encrypt(tmp) signedEncrypted = BIO.MemoryBuffer() s.write(signedEncrypted, p7) # decrypt s = SMIME.SMIME() s.load_key('tests/recipient_key.pem', 'tests/recipient.pem') p7, data = SMIME.smime_load_pkcs7_bio(signedEncrypted) out = s.decrypt(p7) # verify x509 = X509.load_cert('tests/signer.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) st = X509.X509_Store() st.load_info('tests/ca.pem') s.set_x509_store(st) p7_bio = BIO.MemoryBuffer(out) p7, data = SMIME.smime_load_pkcs7_bio(p7_bio) v = s.verify(p7) self.assertEqual(v, self.cleartext)
def test_signEncryptDecryptVerify(self): # sign buf = BIO.MemoryBuffer(self.cleartext) s = SMIME.SMIME() s.load_key('test/signer_key.pem', 'test/signer.pem') p7 = s.sign(buf) # encrypt x509 = X509.load_cert('test/recipient.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) s.set_cipher(SMIME.Cipher('des_ede3_cbc')) tmp = BIO.MemoryBuffer() s.write(tmp, p7) p7 = s.encrypt(tmp) signedEncrypted = BIO.MemoryBuffer() s.write(signedEncrypted, p7) # decrypt s = SMIME.SMIME() s.load_key('test/recipient_key.pem', 'test/recipient.pem') p7, data = SMIME.smime_load_pkcs7_bio(signedEncrypted) out = s.decrypt(p7) # verify x509 = X509.load_cert('test/signer.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) st = X509.X509_Store() st.load_info('test/ca.pem') s.set_x509_store(st) p7_bio = BIO.MemoryBuffer(out) p7, data = SMIME.smime_load_pkcs7_bio(p7_bio) v = s.verify(p7) assert v == self.cleartext
def test_load_bad(self): s = SMIME.SMIME() with self.assertRaises(EVP.EVPError): s.load_key('tests/signer.pem', 'tests/signer.pem') with self.assertRaises(BIO.BIOError): SMIME.load_pkcs7('nosuchfile-dfg456') with self.assertRaises(SMIME.PKCS7_Error): SMIME.load_pkcs7('tests/signer.pem') with self.assertRaises(SMIME.PKCS7_Error): SMIME.load_pkcs7_bio(BIO.MemoryBuffer('no pkcs7')) with self.assertRaises(SMIME.SMIME_Error): SMIME.smime_load_pkcs7('tests/signer.pem') with self.assertRaises(SMIME.SMIME_Error): SMIME.smime_load_pkcs7_bio(BIO.MemoryBuffer('no pkcs7'))
def test_load_smime_bio(self): with open(self.filenameSmime, 'rb') as f: buf = BIO.MemoryBuffer(f.read()) a, b = SMIME.smime_load_pkcs7_bio(buf) self.assertIsInstance(a, SMIME.PKCS7, a) self.assertIsInstance(b, BIO.BIO, b) self.assertEqual(a.type(), SMIME.PKCS7_SIGNED)
def Process(self,inputString): self.verified = False # Note we cast to a String type as unicode will not verify buf = BIO.MemoryBuffer(str(inputString)) sk = X509.X509_Stack() try: InputP7, Inputdata = SMIME.smime_load_pkcs7_bio(buf) except SMIME.SMIME_Error , e: raise smimeX509ValidationError(e)
def test_load_smime_bio(self): f = open(self.filenameSmime, 'rb') buf = BIO.MemoryBuffer(f.read()) f.close() a, b = SMIME.smime_load_pkcs7_bio(buf) assert isinstance(a, SMIME.PKCS7), a assert isinstance(b, BIO.BIO), b assert a.type() == SMIME.PKCS7_SIGNED
def validate_text(self,text_to_verify): buf = BIO.MemoryBuffer(text_to_verify) sk = X509.X509_Stack() p7, data = SMIME.smime_load_pkcs7_bio(buf) try: supplied_stack = p7.get0_signers(sk) except AttributeError, e: if str(e) == "PKCS7 instance has no attribute 'get0_signers'": self.logger.error('m2crypto version 0.18 is the minimum supported, please upgrade.') raise e
def test_decrypt(self): s = SMIME.SMIME() s.load_key('test/recipient_key.pem', 'test/recipient.pem') p7, data = SMIME.smime_load_pkcs7_bio(self.encrypted) assert isinstance(p7, SMIME.PKCS7), p7 self.assertRaises(SMIME.SMIME_Error, s.verify, p7) # No signer out = s.decrypt(p7) assert out == self.cleartext
def test_decryptBad(self): s = SMIME.SMIME() s.load_key('test/signer_key.pem', 'test/signer.pem') p7, data = SMIME.smime_load_pkcs7_bio(self.encrypted) assert isinstance(p7, SMIME.PKCS7), p7 self.assertRaises(SMIME.SMIME_Error, s.verify, p7) # No signer # Cannot decrypt: no recipient matches certificate self.assertRaises(SMIME.PKCS7_Error, s.decrypt, p7)
def test_decrypt(self): s = SMIME.SMIME() s.load_key('tests/recipient_key.pem', 'tests/recipient.pem') p7, data = SMIME.smime_load_pkcs7_bio(self.encrypted) self.assertIsInstance(p7, SMIME.PKCS7, p7) with self.assertRaises(SMIME.SMIME_Error): s.verify(p7) # No signer out = s.decrypt(p7) self.assertEqual(out, self.cleartext)
def test_decrypt(self): s = SMIME.SMIME() s.load_key('tests/recipient_key.pem', 'tests/recipient.pem') p7, data = SMIME.smime_load_pkcs7_bio(self.encrypted) self.assertIsInstance(p7, SMIME.PKCS7, p7) with self.assertRaises(SMIME.SMIME_Error): s.verify(p7) # No signer out = s.decrypt(p7) self.assertEqual(out, self.cleartext)
def test_verifyBad(self): s = SMIME.SMIME() x509 = X509.load_cert('test/recipient.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) st = X509.X509_Store() st.load_info('test/recipient.pem') s.set_x509_store(st) p7, data = SMIME.smime_load_pkcs7_bio(self.signed) assert isinstance(p7, SMIME.PKCS7), p7 self.assertRaises(SMIME.PKCS7_Error, s.verify, p7) # Bad signer
def decrypt(input_bio, private_key, cert, keyring_source, type): """ Decrypts the input data with the private key and the certificate from keyring source. @type input_bio: M2Crypto.BIO @param input_bio: input data to sign. @type private_key: filepath or M2Crypto.BIO or M2Crypto.EVP.PKey @param private_key: recipient private key reference, could be from file, from memory or from pkcs11 smartcard, based on keyring_soruce input parameter. @type cert: filepath or M2Crypto.BIO or M2Crypto.X509.X509 @param cert: recipient certificate, could be from filepath, from memory or from pkcs11 smartcard, based on keyring_soruce input parameter. @type keyring_source: str @keyword keyring_source: the type of the source for input certificate, used to recall the appropriate method for decrypter settings. Ammitted values are: file, memory, pkcs11. @type type: str @keyword type: specifies the type of input PKCS#7 data: PEM or DER @rtype: str @return: the decrypted data in plain form. @raise BadPKCS7Type: The requested PKCS#7 type is not valid. Ammitted values are PEM and DER. """ decrypter = SMIME.SMIME() set_keyring(decrypter, private_key, cert, keyring_source) try: if type == 'PEM': p7, data_bio = SMIME.smime_load_pkcs7_bio(input_bio) elif type == 'DER': p7 = SMIME.PKCS7(m2.pkcs7_read_bio_der(input_bio._ptr()), 1) else: logging.error('pkcs7 type error: unknown type') raise BadPKCS7Type('unknown type: ' + type + '; possible values: PEM, DER') except SMIME.SMIME_Error as e: logging.error('load pkcs7 error: ' + str(e)) pass try: decrypted_data = decrypter.decrypt(p7) except SMIME.SMIME_Error as e: logging.error('smime error: ' + str(e)) raise except SMIME.PKCS7_Error as e: logging.error('pkcs7 error: ' + str(e)) raise return decrypted_data.replace(b'\r', b'')
def verify(self, text): """ verifies a signed SMIME email returns a list of certificates used to sign the SMIME message on success text - string containing the SMIME signed message >>> v = Verifier('/etc/apache/ssl.crt/ca-bundle.crt') >>> v.verify('pippo') Traceback (most recent call last): File "<stdin>", line 1, in ? File "signer.py", line 23, in __init__ raise VerifierError, e VerifierError: cannot extract payloads from message >>> >>> certs = v.verify(test_email) >>> isinstance(certs, list) and len(certs) > 0 True >>> """ if self._smime is None: self._setup() buf = BIO.MemoryBuffer(text) try: p7, data_bio = SMIME.smime_load_pkcs7_bio(buf) except SystemError: # uncaught exception in M2Crypto raise VerifierError, "cannot extract payloads from message" if data_bio is not None: data = data_bio.read() data_bio = BIO.MemoryBuffer(data) sk3 = p7.get0_signers(X509.X509_Stack()) if len(sk3) == 0: raise VerifierError, "no certificates found in message" signer_certs = [] for cert in sk3: signer_certs.append( "-----BEGIN CERTIFICATE-----\n%s-----END CERTIFICATE-----" \ % base64.encodestring(cert.as_der())) self._smime.set_x509_stack(sk3) try: if data_bio is not None: v = self._smime.verify(p7, data_bio) else: v = self._smime.verify(p7) except SMIME.SMIME_Error, e: raise VerifierError, "message verification failed: %s" % e
def verify(self, text): """ verifies a signed SMIME email returns a list of certificates used to sign the SMIME message on success text - string containing the SMIME signed message >>> v = Verifier('/etc/apache/ssl.crt/ca-bundle.crt') >>> v.verify('pippo') Traceback (most recent call last): File "<stdin>", line 1, in ? File "signer.py", line 23, in __init__ raise VerifierError, e VerifierError: cannot extract payloads from message >>> >>> certs = v.verify(test_email) >>> isinstance(certs, list) and len(certs) > 0 True >>> """ if self._smime is None: self._setup() buf = BIO.MemoryBuffer(text) try: p7, data_bio = SMIME.smime_load_pkcs7_bio(buf) except SystemError: # uncaught exception in M2Crypto raise VerifierError, "cannot extract payloads from message" if data_bio is not None: data = data_bio.read() data_bio = BIO.MemoryBuffer(data) sk3 = p7.get0_signers(X509.X509_Stack()) if len(sk3) == 0: raise VerifierError, "no certificates found in message" signer_certs = [] for cert in sk3: signer_certs.append( "-----BEGIN CERTIFICATE-----\n%s-----END CERTIFICATE-----" \ % base64.encodestring(cert.as_der())) self._smime.set_x509_stack(sk3) try: if data_bio is not None: v = self._smime.verify(p7, data_bio) else: v = self._smime.verify(p7) except SMIME.SMIME_Error, e: raise VerifierError, "message verification failed: %s" % e
def decrypt(input_bio, private_key, cert, keyring_source, type): """ Decrypts the input data with the private key and the certificate from keyring source. @type input_bio: M2Crypto.BIO @param input_bio: input data to sign. @type private_key: filepath or M2Crypto.BIO or M2Crypto.EVP.PKey @param private_key: recipient private key reference, could be from file, from memory or from pkcs11 smartcard, based on keyring_soruce input parameter. @type cert: filepath or M2Crypto.BIO or M2Crypto.X509.X509 @param cert: recipient certificate, could be from filepath, from memory or from pkcs11 smartcard, based on keyring_soruce input parameter. @type keyring_source: str @keyword keyring_source: the type of the source for input certificate, used to recall the appropriate method for decrypter settings. Ammitted values are: file, memory, pkcs11. @type type: str @keyword type: specifies the type of input PKCS#7 data: PEM or DER @rtype: str @return: the decrypted data in plain form. @raise BadPKCS7Type: The requested PKCS#7 type is not valid. Ammitted values are PEM and DER. """ decrypter = SMIME.SMIME() set_keyring(decrypter, private_key, cert, keyring_source) try: if type == 'PEM': p7, data_bio = SMIME.smime_load_pkcs7_bio(input_bio) elif type == 'DER': p7 = SMIME.PKCS7(m2.pkcs7_read_bio_der(input_bio._ptr()), 1) else: logging.error('pkcs7 type error: unknown type') raise BadPKCS7Type('unknown type: ' + type + '; possible values: PEM, DER') except SMIME.SMIME_Error as e: logging.error('load pkcs7 error: ' + str(e)) pass try: decrypted_data = decrypter.decrypt(p7) except SMIME.SMIME_Error as e: logging.error('smime error: ' + str(e)) raise except SMIME.PKCS7_Error as e: logging.error('pkcs7 error: ' + str(e)) raise return decrypted_data.replace(b'\r', b'')
def image_by_sha512_writefile_json(self,treess,sha512,path): query_image = self.session.query(model.ImageInstance,model.ImageListInstance).\ filter(model.ImageInstance.fkimagelistinstance == model.ImageListInstance.id).\ filter(model.ImageInstance.sha512 == sha512) if query_image.count() == 0: self.log.warning('Message not found') return False fp = open(path,'w') for touple_set in query_image: image = touple_set[0] image_list = touple_set[1] buf = BIO.MemoryBuffer(str(image_list.data)) sk = X509.X509_Stack() p7, data = SMIME.smime_load_pkcs7_bio(buf) data_str = data.read() fp.write(data_str) fp.close()
def image_by_sha512_writefile_json(self,treess,sha512,path): query_image = self.session.query(model.ImageInstance,model.ImageListInstance).\ filter(model.ImageInstance.fkimagelistinstance == model.ImageListInstance.id).\ filter(model.ImageInstance.sha512 == sha512) if query_image.count() == 0: self.log.warning('Message not found') return False fp = open(path,'w') for touple_set in query_image: image = touple_set[0] image_list = touple_set[1] buf = BIO.MemoryBuffer(str(image_list.data)) sk = X509.X509_Stack() p7, data = SMIME.smime_load_pkcs7_bio(buf) data_str = data.read() fp.write(data_str) fp.close()
def dep_tokenupload(dep_id): # get DEP config dep = db_session.query(DEPConfig).filter(DEPConfig.id == dep_id).one() filedata = request.files['server_token_file'].stream.read() try: smime = filedata # load the encrypted file p7, data = SMIME.smime_load_pkcs7_bio(BIO.MemoryBuffer(str(smime))) # query DB to get cert & key from DB q = db_session.query(DBCertificate, DBPrivateKey).join( DBCertificate, DBPrivateKey.certificates).filter( DBCertificate.id == dep.certificate.id) cert, pk = q.one() # construct SMIME object using cert & key decryptor = SMIME.SMIME() decryptor.load_key_bio(BIO.MemoryBuffer(str(pk.pem_key)), BIO.MemoryBuffer(str(cert.pem_certificate))) # decrypt! out = decryptor.decrypt(p7) eml = Parser().parsestr(out).get_payload() if eml.startswith('-----BEGIN MESSAGE-----\n') and eml.endswith( '\n-----END MESSAGE-----\n'): myjson = eml[24:-23] except SMIME.SMIME_Error: # submitted file was not an SMIME encrypted file # try to just load the file in the hopes the json parser can read it myjson = filedata try: json_loaded = json.loads(myjson) dep.server_token = json_loaded db_session.commit() except ValueError: abort(400, 'Invalid server token supplied') return redirect('/admin/dep/index', Response=FixedLocationResponse)
def test_verify_with_method_callback(self): s = SMIME.SMIME() x509 = X509.load_cert('tests/signer.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) st = X509.X509_Store() st.load_info('tests/ca.pem') st.set_verify_cb(self.verify_cb_dummy_method) s.set_x509_store(st) p7, data = SMIME.smime_load_pkcs7_bio(self.signed) self.assertIsInstance(p7, SMIME.PKCS7, p7) v = s.verify(p7, data) self.assertEqual(v, self.cleartext)
def test_verify_with_method_callback(self): s = SMIME.SMIME() x509 = X509.load_cert('tests/signer.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) st = X509.X509_Store() st.load_info('tests/ca.pem') st.set_verify_cb(self.verify_cb_dummy_method) s.set_x509_store(st) p7, data = SMIME.smime_load_pkcs7_bio(self.signed) self.assertIsInstance(p7, SMIME.PKCS7, p7) v = s.verify(p7, data) self.assertEqual(v, self.cleartext)
def verify(input_bio, certstore_path, AUTO_SIGNED_CERT, type): """ Retrieves X.509 certificate from input data and verifies signed message using as certificate store input certstore, inspired by: U{http://code.activestate.com/recipes/285211/}. @type input_bio: M2Crypto.BIO @param input_bio: input data to verify @type certstore_path: filepath @param certstore_path: path to the file of the trusted certificates, for example /etc/ssl/certs/ca-certificats.crt. @type type: str @keyword type: specifies the type of input PKCS#7 data: PEM or DER @type AUTO_SIGNED_CERT: boolean @keyword AUTOSIGNED_CERT: to accept or not auto signed certificates as valid for verification. @rtype: list or None @return: a list of verified certificates retrieved from the original data if verification success, else None. @raise CertStoreNotAvailable: the reference certstore for verification is not available. @raise MissingSignerCertificate: the input PKCS#7 is not a signed PKCS#7. """ signer = SMIME.SMIME() cert_store = X509.X509_Store() if not os.access(certstore_path, os.R_OK): logging.error('certstore not available for verify') raise CertStoreNotAvailable('certstore not available %' % (certstore_path)) cert_store.load_info(certstore_path) signer.set_x509_store(cert_store) data_bio = None try: if type == 'PEM': p7, data_bio = SMIME.smime_load_pkcs7_bio(input_bio) elif type == 'DER': p7 = SMIME.PKCS7(m2.pkcs7_read_bio_der(input_bio._ptr()), 1) else: logging.error('pkcs7 type error: unknown type') raise BadPKCS7Type('unknown type: ' + type + '; possible values: PEM, DER') except SMIME.SMIME_Error, e: logging.error('load pkcs7 error: ' + str(e)) raise
def verify(input_bio, certstore_path, AUTO_SIGNED_CERT, type): """ Retrieves X.509 certificate from input data and verifies signed message using as certificate store input certstore, inspired by: U{http://code.activestate.com/recipes/285211/}. @type input_bio: M2Crypto.BIO @param input_bio: input data to verify @type certstore_path: filepath @param certstore_path: path to the file of the trusted certificates, for example /etc/ssl/certs/ca-certificats.crt. @type type: str @keyword type: specifies the type of input PKCS#7 data: PEM or DER @type AUTO_SIGNED_CERT: boolean @keyword AUTOSIGNED_CERT: to accept or not auto signed certificates as valid for verification. @rtype: list or None @return: a list of verified certificates retrieved from the original data if verification success, else None. @raise CertStoreNotAvailable: the reference certstore for verification is not available. @raise MissingSignerCertificate: the input PKCS#7 is not a signed PKCS#7. """ signer = SMIME.SMIME() cert_store = X509.X509_Store() if not os.access(certstore_path, os.R_OK): logging.error('certstore not available for verify') raise CertStoreNotAvailable('certstore not available %' % (certstore_path)) cert_store.load_info(certstore_path) signer.set_x509_store(cert_store) data_bio = None try: if type == 'PEM': p7, data_bio = SMIME.smime_load_pkcs7_bio(input_bio) elif type == 'DER': p7 = SMIME.PKCS7(m2.pkcs7_read_bio_der(input_bio._ptr()), 1) else: logging.error('pkcs7 type error: unknown type') raise BadPKCS7Type('unknown type: ' + type + '; possible values: PEM, DER') except SMIME.SMIME_Error, e: logging.error('load pkcs7 error: ' + str(e)) raise
def verify_payload(msg, raw_sig, cert, ca_cert, verify_cert): signer = SMIME.SMIME() signerKey = X509.X509_Stack() signerKey.push(X509.load_cert(cert)) signer.set_x509_stack(signerKey) signerStore = X509.X509_Store() signerStore.load_info(ca_cert) signer.set_x509_store(signerStore) if raw_sig: raw_sig.strip() sig = "-----BEGIN PKCS7-----\n%s\n-----END PKCS7-----\n"%raw_sig.replace('\r\n','\n') p7 = SMIME.load_pkcs7_bio(BIO.MemoryBuffer(sig)) data_bio = BIO.MemoryBuffer(msg) if verify_cert: signer.verify(p7, data_bio) else: signer.verify(p7, data_bio,SMIME.PKCS7_NOVERIFY) else: p7, data_bio = SMIME.smime_load_pkcs7_bio(BIO.MemoryBuffer(msg)) signer.verify(p7, data_bio)
def dep_tokenupload(dep_id): # get DEP config dep = db_session.query(DEPConfig).filter(DEPConfig.id == dep_id).one() filedata = request.files['server_token_file'].stream.read() try: smime = filedata # load the encrypted file p7, data = SMIME.smime_load_pkcs7_bio(BIO.MemoryBuffer(str(smime))) # query DB to get cert & key from DB q = db_session.query(DBCertificate, DBPrivateKey).join(DBCertificate, DBPrivateKey.certificates).filter(DBCertificate.id == dep.certificate.id) cert, pk = q.one() # construct SMIME object using cert & key decryptor = SMIME.SMIME() decryptor.load_key_bio(BIO.MemoryBuffer(str(pk.pem_key)), BIO.MemoryBuffer(str(cert.pem_certificate))) # decrypt! out = decryptor.decrypt(p7) eml = Parser().parsestr(out).get_payload() if eml.startswith('-----BEGIN MESSAGE-----\n') and eml.endswith('\n-----END MESSAGE-----\n'): myjson = eml[24:-23] except SMIME.SMIME_Error: # submitted file was not an SMIME encrypted file # try to just load the file in the hopes the json parser can read it myjson = filedata try: json_loaded = json.loads(myjson) dep.server_token = json_loaded db_session.commit() except ValueError: abort(400, 'Invalid server token supplied') return redirect('/admin/dep/index', Response=FixedLocationResponse)
def test_verify(self): s = SMIME.SMIME() x509 = X509.load_cert('tests/signer.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) st = X509.X509_Store() st.load_info('tests/ca.pem') s.set_x509_store(st) p7, data = SMIME.smime_load_pkcs7_bio(self.signed) self.assertIsInstance(p7, SMIME.PKCS7, p7) v = s.verify(p7, data) self.assertEqual(v, self.cleartext) t = p7.get0_signers(sk) self.assertEqual(len(t), 1) self.assertEqual(t[0].as_pem(), x509.as_pem(), t[0].as_text())
def test_verify(self): s = SMIME.SMIME() x509 = X509.load_cert('tests/signer.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) st = X509.X509_Store() st.load_info('tests/ca.pem') s.set_x509_store(st) p7, data = SMIME.smime_load_pkcs7_bio(self.signed) self.assertIsInstance(p7, SMIME.PKCS7, p7) v = s.verify(p7, data) self.assertEqual(v, self.cleartext) t = p7.get0_signers(sk) self.assertEqual(len(t), 1) self.assertEqual(t[0].as_pem(), x509.as_pem(), t[0].as_text())
def test_verify(self): s = SMIME.SMIME() x509 = X509.load_cert('test/signer.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) st = X509.X509_Store() st.load_info('test/ca.pem') s.set_x509_store(st) p7, data = SMIME.smime_load_pkcs7_bio(self.signed) assert isinstance(p7, SMIME.PKCS7), p7 v = s.verify(p7, data) assert v == self.cleartext t = p7.get0_signers(sk) assert len(t) == 1 assert t[0].as_pem() == x509.as_pem(), t[0].as_text()
def decrypt_message(encrypted_text, certificate, key, capath): ''' Decrypt the specified message using the certificate and key contained in the named PEM files. The capath should point to a directory holding all the CAs that we accept This decryption function can be used whether or not OpenSSL is used to encrypt the data ''' s = SMIME.SMIME() blob = BIO.MemoryBuffer(encrypted_text) # m2Crypto v0.17? Then need to add this line to smime_load_pkcs7_bio, # in SMIME.py, at line 98 # m2.bio_set_mem_eof_return(p7_bio._ptr(),0) # # Otherwise you get a 'not enough data' error from SMIME module # Alternatively, blob.write_close() also seems to fix this, but this # might need to be revisited if a later M2Crypto is used blob.write_close() s.load_key(key, certificate) p7, data = SMIME.smime_load_pkcs7_bio(blob) ########### # Write data to a temporary file, then decrypt it # Workaround because the above doesn't work with M2Crypto v0.17 #tmpfd,tmpname = tempfile.mkstemp() #os.write(tmpfd,encrypted_text) #os.close(tmpfd) #p7, data = SMIME.smime_load_pkcs7(tmpname) #os.remove(tmpname) ########## out = s.decrypt(p7) return out
def parse_content_block(content_block, privkey=None, pubkey=None): if content_block.content_binding == 'application/x-pks7-mime': if not privkey and not pubkey: return None inbuf = BIO.MemoryBuffer(StringIO(content_block.content).read()) s = SMIME.SMIME() try: s.load_key(privkey, pubkey) p7, data = SMIME.smime_load_pkcs7_bio(inbuf) buf = s.decrypt(p7) except SMIME.PKCS7_Error: return None f = StringIO(buf) new_block = f.read() f.close() return parse_content_block(tm.ContentBlock.from_xml(new_block), privkey, pubkey) elif content_block.content_binding == t.CB_STIX_XML_111: f = StringIO(content_block.content) data = f.read() f.close() return data else: return None
import httplib, urlparse from M2Crypto import BIO, SMIME, X509 conn = httplib.HTTPConnection("localhost:9095") conn.request("GET", "/smime/encrypted") res = conn.getresponse() if res.status != 200: print res.status raise Exception("Failed to connect") contentType = res.getheader("content-type") data = res.read() # Need to reconstruct a Mail message with content type # as SMIME wants it in that format bio = BIO.MemoryBuffer("Content-Type: ") bio.write(contentType) bio.write("\r\n\r\n") bio.write(data) s = SMIME.SMIME() s.load_key('src/main/resources/private.pem', 'src/main/resources/cert.pem') p7, d = SMIME.smime_load_pkcs7_bio(bio) out = s.decrypt(p7) print "--- Received Data ---" # It may contain headers like Content-Type, so you'll have to parse it print out
def testAllTheThings(self): """ Test the full scenario: multiple encrypted and plaintext recipients. Tests that multiple recipients can all read a message, and that recipients with no Identity records get plain text. """ count = 1 sender = Identity.objects.get(address="*****@*****.**") recipients = [identity.address for identity in Identity.objects.all()] recipients.extend(["*****@*****.**", "*****@*****.**"]) message = mail.EmailMultiAlternatives( self.text_template % count, self.text_template % count, sender.address, recipients, ) message.attach_alternative(self.html_template % count, "text/html") message.send() backend = mail.get_connection() self.assertEqual(len(backend.messages), 2) # # verify the encryption and signature # s = SMIME.SMIME() # Load the sender's cert. x509 = X509.load_cert_string(data.RECIPIENT1_CERTIFICATE) sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) # Load the sender's CA cert. st = X509.X509_Store() st.add_x509(x509) s.set_x509_store(st) # Decrypt the message as both encrypted recipients # # recipient 1 # recipient1_cert = BIO.MemoryBuffer( data.RECIPIENT1_CERTIFICATE.encode("UTF-8")) recipient1_key = BIO.MemoryBuffer(data.RECIPIENT1_KEY.encode("UTF-8")) s.load_key_bio(recipient1_key, recipient1_cert) msg = BIO.MemoryBuffer(backend.messages[1]["message"].encode("UTF-8")) p7, msg_data = SMIME.smime_load_pkcs7_bio(msg) out = s.decrypt(p7) # Verify the message msg = BIO.MemoryBuffer(out) p7, msg_data = SMIME.smime_load_pkcs7_bio(msg) verified_msg = s.verify(p7, msg_data) self.assertTrue(verified_msg) # # recipient 2 # recipient2_cert = BIO.MemoryBuffer( data.RECIPIENT2_CERTIFICATE.encode("UTF-8")) recipient2_key = BIO.MemoryBuffer(data.RECIPIENT2_KEY.encode("UTF-8")) s.load_key_bio(recipient2_key, recipient2_cert) msg = BIO.MemoryBuffer(backend.messages[1]["message"].encode("UTF-8")) p7, msg_data = SMIME.smime_load_pkcs7_bio(msg) out = s.decrypt(p7) # Verify the message msg = BIO.MemoryBuffer(out) p7, msg_data = SMIME.smime_load_pkcs7_bio(msg) self.assertTrue(s.verify(p7, msg_data)) # verify that the plaintext also got through msg = BIO.MemoryBuffer(backend.messages[1]["message"].encode("UTF-8"))
def verify(input_bio, certstore_path, AUTO_SIGNED_CERT, type): """ Retrieves X.509 certificate from input data and verifies signed message using as certificate store input certstore, inspired by: U{http://code.activestate.com/recipes/285211/}. @type input_bio: M2Crypto.BIO @param input_bio: input data to verify @type certstore_path: filepath @param certstore_path: path to the file of the trusted certificates, for example /etc/ssl/certs/ca-certificats.crt. @type type: str @keyword type: specifies the type of input PKCS#7 data: PEM or DER @type AUTO_SIGNED_CERT: boolean @keyword AUTOSIGNED_CERT: to accept or not auto signed certificates as valid for verification. @rtype: list or None @return: a list of verified certificates retrieved from the original data if verification success, else None. @raise CertStoreNotAvailable: the reference certstore for verification is not available. @raise MissingSignerCertificate: the input PKCS#7 is not a signed PKCS#7. """ signer = SMIME.SMIME() cert_store = X509.X509_Store() if not os.access(certstore_path, os.R_OK): logging.error('certstore not available for verify') raise CertStoreNotAvailable('certstore not available %' % (certstore_path)) cert_store.load_info(certstore_path) signer.set_x509_store(cert_store) data_bio = None try: if type == 'PEM': p7, data_bio = SMIME.smime_load_pkcs7_bio(input_bio) elif type == 'DER': p7 = SMIME.PKCS7(m2.pkcs7_read_bio_der(input_bio._ptr()), 1) else: logging.error('pkcs7 type error: unknown type') raise BadPKCS7Type('unknown type: ' + type + '; possible values: PEM, DER') except SMIME.SMIME_Error as e: logging.error('load pkcs7 error: ' + str(e)) raise if data_bio is not None: data = data_bio.read() data_bio = BIO_from_buffer(data) sk3 = p7.get0_signers(X509.X509_Stack()) if len(sk3) == 0: logging.error('missing certificate') raise MissingSignerCertificate('missing certificate') signer_certs = [] for cert in sk3: signer_certs.append( "-----BEGIN CERTIFICATE-----\n{}-----END CERTIFICATE-----\n" .format(base64.encodestring(cert.as_der()).decode('ascii'))) signer.set_x509_stack(sk3) v = None try: if AUTO_SIGNED_CERT: v = signer.verify(p7, data_bio, flags=SMIME.PKCS7_NOVERIFY) else: v = signer.verify(p7, data_bio) except SMIME.SMIME_Error as e: logging.error('smime error: ' + str(e)) raise except SMIME.PKCS7_Error as e: logging.error('pkcs7 error: ' + str(e)) raise if data_bio is not None and data != v and v is not None: return return signer_certs
s = SMIME.SMIME() # Load private key and cert. s.load_key('mycert-private.pem', 'mycert.pem') # Load the signed/encrypted data. p7, data = SMIME.smime_load_pkcs7('target/python_encrypted_signed.txt') # After the above step, 'data' == None. # Decrypt p7. 'out' now contains a PKCS #7 signed blob. out = s.decrypt(p7) # Load the signer's cert. x509 = X509.load_cert('mycert.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) # Load the signer's CA cert. In this case, because the signer's # cert is self-signed, it is the signer's cert itself. st = X509.X509_Store() st.load_info('mycert.pem') s.set_x509_store(st) # Recall 'out' contains a PKCS #7 blob. # Transform 'out'; verify the resulting PKCS #7 blob. p7_bio = BIO.MemoryBuffer(out) p7, data = SMIME.smime_load_pkcs7_bio(p7_bio) v = s.verify(p7, data) print v
def download(self): downloadsneeded = {} QueryResults = self.Session.query(model.Subscription,model.ImageDefinition,model.ImageListInstance,model.ImageInstance).\ filter(model.ImageDefinition.cache == 1).\ filter(model.ImageDefinition.latest == model.ImageInstance.id).\ filter(model.ImageDefinition.id == model.ImageInstance.fkIdentifier).\ filter(model.ImageListInstance.expired == None).\ filter(model.Subscription.authorised == True).\ filter(model.Subscription.imagelist_latest == model.ImageListInstance.id).\ filter(model.ImageDefinition.subscription == model.Subscription.id).\ filter(model.ImageListInstance.id == model.ImageInstance.fkimagelistinstance) for line in QueryResults: sub = line[0] imageDef = line[1] imageListInst = line[2] ImageInst = line[3] uuid = imageDef.identifier details = {'hv:uri' : str(ImageInst.uri), 'sl:checksum:sha512' : str(ImageInst.sha512), 'hv:size': int(ImageInst.size), 'dc:identifier' : uuid, 'message' : str(imageListInst.data), 'hv:imagelist.dc:identifier' : str(sub.identifier), 'msgHash' : str(imageListInst.data_hash), 'dc:title' : str(ImageInst.title), 'dc:description' : str(ImageInst.description), 'hv:version' : str(ImageInst.version), 'hv:hypervisor' : str(ImageInst.hypervisor), 'sl:arch' : str(ImageInst.arch), 'sl:comments' : str(ImageInst.comments), 'sl:os' : str(ImageInst.os), 'sl:osversion' : str(ImageInst.osversion), # And now the legacy values 'uri' : str(ImageInst.uri), 'sha512' : str(ImageInst.sha512), 'size': int(ImageInst.size), 'uuid' : uuid, } # read message buf = BIO.MemoryBuffer(str(imageListInst.data)) sk = X509.X509_Stack() p7, data = SMIME.smime_load_pkcs7_bio(buf) data_str = data.read() try: jsonData = json.loads(str(data_str)) except ValueError: self.log.error("proiblem reading JSON") continue if jsonData == None: self.log.error("Downlaoded jsonData was not valid image.") continue vmilist = VMimageListDecoder(jsonData) if vmilist == None: self.log.error("Downlaoded metadata from '%s' was not valid image list Object." % (subscriptionKey)) # For Vo handling imagelist_vo = vmilist.metadata.get(u'ad:vo') if imagelist_vo != None: if len(imagelist_vo) > 0: details['hv:imagelist.ad:vo'] = imagelist_vo matchingImage = None for image in vmilist.images: if "dc:identifier" in image.metadata.keys(): if uuid == image.metadata["dc:identifier"]: matchingImage = image if matchingImage != None: for metafield in matchingImage.metadata.keys(): newfield = "hv:image.%s" % (metafield) details[newfield] = matchingImage.metadata[metafield] if not uuid in self.cacheDir.index.keys(): downloadsneeded[uuid] = details continue if self.cacheDir.index[uuid]['sha512'] != str(ImageInst.sha512): downloadsneeded[uuid] = details continue for key in downloadsneeded.keys(): if not self.DownloadDir.indexAdd(downloadsneeded[key]): self.log.error("Failed to add metadata request to download file '%s'." % (key)) continue if not self.DownloadDir.download(key): self.log.error("Failed to download file '%s'." % (key)) self.DownloadDir.indexSave() continue if self.callbackEventAvailablePrefix != None: metadata = {} metadata.update(dict(downloadsneeded[key])) metadata.update(dict(self.DownloadDir.index[key])) #for pkey in metadata.keys(): # print "%s---%s" % (pkey, metadata[pkey]) self.callbackEventAvailablePrefix(metadata) if not self.cacheDir.moveFrom(self.DownloadDir,key): self.log.error("Failed to Move file '%s' into the enbdorsed directory." % (key)) continue self.DownloadDir.indexSave() self.cacheDir.indexSave() self.log.info("moved file %s" % (key)) if self.callbackEventAvailablePostfix != None: metadata = {} #metadata.update(dict(ddownloadsneeded[key])) metadata.update(dict(self.cacheDir.index[key])) self.callbackEventAvailablePostfix(metadata) return True
import httplib, urlparse from M2Crypto import BIO, SMIME, X509 conn = httplib.HTTPConnection("localhost:9095") conn.request("GET", "/smime/encrypted") res = conn.getresponse() if res.status != 200: print res.status raise Exception("Failed to connect") contentType = res.getheader("content-type") data = res.read() # Need to reconstruct a Mail message with content type # as SMIME wants it in that format bio = BIO.MemoryBuffer("Content-Type: ") bio.write(contentType) bio.write("\r\n\r\n") bio.write(data) s = SMIME.SMIME() s.load_key("src/main/resources/private.pem", "src/main/resources/cert.pem") p7, d = SMIME.smime_load_pkcs7_bio(bio) out = s.decrypt(p7) print "--- Received Data ---" # It may contain headers like Content-Type, so you'll have to parse it print out
raise Exception("Failed to connect") contentType = res.getheader("content-type") data = res.read() # Need to reconstruct a Mail message with content type # as SMIME wants it in that format bio = BIO.MemoryBuffer("Content-Type: ") bio.write(contentType) bio.write("\r\n\r\n") bio.write(data) s = SMIME.SMIME() s.load_key('src/main/resources/private.pem', 'src/main/resources/cert.pem') p7, d = SMIME.smime_load_pkcs7_bio(bio) out = s.decrypt(p7) # Load the signer's cert. x509 = X509.load_cert('src/main/resources/cert.pem') sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) # Load the signer's CA cert. In this case, because the signer's # cert is self-signed, it is the signer's cert itself. st = X509.X509_Store() st.load_info('src/main/resources/cert.pem') s.set_x509_store(st) # Recall 'out' contains a PKCS #7 blob.
def download(self): downloadsneeded = {} QueryResults = self.Session.query(model.Subscription,model.ImageDefinition,model.ImageListInstance,model.ImageInstance).\ filter(model.ImageDefinition.cache == 1).\ filter(model.ImageDefinition.latest == model.ImageInstance.id).\ filter(model.ImageDefinition.id == model.ImageInstance.fkIdentifier).\ filter(model.ImageListInstance.expired == None).\ filter(model.Subscription.authorised == True).\ filter(model.Subscription.imagelist_latest == model.ImageListInstance.id).\ filter(model.ImageDefinition.subscription == model.Subscription.id).\ filter(model.ImageListInstance.id == model.ImageInstance.fkimagelistinstance) for line in QueryResults: sub = line[0] imageDef = line[1] imageListInst = line[2] ImageInst = line[3] uuid = imageDef.identifier details = { 'hv:uri': str(ImageInst.uri), 'sl:checksum:sha512': str(ImageInst.sha512), 'hv:size': int(ImageInst.size), 'dc:identifier': uuid, 'message': str(imageListInst.data), 'hv:imagelist.dc:identifier': str(sub.identifier), 'msgHash': str(imageListInst.data_hash), 'dc:title': str(ImageInst.title), 'dc:description': str(ImageInst.description), 'hv:version': str(ImageInst.version), 'hv:hypervisor': str(ImageInst.hypervisor), 'sl:arch': str(ImageInst.arch), 'sl:comments': str(ImageInst.comments), 'sl:os': str(ImageInst.os), 'sl:osversion': str(ImageInst.osversion), # And now the legacy values 'uri': str(ImageInst.uri), 'sha512': str(ImageInst.sha512), 'size': int(ImageInst.size), 'uuid': uuid, } # read message buf = BIO.MemoryBuffer(str(imageListInst.data)) sk = X509.X509_Stack() p7, data = SMIME.smime_load_pkcs7_bio(buf) data_str = data.read() try: jsonData = json.loads(str(data_str)) except ValueError: self.log.error("proiblem reading JSON") continue if jsonData == None: self.log.error("Downlaoded jsonData was not valid image.") continue vmilist = VMimageListDecoder(jsonData) if vmilist == None: self.log.error( "Downlaoded metadata from '%s' was not valid image list Object." % (subscriptionKey)) # For Vo handling imagelist_vo = vmilist.metadata.get(u'ad:vo') if imagelist_vo != None: if len(imagelist_vo) > 0: details['hv:imagelist.ad:vo'] = imagelist_vo matchingImage = None for image in vmilist.images: if "dc:identifier" in image.metadata.keys(): if uuid == image.metadata["dc:identifier"]: matchingImage = image if matchingImage != None: for metafield in matchingImage.metadata.keys(): newfield = "hv:image.%s" % (metafield) details[newfield] = matchingImage.metadata[metafield] if not uuid in self.cacheDir.index.keys(): downloadsneeded[uuid] = details continue if self.cacheDir.index[uuid]['sha512'] != str(ImageInst.sha512): downloadsneeded[uuid] = details continue for key in downloadsneeded.keys(): if not self.DownloadDir.indexAdd(downloadsneeded[key]): self.log.error( "Failed to add metadata request to download file '%s'." % (key)) continue if not self.DownloadDir.download(key): self.log.error("Failed to download file '%s'." % (key)) self.DownloadDir.indexSave() continue if self.callbackEventAvailablePrefix != None: metadata = {} metadata.update(dict(downloadsneeded[key])) metadata.update(dict(self.DownloadDir.index[key])) #for pkey in metadata.keys(): # print "%s---%s" % (pkey, metadata[pkey]) self.callbackEventAvailablePrefix(metadata) if not self.cacheDir.moveFrom(self.DownloadDir, key): self.log.error( "Failed to Move file '%s' into the enbdorsed directory." % (key)) continue self.DownloadDir.indexSave() self.cacheDir.indexSave() self.log.info("moved file %s" % (key)) if self.callbackEventAvailablePostfix != None: metadata = {} #metadata.update(dict(ddownloadsneeded[key])) metadata.update(dict(self.cacheDir.index[key])) self.callbackEventAvailablePostfix(metadata) return True
def validate_text(self, text_to_verify): buf = BIO.MemoryBuffer(text_to_verify) sk = X509.X509_Stack() p7, data = SMIME.smime_load_pkcs7_bio(buf) try: supplied_stack = p7.get0_signers(sk) except AttributeError as e: if str(e) == "PKCS7 instance has no attribute 'get0_signers'": self.logger.error( 'm2crypto version 0.18 is the minimum supported, please upgrade.' ) raise e issuer_dn = None signer_dn = None signer_serial_number = None supplied_list = [] while True: one = supplied_stack.pop() if one == None: break else: supplied_list.append(one) certdictionary = [] for item in supplied_list: itemdictionary = {} issuer_dn = str(item.get_issuer()) signer_dn = str(item.get_subject()) cert_sn = str(item.get_serial_number()) itemdictionary['subject'] = signer_dn itemdictionary['issuer'] = issuer_dn itemdictionary['serial_number'] = cert_sn certdictionary.append(itemdictionary) # Only validate files signed with a certificate issued a correct CA if not len(certdictionary) == 1: if len(certdictionary) > 1: raise SmimeX509ValidationError( "To many keys in signature file.") if len(certdictionary) == 0: raise SmimeX509ValidationError("No keys found signature file.") baseCert = certdictionary[0] if not self.ca_name_spaces.checkCrlHeirarchy( baseCert['subject'], baseCert['issuer'], baseCert['serial_number']): raise SmimeX509ValidationError("Cert %s is expired") CaHeirarchy = self.ca_name_spaces.GetCaHeirarchListWithCaDn( baseCert['issuer']) s = SMIME.SMIME() sk = X509.X509_Stack() for item in CaHeirarchy: foundKey = self.ca_name_spaces.GetKeyByDn(item) if foundKey == None: raise SmimeX509ValidationError("No trusted Key for '%s'" % (item)) sk.push(foundKey) s.set_x509_stack(sk) st = X509.X509_Store() #print self.ca_name_spaces.ca[correct_issuer_dn].ca_filename for item in CaHeirarchy: foundKey = self.ca_name_spaces.GetKeyByDn(item) if foundKey == None: raise SmimeX509ValidationError("No trusted Key for '%s'" % (item)) st.add_cert(foundKey) s.set_x509_store(st) try: v = s.verify(p7, data) #when python 2.6 is the min version of supported #change back to #except SMIME.PKCS7_Error as e: except SMIME.PKCS7_Error as e: raise SmimeX509ValidationError(e) output = { 'signer_dn': signer_dn, 'issuer_dn': issuer_dn, 'data': data.read() } return output
def testAllTheThings(self): """ Test the full scenario: multiple encrypted and plaintext recipients. Tests that multiple recipients can all read a message, and that recipients with no Identity records get plain text. """ count = 1 sender = Identity.objects.get(address='*****@*****.**') recipients = [identity.address for identity in Identity.objects.all()] recipients.extend([ '*****@*****.**', '*****@*****.**' ]) message = mail.EmailMultiAlternatives( self.text_template % count, self.text_template % count, sender.address, recipients ) message.attach_alternative(self.html_template % count, "text/html") message.send() backend = mail.get_connection() self.assertEqual(len(backend.messages), 2) # # verify the encryption and signature # s = SMIME.SMIME() # Load the sender's cert. x509 = X509.load_cert_string(data.RECIPIENT1_CERTIFICATE) sk = X509.X509_Stack() sk.push(x509) s.set_x509_stack(sk) # Load the sender's CA cert. st = X509.X509_Store() st.add_x509(x509) s.set_x509_store(st) # Decrypt the message as both encrypted recipients # # recipient 1 # recipient1_cert = BIO.MemoryBuffer(data.RECIPIENT1_CERTIFICATE) recipient1_key = BIO.MemoryBuffer(data.RECIPIENT1_KEY) s.load_key_bio(recipient1_key, recipient1_cert) msg = BIO.MemoryBuffer(backend.messages[1]['message']) p7, msg_data = SMIME.smime_load_pkcs7_bio(msg) out = s.decrypt(p7) # Verify the message msg = BIO.MemoryBuffer(out) p7, msg_data = SMIME.smime_load_pkcs7_bio(msg) verified_msg = s.verify(p7, msg_data) self.assertTrue(verified_msg) # # recipient 2 # recipient2_cert = BIO.MemoryBuffer(data.RECIPIENT2_CERTIFICATE) recipient2_key = BIO.MemoryBuffer(data.RECIPIENT2_KEY) s.load_key_bio(recipient2_key, recipient2_cert) msg = BIO.MemoryBuffer(backend.messages[1]['message']) p7, msg_data = SMIME.smime_load_pkcs7_bio(msg) out = s.decrypt(p7) # Verify the message msg = BIO.MemoryBuffer(out) p7, msg_data = SMIME.smime_load_pkcs7_bio(msg) self.assertTrue(s.verify(p7, msg_data)) # verify that the plaintext also got through msg = BIO.MemoryBuffer(backend.messages[1]['message'])