mirror of
https://github.com/kovidgoyal/calibre.git
synced 2025-07-09 03:04:10 -04:00
Add the CA:TRUE basic constraint when generating a CA certificate
This commit is contained in:
parent
7da4a00a9b
commit
3511b4e5e4
@ -97,7 +97,7 @@ static PyObject* create_rsa_cert_req(PyObject *self, PyObject *args) {
|
|||||||
RSA *KeyPair = NULL;
|
RSA *KeyPair = NULL;
|
||||||
PyObject *capsule = NULL, *ans = NULL, *t = NULL;
|
PyObject *capsule = NULL, *ans = NULL, *t = NULL;
|
||||||
X509_NAME *Name = NULL;
|
X509_NAME *Name = NULL;
|
||||||
char *common_name = NULL, *country = NULL, *state = NULL, *locality = NULL, *org = NULL, *org_unit = NULL, *email = NULL, buf[1024];
|
char *common_name = NULL, *country = NULL, *state = NULL, *locality = NULL, *org = NULL, *org_unit = NULL, *email = NULL, *basic_constraints = NULL, buf[1024];
|
||||||
X509_REQ *Cert = NULL;
|
X509_REQ *Cert = NULL;
|
||||||
EVP_PKEY *PrivateKey = NULL;
|
EVP_PKEY *PrivateKey = NULL;
|
||||||
PyObject *alt_names = NULL;
|
PyObject *alt_names = NULL;
|
||||||
@ -105,7 +105,7 @@ static PyObject* create_rsa_cert_req(PyObject *self, PyObject *args) {
|
|||||||
Py_ssize_t i = 0;
|
Py_ssize_t i = 0;
|
||||||
STACK_OF(X509_EXTENSION) *exts = NULL;
|
STACK_OF(X509_EXTENSION) *exts = NULL;
|
||||||
|
|
||||||
if(!PyArg_ParseTuple(args, "OOszzzzzz", &capsule, &alt_names, &common_name, &country, &state, &locality, &org, &org_unit, &email)) return NULL;
|
if(!PyArg_ParseTuple(args, "OOszzzzzzz", &capsule, &alt_names, &common_name, &country, &state, &locality, &org, &org_unit, &email, &basic_constraints)) return NULL;
|
||||||
if(!PyCapsule_CheckExact(capsule)) return PyErr_Format(PyExc_TypeError, "The key is not a capsule object");
|
if(!PyCapsule_CheckExact(capsule)) return PyErr_Format(PyExc_TypeError, "The key is not a capsule object");
|
||||||
if(!PySequence_Check(alt_names)) return PyErr_Format(PyExc_TypeError, "alt_names must be a sequence");
|
if(!PySequence_Check(alt_names)) return PyErr_Format(PyExc_TypeError, "alt_names must be a sequence");
|
||||||
KeyPair = PyCapsule_GetPointer(capsule, NULL);
|
KeyPair = PyCapsule_GetPointer(capsule, NULL);
|
||||||
@ -123,7 +123,7 @@ static PyObject* create_rsa_cert_req(PyObject *self, PyObject *args) {
|
|||||||
if (!add_entry(Name, "emailAddress", email)) goto error;
|
if (!add_entry(Name, "emailAddress", email)) goto error;
|
||||||
if (!add_entry(Name, "CN", common_name)) goto error;
|
if (!add_entry(Name, "CN", common_name)) goto error;
|
||||||
|
|
||||||
if (PySequence_Length(alt_names) > 0) {
|
if (PySequence_Length(alt_names) > 0 || basic_constraints) {
|
||||||
exts = sk_X509_EXTENSION_new_null();
|
exts = sk_X509_EXTENSION_new_null();
|
||||||
if (!exts) { set_error("sk_X509_EXTENSION_new_null"); goto error; }
|
if (!exts) { set_error("sk_X509_EXTENSION_new_null"); goto error; }
|
||||||
for (i = 0; i < PySequence_Length(alt_names); i++) {
|
for (i = 0; i < PySequence_Length(alt_names); i++) {
|
||||||
@ -133,6 +133,9 @@ static PyObject* create_rsa_cert_req(PyObject *self, PyObject *args) {
|
|||||||
Py_XDECREF(t);
|
Py_XDECREF(t);
|
||||||
if(!add_ext(exts, NID_subject_alt_name, buf)) goto error;
|
if(!add_ext(exts, NID_subject_alt_name, buf)) goto error;
|
||||||
}
|
}
|
||||||
|
if (basic_constraints) {
|
||||||
|
if(!add_ext(exts, NID_basic_constraints, basic_constraints)) goto error;
|
||||||
|
}
|
||||||
X509_REQ_add_extensions(Cert, exts);
|
X509_REQ_add_extensions(Cert, exts);
|
||||||
sk_X509_EXTENSION_pop_free(exts, X509_EXTENSION_free);
|
sk_X509_EXTENSION_pop_free(exts, X509_EXTENSION_free);
|
||||||
}
|
}
|
||||||
@ -243,13 +246,11 @@ static PyObject* create_rsa_cert(PyObject *self, PyObject *args) {
|
|||||||
if (!Name) { set_error("X509_REQ_get_subject_name(CA_cert)"); goto error; }
|
if (!Name) { set_error("X509_REQ_get_subject_name(CA_cert)"); goto error; }
|
||||||
if (!X509_set_issuer_name(Cert, Name)) { set_error("X509_set_issuer_name"); goto error; }
|
if (!X509_set_issuer_name(Cert, Name)) { set_error("X509_set_issuer_name"); goto error; }
|
||||||
|
|
||||||
if (!req_is_for_CA_cert) {
|
exts = X509_REQ_get_extensions(req);
|
||||||
exts = X509_REQ_get_extensions(req);
|
if (exts) {
|
||||||
if (exts) {
|
X509V3_set_ctx(&ctx, CA_cert, Cert, NULL, NULL, 0);
|
||||||
X509V3_set_ctx(&ctx, CA_cert, Cert, NULL, NULL, 0);
|
for (i = 0; i < sk_X509_EXTENSION_num(exts); i++) {
|
||||||
for (i = 0; i < sk_X509_EXTENSION_num(exts); i++) {
|
if(!X509_add_ext(Cert, sk_X509_EXTENSION_value(exts, i), -1)) { set_error("X509_add_ext"); goto error; }
|
||||||
if(!X509_add_ext(Cert, sk_X509_EXTENSION_value(exts, i), -1)) { set_error("X509_add_ext"); goto error; }
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -9,7 +9,7 @@ __copyright__ = '2015, Kovid Goyal <kovid at kovidgoyal.net>'
|
|||||||
from calibre.constants import plugins
|
from calibre.constants import plugins
|
||||||
certgen, err = plugins['certgen']
|
certgen, err = plugins['certgen']
|
||||||
if err:
|
if err:
|
||||||
raise ImportError('Failed to load teh certgen module with error: %s' % err)
|
raise ImportError('Failed to load the certgen module with error: %s' % err)
|
||||||
|
|
||||||
|
|
||||||
def create_key_pair(size=2048):
|
def create_key_pair(size=2048):
|
||||||
@ -19,7 +19,7 @@ def create_key_pair(size=2048):
|
|||||||
def create_cert_request(
|
def create_cert_request(
|
||||||
key_pair, common_name,
|
key_pair, common_name,
|
||||||
country='IN', state='Maharashtra', locality='Mumbai', organization=None,
|
country='IN', state='Maharashtra', locality='Mumbai', organization=None,
|
||||||
organizational_unit=None, email_address=None, alt_names=()
|
organizational_unit=None, email_address=None, alt_names=(), basic_constraints=None
|
||||||
):
|
):
|
||||||
def enc(x):
|
def enc(x):
|
||||||
if isinstance(x, type('')):
|
if isinstance(x, type('')):
|
||||||
@ -27,7 +27,7 @@ def create_cert_request(
|
|||||||
return x or None
|
return x or None
|
||||||
return certgen.create_rsa_cert_req(
|
return certgen.create_rsa_cert_req(
|
||||||
key_pair, tuple(bytes(enc(x)) for x in alt_names if x),
|
key_pair, tuple(bytes(enc(x)) for x in alt_names if x),
|
||||||
*map(enc, (common_name, country, state, locality, organization, organizational_unit, email_address))
|
*map(enc, (common_name, country, state, locality, organization, organizational_unit, email_address, basic_constraints))
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
@ -59,7 +59,7 @@ def create_server_cert(
|
|||||||
):
|
):
|
||||||
# Create the Certificate Authority
|
# Create the Certificate Authority
|
||||||
cakey = create_key_pair(key_size)
|
cakey = create_key_pair(key_size)
|
||||||
careq = create_cert_request(cakey, ca_name)
|
careq = create_cert_request(cakey, ca_name, basic_constraints='CA:TRUE')
|
||||||
cacert = create_ca_cert(careq, cakey)
|
cacert = create_ca_cert(careq, cakey)
|
||||||
|
|
||||||
# Create the server certificate issued by the newly created CA
|
# Create the server certificate issued by the newly created CA
|
||||||
@ -81,8 +81,11 @@ def create_server_cert(
|
|||||||
export(ca_key_file, cakey, serialize_key, encrypt_key_with_password)
|
export(ca_key_file, cakey, serialize_key, encrypt_key_with_password)
|
||||||
return cacert, cakey, cert, pkey
|
return cacert, cakey, cert, pkey
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
cacert, cakey, cert, pkey = create_server_cert('test.me', alt_names=['1.test.me', '*.all.test.me'])
|
cacert, cakey, cert, pkey = create_server_cert('test.me', alt_names=['1.test.me', '*.all.test.me'])
|
||||||
|
print("CA Certificate")
|
||||||
|
print (cert_info(cacert).encode('utf-8'))
|
||||||
|
print(), print(), print()
|
||||||
|
print('Server Certificate')
|
||||||
print (cert_info(cert).encode('utf-8'))
|
print (cert_info(cert).encode('utf-8'))
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user