summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorEndi S. Dewata <edewata@redhat.com>2016-05-11 19:33:51 +0200
committerEndi S. Dewata <edewata@redhat.com>2016-05-12 17:32:55 +0200
commitb5b2ea7762b2fb3a7248aa779ce4f4ebd1e7ef9b (patch)
treec26d8b8c10057c4361e155dca2441a6ea6b8d882
parentd39e24e48c74e31e2232768040b264d372e1fe76 (diff)
Fixed missing CSR extensions for external CA case.
The deployment tool has been modified to generate CSR with basic constraints and key usage extensions for the externally-signed CA signing certificate. https://fedorahosted.org/pki/ticket/2312
-rw-r--r--base/common/python/pki/nssdb.py50
-rw-r--r--base/server/python/pki/server/deployment/scriptlets/configuration.py23
2 files changed, 70 insertions, 3 deletions
diff --git a/base/common/python/pki/nssdb.py b/base/common/python/pki/nssdb.py
index 30b1d4793..7908461b1 100644
--- a/base/common/python/pki/nssdb.py
+++ b/base/common/python/pki/nssdb.py
@@ -169,7 +169,10 @@ class NSSDatabase(object):
def create_request(self, subject_dn, request_file, noise_file=None,
key_type=None, key_size=None, curve=None,
- hash_alg=None):
+ hash_alg=None,
+ basic_constraints_ext=None,
+ key_usage_ext=None):
+
tmpdir = tempfile.mkdtemp()
try:
@@ -185,6 +188,8 @@ class NSSDatabase(object):
binary_request_file = os.path.join(tmpdir, 'request.bin')
+ keystroke = ''
+
cmd = [
'certutil',
'-R',
@@ -213,8 +218,49 @@ class NSSDatabase(object):
if hash_alg:
cmd.extend(['-Z', hash_alg])
+ if key_usage_ext:
+
+ cmd.extend(['--keyUsage'])
+
+ usages = []
+ for usage in key_usage_ext:
+ if key_usage_ext[usage]:
+ usages.append(usage)
+
+ cmd.extend([','.join(usages)])
+
+ if basic_constraints_ext:
+
+ cmd.extend(['-2', hash_alg])
+
+ # Is this a CA certificate [y/N]?
+ if basic_constraints_ext['ca']:
+ keystroke += 'y'
+
+ keystroke += '\n'
+
+ # Enter the path length constraint, enter to skip [<0 for unlimited path]:
+ if basic_constraints_ext['path_length'] is not None:
+ keystroke += basic_constraints_ext['path_length']
+
+ keystroke += '\n'
+
+ # Is this a critical extension [y/N]?
+ if basic_constraints_ext['critical']:
+ keystroke += 'y'
+
+ keystroke += '\n'
+
# generate binary request
- subprocess.check_call(cmd)
+ p = subprocess.Popen(cmd, stdin=subprocess.PIPE, stdout=subprocess.PIPE,
+ stderr=subprocess.STDOUT)
+
+ p.communicate(keystroke)
+
+ rc = p.wait()
+
+ if rc:
+ raise Exception('Failed to generate certificate request. RC: %d' % rc)
# encode binary request in base-64
b64_request_file = os.path.join(tmpdir, 'request.b64')
diff --git a/base/server/python/pki/server/deployment/scriptlets/configuration.py b/base/server/python/pki/server/deployment/scriptlets/configuration.py
index 373b58ef4..6da08c587 100644
--- a/base/server/python/pki/server/deployment/scriptlets/configuration.py
+++ b/base/server/python/pki/server/deployment/scriptlets/configuration.py
@@ -98,6 +98,7 @@ class PkiScriptlet(pkiscriptlet.AbstractBasePkiScriptlet):
if external and step_one: # external CA step 1 only
# Determine CA signing key type and algorithm
+
key_type = deployer.mdict['pki_ca_signing_key_type']
key_alg = deployer.mdict['pki_ca_signing_key_algorithm']
@@ -125,19 +126,38 @@ class PkiScriptlet(pkiscriptlet.AbstractBasePkiScriptlet):
# If filename specified, generate CA cert request and
# import it into CS.cfg.
+
external_csr_path = deployer.mdict['pki_external_csr_path']
if external_csr_path:
+
config.pki_log.info(
"generating CA signing certificate request in %s",
external_csr_path,
extra=config.PKI_INDENTATION_LEVEL_2)
+
+ basic_constraints_ext = {
+ 'ca': True,
+ 'path_length': None,
+ 'critical': True
+ }
+
+ key_usage_ext = {
+ 'digitalSignature': True,
+ 'nonRepudiation': True,
+ 'certSigning': True,
+ 'crlSigning': True,
+ 'critical': True
+ }
+
nssdb.create_request(
subject_dn=deployer.mdict['pki_ca_signing_subject_dn'],
request_file=external_csr_path,
key_type=key_type,
key_size=key_size,
curve=curve,
- hash_alg=hash_alg)
+ hash_alg=hash_alg,
+ basic_constraints_ext=basic_constraints_ext,
+ key_usage_ext=key_usage_ext)
with open(external_csr_path) as f:
signing_csr = f.read()
@@ -148,6 +168,7 @@ class PkiScriptlet(pkiscriptlet.AbstractBasePkiScriptlet):
# This is needed by IPA to detect step 1 completion.
# See is_step_one_done() in ipaserver/install/cainstance.py.
+
subsystem.config['preop.ca.type'] = 'otherca'
subsystem.save()