diff options
Diffstat (limited to 'scripts')
-rw-r--r-- | scripts/rpki/cms.py | 27 | ||||
-rw-r--r-- | scripts/rpki/x509.py | 43 | ||||
-rwxr-xr-x | scripts/rpkid.py | 19 |
3 files changed, 71 insertions, 18 deletions
diff --git a/scripts/rpki/cms.py b/scripts/rpki/cms.py index 86a73643..af237c31 100644 --- a/scripts/rpki/cms.py +++ b/scripts/rpki/cms.py @@ -10,19 +10,18 @@ import os, rpki.x509, rpki.exceptions, lxml.etree # openssl smime -sign -nodetach -outform DER -signer biz-certs/Alice-EE.cer -certfile biz-certs/Alice-CA.cer -inkey biz-certs/Alice-EE.key -in PLAN -out PLAN.der -def encode(xml, key, cert_files): +def encode(xml, keypair, certs): """Encode a chunk of XML as CMS signed with a specified key and bag of certificates. We have to sort the certificates into the correct order before the OpenSSL CLI tool will accept them. rpki.x509 handles that for us. """ - certs = rpki.x509.X509_chain() - certs.load_from_PEM(cert_files) certs.chainsort() signer_filename = "cms.tmp.signer.pem" certfile_filename = "cms.tmp.certfile.pem" + plaintext_filename = "cms.tmp.plaintext" f = open(signer_filename, "w") f.write(certs[0].get_PEM()) @@ -33,14 +32,20 @@ def encode(xml, key, cert_files): f.write(cert.get_PEM()) f.close() - i,o = os.popen2(["openssl", "smime", "-sign", "-nodetach", "-outform", "DER", "-signer", signer_filename, "-certfile", certfile_filename, "-inkey", key]) - i.write(xml) + f = open(plaintext_filename, "w") + f.write(xml) + f.close() + + i,o = os.popen2(("openssl", "smime", "-sign", "-nodetach", "-outform", "DER", "-signer", signer_filename, + "-certfile", certfile_filename, "-inkey", "/dev/stdin", "-in", plaintext_filename)) + i.write(keypair.get_PEM()) i.close() cms = o.read() o.close() os.unlink(signer_filename) os.unlink(certfile_filename) + os.unlink(plaintext_filename) return cms @@ -54,18 +59,28 @@ def decode(cms, ta): verification, we raise an exception. """ - i,o,e = os.popen3(["openssl", "smime", "-verify", "-inform", "DER", "-CAfile", ta]) + ta_filename = "cms.tmp.ta.pem" + + f = open(ta_filename, "w") + f.write(ta.get_PEM()) + f.close() + + i,o,e = os.popen3(("openssl", "smime", "-verify", "-inform", "DER", "-CAfile", ta_filename)) i.write(cms) i.close() xml = o.read() o.close() status = e.read() e.close() + + os.unlink(ta_filename) + if status == "Verification successful\n": return xml else: raise rpki.exceptions.CMSVerificationFailed, "CMS verification failed with status %s" % status + def xml_decode(elt, ta): """Composite routine to decode CMS-wrapped XML.""" return lxml.etree.fromstring(decode(elt, ta)) diff --git a/scripts/rpki/x509.py b/scripts/rpki/x509.py index 58c1ab06..3eb16c7d 100644 --- a/scripts/rpki/x509.py +++ b/scripts/rpki/x509.py @@ -13,7 +13,7 @@ some of the nasty details. This involves a lot of format conversion. """ import POW, tlslite.api, POW.pkix, base64, time -import rpki.exceptions, rpki.resource_set +import rpki.exceptions, rpki.resource_set, rpki.manifest class PEM_converter(object): """Convert between DER and PEM encodings for various kinds of ASN.1 data.""" @@ -291,6 +291,18 @@ class X509_chain(list): packages. """ + def __init__(self, *args, **kw): + if args: + self[:] = args + elif "PEM_files" in kw: + self.load_from_PEM(kw["PEM_files"]) + elif "DER_files" in kw: + self.load_from_DER(kw["DER_files"]) + elif "Auto_files" in kw: + self.load_from_Auto(kw["Auto_files"]) + elif kw: + raise TypeError + def chainsort(self): """Sort a bag of certs into a chain, leaf first. @@ -334,6 +346,10 @@ class X509_chain(list): """Load a set of certs from a list of DER files.""" self.extend([X509(DER_file=f) for f in files]) + def load_from_Auto(self, files): + """Load a set of certs from a list of DER or PEM files (guessing).""" + self.extend([X509(Auto_file=f) for f in files]) + class PKCS10_Request(DER_object): """Class to hold a PKCS #10 request.""" @@ -434,3 +450,28 @@ class RSA_Keypair(DER_object): def get_public_DER(self): return self.get_POW().derWrite(POW.RSA_PUBLIC_KEY) + +class Manifest(DER_object): + """Class to hold a signed manifest.""" + + formats = ("DER", "POWpkix") + pem_converter = PEM_converter("RPKI MANIFEST") + + def get_DER(self): + """Get the DER value of this manifest.""" + assert not self.empty() + if self.DER: + return self.DER + if self.POWpkix: + self.DER = self.POWpkix.toString() + return self.get_DER() + raise rpki.exceptions.DERObjectConversionError, "No conversion path to DER available" + + def get_POWpkix(self): + """Get the POW.pkix value of this manifest.""" + assert not self.empty() + if not self.POWpkix: + mani = rpki.manifest.Manifest() + mani.fromString(self.get_DER()) + self.POWpkix = mani + return self.POWpkix diff --git a/scripts/rpkid.py b/scripts/rpkid.py index 885e888a..b1f88fd5 100755 --- a/scripts/rpkid.py +++ b/scripts/rpkid.py @@ -6,7 +6,7 @@ framework onto which I'm bolting various parts for testing. """ import tlslite.api, MySQLdb, xml.sax, lxml.etree, lxml.sax, POW, POW.pkix, traceback, os, time -import rpki.https, rpki.config, rpki.resource_set, rpki.up_down, rpki.left_right, rpki.relaxng, rpki.cms, rpki.exceptions +import rpki.https, rpki.config, rpki.resource_set, rpki.up_down, rpki.left_right, rpki.relaxng, rpki.cms, rpki.exceptions, rpki.x509 def left_right_handler(query, path): try: @@ -62,17 +62,14 @@ gctx.db = MySQLdb.connect(user = gctx.cfg.get(gctx.cfg_section, "sql-username" gctx.cur = gctx.db.cursor() -gctx.cms_ta_irdb = gctx.cfg.get(gctx.cfg_section, "cms-ta-irdb") -gctx.cms_ta_irbe = gctx.cfg.get(gctx.cfg_section, "cms-ta-irbe") -gctx.cms_key = gctx.cfg.get(gctx.cfg_section, "cms-key") -gctx.cms_certs = gctx.cfg.multiget(gctx.cfg_section, "cms-cert") +gctx.cms_ta_irdb = rpki.x509.X509(Auto_file = gctx.cfg.get(gctx.cfg_section, "cms-ta-irdb")) +gctx.cms_ta_irbe = rpki.x509.X509(Auto_file = gctx.cfg.get(gctx.cfg_section, "cms-ta-irbe")) +gctx.cms_key = rpki.x509.RSA_Keypair(Auto_file = gctx.cfg.get(gctx.cfg_section, "cms-key")) +gctx.cms_certs = rpki.x509.X509_chain(Auto_files = gctx.cfg.multiget(gctx.cfg_section, "cms-cert")) -gctx.https_key = rpki.x509.RSA_Keypair(PEM_file = gctx.cfg.get(gctx.cfg_section, "https-key")) -gctx.https_certs = certChain = rpki.x509.X509_chain() -gctx.https_tas = rpki.x509.X509_chain() - -gctx.https_certs.load_from_PEM(gctx.cfg.multiget(gctx.cfg_section, "https-cert")) -gctx.https_tas.load_from_PEM(gctx.cfg.multiget(gctx.cfg_section, "https-ta")) +gctx.https_key = rpki.x509.RSA_Keypair(Auto_file = gctx.cfg.get(gctx.cfg_section, "https-key")) +gctx.https_certs = rpki.x509.X509_chain(Auto_files = gctx.cfg.multiget(gctx.cfg_section, "https-cert")) +gctx.https_tas = rpki.x509.X509_chain(Auto_files = gctx.cfg.multiget(gctx.cfg_section, "https-ta")) gctx.irdb_host = gctx.cfg.get(gctx.cfg_section, "irdb-host") gctx.irdb_port = gctx.cfg.get(gctx.cfg_section, "irdb-port") |