diff --git a/ipaserver/install/cainstance.py b/ipaserver/install/cainstance.py index 8e0e69888..6165fd192 100644 --- a/ipaserver/install/cainstance.py +++ b/ipaserver/install/cainstance.py @@ -1280,6 +1280,12 @@ class CAInstance(DogtagInstance): os.chmod(keyfile, 0o600) os.chown(keyfile, pent.pw_uid, pent.pw_gid) + def __remove_lightweight_ca_key_retrieval_custodia(self): + keyfile = os.path.join(paths.PKI_TOMCAT, + self.service_prefix + '.keys') + keystore = IPAKEMKeys({'server_keys': keyfile}) + keystore.remove_keys(self.service_prefix) + def add_lightweight_ca_tracking_requests(self): try: lwcas = api.Backend.ldap2.get_entries( diff --git a/ipaserver/install/custodiainstance.py b/ipaserver/install/custodiainstance.py index 7ca23b408..46998164a 100644 --- a/ipaserver/install/custodiainstance.py +++ b/ipaserver/install/custodiainstance.py @@ -64,10 +64,22 @@ class CustodiaInstance(SimpleServiceInstance): realm=self.realm) sysupgrade.set_upgrade_state('custodia', 'installed', True) + def uninstall(self): + super(CustodiaInstance, self).uninstall() + keystore = IPAKEMKeys({ + 'server_keys': self.server_keys, + 'ldap_uri': self.ldap_uri + }) + keystore.remove_server_keys() + installutils.remove_file(self.config_file) + sysupgrade.set_upgrade_state('custodia', 'installed', False) + def __gen_keys(self): - KeyStore = IPAKEMKeys({'server_keys': self.server_keys, - 'ldap_uri': self.ldap_uri}) - KeyStore.generate_server_keys() + keystore = IPAKEMKeys({ + 'server_keys': self.server_keys, + 'ldap_uri': self.ldap_uri + }) + keystore.generate_server_keys() def upgrade_instance(self): if not sysupgrade.get_upgrade_state("custodia", "installed"): diff --git a/ipaserver/secrets/kem.py b/ipaserver/secrets/kem.py index 8fecd5bb5..266d975d5 100644 --- a/ipaserver/secrets/kem.py +++ b/ipaserver/secrets/kem.py @@ -1,6 +1,8 @@ # Copyright (C) 2015 IPA Project Contributors, see COPYING for license from __future__ import print_function + +import errno import os # pylint: disable=import-error @@ -124,6 +126,12 @@ class KEMLdap(iSecLdap): encoding=serialization.Encoding.DER, format=serialization.PublicFormat.SubjectPublicKeyInfo) + def _get_dn(self, usage, principal): + servicename, host = principal.split('@')[0].split('/') + name = '%s/%s' % (KEY_USAGE_MAP[usage], host) + service_rdn = ('cn', servicename) if servicename != 'host' else DN() + return DN(('cn', name), service_rdn, self.keysbase) + def set_key(self, usage, principal, key): """ Write key for the host or service. @@ -137,24 +145,35 @@ class KEMLdap(iSecLdap): """ public_key = self._format_public_key(key) + dn = self._get_dn(usage, principal) conn = self.connect() - servicename, host = principal.split('@')[0].split('/') - name = '%s/%s' % (KEY_USAGE_MAP[usage], host) - service_rdn = ('cn', servicename) if servicename != 'host' else DN() - dn = str(DN(('cn', name), service_rdn, self.keysbase)) try: mods = [('objectClass', [b'nsContainer', b'ipaKeyPolicy', b'ipaPublicKeyObject', b'groupOfPrincipals']), - ('cn', name.encode('utf-8')), + ('cn', dn[0].value.encode('utf-8')), ('ipaKeyUsage', RFC5280_USAGE_MAP[usage].encode('utf-8')), ('memberPrincipal', principal.encode('utf-8')), ('ipaPublicKey', public_key)] - conn.add_s(dn, mods) + conn.add_s(str(dn), mods) except ldap.ALREADY_EXISTS: mods = [(ldap.MOD_REPLACE, 'ipaPublicKey', public_key)] - conn.modify_s(dn, mods) + conn.modify_s(str(dn), mods) + + def del_key(self, usage, principal): + """Delete key for host or service + + :returns: DN of removed key or None when key was not found + """ + dn = self._get_dn(usage, principal) + conn = self.connect() + try: + conn.delete_s(str(dn)) + except ldap.NO_SUCH_OBJECT: + return None + else: + return dn def newServerKeys(path, keyid): @@ -216,6 +235,24 @@ class IPAKEMKeys(KEMKeysStore): ldapconn.set_key(KEY_USAGE_SIG, principal, pubkeys[0]) ldapconn.set_key(KEY_USAGE_ENC, principal, pubkeys[1]) + def remove_server_keys(self): + """Remove keys from LDAP and disk + """ + self.remove_keys('host') + + def remove_keys(self, servicename): + """Remove keys from LDAP and disk + """ + principal = '%s/%s@%s' % (servicename, self.host, self.realm) + ldapconn = KEMLdap(self.ldap_uri) + ldapconn.del_key(KEY_USAGE_SIG, principal) + ldapconn.del_key(KEY_USAGE_ENC, principal) + try: + os.unlink(self.config['server_keys']) + except OSError as e: + if e.errno != errno.ENOENT: + raise + @property def server_keys(self): if self._server_keys is None: