blob: a3319c0a31cc1f91ece35f18b3ea4a2786cd0990 [file] [log] [blame]
Jean-Paul Calderone897bc252008-02-18 20:50:23 -05001/*
2 * pkcs12.c
3 *
Jean-Paul Calderone8671c852011-03-02 19:26:20 -05004 * Copyright (C) AB Strakt
5 * See LICENSE for details.
Jean-Paul Calderone897bc252008-02-18 20:50:23 -05006 *
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -04007 * Certificate transport (PKCS12) handling code,
Jean-Paul Calderone897bc252008-02-18 20:50:23 -05008 * mostly thin wrappers around OpenSSL.
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -04009 * See the file RATIONALE for a short explanation of why
Jean-Paul Calderone897bc252008-02-18 20:50:23 -050010 * this module was written.
11 *
12 * Reviewed 2001-07-23
13 */
14#include <Python.h>
15#define crypto_MODULE
16#include "crypto.h"
17
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -040018/*
19 * PKCS12 is a standard exchange format for digital certificates.
Jean-Paul Calderone897bc252008-02-18 20:50:23 -050020 * See e.g. the OpenSSL homepage http://www.openssl.org/ for more information
21 */
22
23static void crypto_PKCS12_dealloc(crypto_PKCS12Obj *self);
Jean-Paul Calderoned0a98762009-07-25 21:23:01 -040024static int crypto_PKCS12_clear(crypto_PKCS12Obj *self);
Jean-Paul Calderone897bc252008-02-18 20:50:23 -050025
26static char crypto_PKCS12_get_certificate_doc[] = "\n\
27Return certificate portion of the PKCS12 structure\n\
28\n\
Jean-Paul Calderone54bcc832009-05-27 14:06:48 -040029@return: X509 object containing the certificate\n\
Jean-Paul Calderone897bc252008-02-18 20:50:23 -050030";
31static PyObject *
32crypto_PKCS12_get_certificate(crypto_PKCS12Obj *self, PyObject *args)
33{
34 if (!PyArg_ParseTuple(args, ":get_certificate"))
35 return NULL;
36
37 Py_INCREF(self->cert);
38 return self->cert;
39}
40
Rick Dean623ee362009-07-17 12:22:16 -050041static char crypto_PKCS12_set_certificate_doc[] = "\n\
Rick Deane182f482009-07-17 14:49:48 -050042Replace the certificate portion of the PKCS12 structure\n\
Rick Dean623ee362009-07-17 12:22:16 -050043\n\
Rick Deane182f482009-07-17 14:49:48 -050044@param cert: The new certificate.\n\
Jean-Paul Calderonebade3132009-07-24 21:27:13 -040045@type cert: L{X509} or L{NoneType}\n\
Rick Dean379917c2009-07-21 11:37:41 -050046@return: None\n\
Rick Dean623ee362009-07-17 12:22:16 -050047";
Rick Dean38a05c82009-07-18 01:41:30 -050048static PyObject *
Jean-Paul Calderonebade3132009-07-24 21:27:13 -040049crypto_PKCS12_set_certificate(crypto_PKCS12Obj *self, PyObject *args, PyObject *keywds) {
Rick Dean623ee362009-07-17 12:22:16 -050050 PyObject *cert = NULL;
51 static char *kwlist[] = {"cert", NULL};
52
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -040053 if (!PyArg_ParseTupleAndKeywords(args, keywds, "O:set_certificate",
Rick Dean623ee362009-07-17 12:22:16 -050054 kwlist, &cert))
55 return NULL;
56
Jean-Paul Calderonebade3132009-07-24 21:27:13 -040057 if (cert != Py_None && ! crypto_X509_Check(cert)) {
Rick Dean623ee362009-07-17 12:22:16 -050058 PyErr_SetString(PyExc_TypeError, "cert must be type X509 or None");
59 return NULL;
60 }
61
62 Py_INCREF(cert); /* Make consistent before calling Py_DECREF() */
Rick Dean585cd9e2009-07-18 14:58:11 -050063 Py_DECREF(self->cert);
Rick Dean623ee362009-07-17 12:22:16 -050064 self->cert = cert;
65
Rick Dean38a05c82009-07-18 01:41:30 -050066 Py_INCREF(Py_None);
67 return Py_None;
Rick Dean623ee362009-07-17 12:22:16 -050068}
69
Jean-Paul Calderone897bc252008-02-18 20:50:23 -050070static char crypto_PKCS12_get_privatekey_doc[] = "\n\
71Return private key portion of the PKCS12 structure\n\
72\n\
Jean-Paul Calderone54bcc832009-05-27 14:06:48 -040073@returns: PKey object containing the private key\n\
Jean-Paul Calderone897bc252008-02-18 20:50:23 -050074";
Rick Dean623ee362009-07-17 12:22:16 -050075static crypto_PKeyObj *
Jean-Paul Calderone897bc252008-02-18 20:50:23 -050076crypto_PKCS12_get_privatekey(crypto_PKCS12Obj *self, PyObject *args)
77{
78 if (!PyArg_ParseTuple(args, ":get_privatekey"))
79 return NULL;
80
81 Py_INCREF(self->key);
Rick Dean864e15e2009-07-17 15:21:23 -050082 return (crypto_PKeyObj *) self->key;
Rick Dean623ee362009-07-17 12:22:16 -050083}
84
85static char crypto_PKCS12_set_privatekey_doc[] = "\n\
Rick Deane182f482009-07-17 14:49:48 -050086Replace or set the certificate portion of the PKCS12 structure\n\
Rick Dean623ee362009-07-17 12:22:16 -050087\n\
Rick Deane182f482009-07-17 14:49:48 -050088@param pkey: The new private key.\n\
89@type pkey: L{PKey}\n\
90@return: None\n\
Rick Dean623ee362009-07-17 12:22:16 -050091";
Rick Dean38a05c82009-07-18 01:41:30 -050092static PyObject *
Jean-Paul Calderoned8665432009-07-24 21:28:52 -040093crypto_PKCS12_set_privatekey(crypto_PKCS12Obj *self, PyObject *args, PyObject *keywds) {
Rick Dean623ee362009-07-17 12:22:16 -050094 PyObject *pkey = NULL;
95 static char *kwlist[] = {"pkey", NULL};
96
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -040097 if (!PyArg_ParseTupleAndKeywords(args, keywds, "O:set_privatekey",
Rick Dean623ee362009-07-17 12:22:16 -050098 kwlist, &pkey))
99 return NULL;
100
Jean-Paul Calderoned8665432009-07-24 21:28:52 -0400101 if (pkey != Py_None && ! crypto_PKey_Check(pkey)) {
Rick Dean623ee362009-07-17 12:22:16 -0500102 PyErr_SetString(PyExc_TypeError, "pkey must be type X509 or None");
103 return NULL;
104 }
105
106 Py_INCREF(pkey); /* Make consistent before calling Py_DECREF() */
Rick Dean585cd9e2009-07-18 14:58:11 -0500107 Py_DECREF(self->key);
Rick Dean623ee362009-07-17 12:22:16 -0500108 self->key = pkey;
109
Rick Dean38a05c82009-07-18 01:41:30 -0500110 Py_INCREF(Py_None);
111 return Py_None;
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500112}
113
114static char crypto_PKCS12_get_ca_certificates_doc[] = "\n\
115Return CA certificates within of the PKCS12 object\n\
116\n\
Jean-Paul Calderone54bcc832009-05-27 14:06:48 -0400117@return: A newly created tuple containing the CA certificates in the chain,\n\
118 if any are present, or None if no CA certificates are present.\n\
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500119";
120static PyObject *
121crypto_PKCS12_get_ca_certificates(crypto_PKCS12Obj *self, PyObject *args)
122{
123 if (!PyArg_ParseTuple(args, ":get_ca_certificates"))
124 return NULL;
125
126 Py_INCREF(self->cacerts);
127 return self->cacerts;
128}
129
Rick Dean623ee362009-07-17 12:22:16 -0500130static char crypto_PKCS12_set_ca_certificates_doc[] = "\n\
Rick Deane182f482009-07-17 14:49:48 -0500131Replace or set the CA certificates withing the PKCS12 object.\n\
Rick Dean623ee362009-07-17 12:22:16 -0500132\n\
Rick Deane182f482009-07-17 14:49:48 -0500133@param cacerts: The new CA certificates.\n\
Jean-Paul Calderoned8665432009-07-24 21:28:52 -0400134@type cacerts: Iterable of L{X509} or L{NoneType}\n\
Rick Deane182f482009-07-17 14:49:48 -0500135@return: None\n\
Rick Dean623ee362009-07-17 12:22:16 -0500136";
Rick Dean38a05c82009-07-18 01:41:30 -0500137static PyObject *
Rick Dean623ee362009-07-17 12:22:16 -0500138crypto_PKCS12_set_ca_certificates(crypto_PKCS12Obj *self, PyObject *args, PyObject *keywds)
139{
Jean-Paul Calderone499fa1d2009-07-24 21:15:30 -0400140 PyObject *obj;
Rick Dean623ee362009-07-17 12:22:16 -0500141 PyObject *cacerts;
142 static char *kwlist[] = {"cacerts", NULL};
Rick Dean25bcc1f2009-07-20 11:53:13 -0500143 int i, len; /* Py_ssize_t for Python 2.5+ */
Rick Dean623ee362009-07-17 12:22:16 -0500144
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -0400145 if (!PyArg_ParseTupleAndKeywords(args, keywds, "O:set_ca_certificates",
Rick Dean623ee362009-07-17 12:22:16 -0500146 kwlist, &cacerts))
147 return NULL;
148 if (cacerts == Py_None) {
Rick Deane84d1462009-07-24 09:27:01 -0500149 Py_INCREF(cacerts);
Jean-Paul Calderone206c2272009-07-24 21:22:38 -0400150 } else {
151 /* It's iterable */
Rick Deane84d1462009-07-24 09:27:01 -0500152 cacerts = PySequence_Tuple(cacerts);
Jean-Paul Calderone206c2272009-07-24 21:22:38 -0400153 if (cacerts == NULL) {
Rick Deane84d1462009-07-24 09:27:01 -0500154 return NULL;
155 }
Jean-Paul Calderone206c2272009-07-24 21:22:38 -0400156 len = PyTuple_Size(cacerts);
157
Rick Dean48305252009-07-18 15:28:38 -0500158 /* Check is's a simple list filled only with X509 objects. */
Jean-Paul Calderone206c2272009-07-24 21:22:38 -0400159 for (i = 0; i < len; i++) {
Jean-Paul Calderone4c6b72e2009-07-24 21:18:51 -0400160 obj = PyTuple_GetItem(cacerts, i);
Jean-Paul Calderonefed4d152009-07-24 21:23:57 -0400161 if (!crypto_X509_Check(obj)) {
Rick Deane84d1462009-07-24 09:27:01 -0500162 Py_DECREF(cacerts);
Rick Deane84d1462009-07-24 09:27:01 -0500163 PyErr_SetString(PyExc_TypeError, "iterable must only contain X509Type");
Rick Dean623ee362009-07-17 12:22:16 -0500164 return NULL;
165 }
Rick Dean623ee362009-07-17 12:22:16 -0500166 }
Rick Dean623ee362009-07-17 12:22:16 -0500167 }
168
Rick Dean585cd9e2009-07-18 14:58:11 -0500169 Py_DECREF(self->cacerts);
Rick Dean623ee362009-07-17 12:22:16 -0500170 self->cacerts = cacerts;
171
Rick Dean38a05c82009-07-18 01:41:30 -0500172 Py_INCREF(Py_None);
173 return Py_None;
Rick Dean623ee362009-07-17 12:22:16 -0500174}
175
Rick Dean42d69e12009-07-20 11:36:08 -0500176static char crypto_PKCS12_get_friendlyname_doc[] = "\n\
177Return friendly name portion of the PKCS12 structure\n\
178\n\
179@returns: String containing the friendlyname\n\
180";
Rick Dean99251c22009-07-24 09:32:46 -0500181static PyObject *
Jean-Paul Calderone4a45cbc2009-07-24 21:41:12 -0400182crypto_PKCS12_get_friendlyname(crypto_PKCS12Obj *self, PyObject *args) {
Rick Dean42d69e12009-07-20 11:36:08 -0500183 if (!PyArg_ParseTuple(args, ":get_friendlyname"))
184 return NULL;
185
186 Py_INCREF(self->friendlyname);
Rick Dean99251c22009-07-24 09:32:46 -0500187 return (PyObject *) self->friendlyname;
Rick Dean42d69e12009-07-20 11:36:08 -0500188}
189
190static char crypto_PKCS12_set_friendlyname_doc[] = "\n\
191Replace or set the certificate portion of the PKCS12 structure\n\
192\n\
193@param name: The new friendly name.\n\
194@type name: L{str}\n\
195@return: None\n\
196";
197static PyObject *
Jean-Paul Calderone4a45cbc2009-07-24 21:41:12 -0400198crypto_PKCS12_set_friendlyname(crypto_PKCS12Obj *self, PyObject *args, PyObject *keywds) {
Rick Dean42d69e12009-07-20 11:36:08 -0500199 PyObject *name = NULL;
200 static char *kwlist[] = {"name", NULL};
201
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -0400202 if (!PyArg_ParseTupleAndKeywords(args, keywds, "O:set_friendlyname",
Rick Dean42d69e12009-07-20 11:36:08 -0500203 kwlist, &name))
204 return NULL;
205
Jean-Paul Calderone2f6c66f2010-08-11 19:53:43 -0400206 if (name != Py_None && ! PyBytes_CheckExact(name)) {
Jean-Paul Calderoneadd7bf02010-08-22 17:38:30 -0400207 PyErr_SetString(PyExc_TypeError, "name must be a byte string or None");
Rick Dean42d69e12009-07-20 11:36:08 -0500208 return NULL;
209 }
210
211 Py_INCREF(name); /* Make consistent before calling Py_DECREF() */
212 Py_DECREF(self->friendlyname);
213 self->friendlyname = name;
214
215 Py_INCREF(Py_None);
216 return Py_None;
217}
218
Rick Dean623ee362009-07-17 12:22:16 -0500219static char crypto_PKCS12_export_doc[] = "\n\
Rick Deane182f482009-07-17 14:49:48 -0500220export([passphrase=None][, friendly_name=None][, iter=2048][, maciter=1]\n\
221Dump a PKCS12 object as a string. See also \"man PKCS12_create\".\n\
Rick Dean623ee362009-07-17 12:22:16 -0500222\n\
Rick Deane182f482009-07-17 14:49:48 -0500223@param passphrase: used to encrypt the PKCS12\n\
224@type passphrase: L{str}\n\
Rick Deane182f482009-07-17 14:49:48 -0500225@param iter: How many times to repeat the encryption\n\
226@type iter: L{int}\n\
227@param maciter: How many times to repeat the MAC\n\
228@type maciter: L{int}\n\
229@return: The string containing the PKCS12\n\
Rick Dean623ee362009-07-17 12:22:16 -0500230";
Rick Dean623ee362009-07-17 12:22:16 -0500231static PyObject *
Jean-Paul Calderone4a45cbc2009-07-24 21:41:12 -0400232crypto_PKCS12_export(crypto_PKCS12Obj *self, PyObject *args, PyObject *keywds) {
233 int i; /* Py_ssize_t for Python 2.5+ */
234 PyObject *obj;
Rick Dean623ee362009-07-17 12:22:16 -0500235 int buf_len;
236 PyObject *buffer;
237 char *temp, *passphrase = NULL, *friendly_name = NULL;
238 BIO *bio;
239 PKCS12 *p12;
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -0400240 EVP_PKEY *pkey = NULL;
Rick Dean623ee362009-07-17 12:22:16 -0500241 STACK_OF(X509) *cacerts = NULL;
242 X509 *x509 = NULL;
Rick Deane182f482009-07-17 14:49:48 -0500243 int iter = 0; /* defaults to PKCS12_DEFAULT_ITER */
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -0400244 int maciter = 0;
Rick Dean42d69e12009-07-20 11:36:08 -0500245 static char *kwlist[] = {"passphrase", "iter", "maciter", NULL};
Rick Dean623ee362009-07-17 12:22:16 -0500246
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -0400247 if (!PyArg_ParseTupleAndKeywords(args, keywds, "|zii:export",
Rick Dean42d69e12009-07-20 11:36:08 -0500248 kwlist, &passphrase, &iter, &maciter))
Rick Dean623ee362009-07-17 12:22:16 -0500249 return NULL;
250
Rick Dean585cd9e2009-07-18 14:58:11 -0500251 if (self->key != Py_None) {
Rick Dean623ee362009-07-17 12:22:16 -0500252 pkey = ((crypto_PKeyObj*) self->key)->pkey;
253 }
Rick Dean585cd9e2009-07-18 14:58:11 -0500254 if (self->cert != Py_None) {
Rick Dean623ee362009-07-17 12:22:16 -0500255 x509 = ((crypto_X509Obj*) self->cert)->x509;
256 }
Rick Dean585cd9e2009-07-18 14:58:11 -0500257 if (self->cacerts != Py_None) {
Rick Dean8fefeb02009-07-24 10:56:29 -0500258 cacerts = sk_X509_new_null();
Jean-Paul Calderone4a45cbc2009-07-24 21:41:12 -0400259 for (i = 0; i < PyTuple_Size(self->cacerts); i++) { /* For each CA cert */
Rick Dean623ee362009-07-17 12:22:16 -0500260 obj = PySequence_GetItem(self->cacerts, i);
261 /* assert(PyObject_IsInstance(obj, (PyObject *) &crypto_X509_Type )); */
262 sk_X509_push(cacerts, (( crypto_X509Obj* ) obj)->x509);
263 Py_DECREF(obj);
264 }
265 }
Rick Dean42d69e12009-07-20 11:36:08 -0500266 if (self->friendlyname != Py_None) {
Jean-Paul Calderone2f6c66f2010-08-11 19:53:43 -0400267 friendly_name = PyBytes_AsString(self->friendlyname);
Rick Dean42d69e12009-07-20 11:36:08 -0500268 }
Rick Dean623ee362009-07-17 12:22:16 -0500269
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -0400270 p12 = PKCS12_create(passphrase, friendly_name, pkey, x509, cacerts,
Rick Dean623ee362009-07-17 12:22:16 -0500271 NID_pbe_WithSHA1And3_Key_TripleDES_CBC,
272 NID_pbe_WithSHA1And3_Key_TripleDES_CBC,
273 iter, maciter, 0);
Rick Dean8fefeb02009-07-24 10:56:29 -0500274 sk_X509_free(cacerts); /* NULL safe. Free just the container. */
Jean-Paul Calderone4a45cbc2009-07-24 21:41:12 -0400275 if (p12 == NULL) {
Rick Dean623ee362009-07-17 12:22:16 -0500276 exception_from_error_queue(crypto_Error);
277 return NULL;
278 }
279 bio = BIO_new(BIO_s_mem());
280 i2d_PKCS12_bio(bio, p12);
281 buf_len = BIO_get_mem_data(bio, &temp);
Jean-Paul Calderone2f6c66f2010-08-11 19:53:43 -0400282 buffer = PyBytes_FromStringAndSize(temp, buf_len);
Rick Dean623ee362009-07-17 12:22:16 -0500283 BIO_free(bio);
284 return buffer;
285}
286
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500287/*
288 * ADD_METHOD(name) expands to a correct PyMethodDef declaration
289 * { 'name', (PyCFunction)crypto_PKCS12_name, METH_VARARGS, crypto_PKCS12_name_doc }
290 * for convenience
291 */
292#define ADD_METHOD(name) \
293 { #name, (PyCFunction)crypto_PKCS12_##name, METH_VARARGS, crypto_PKCS12_##name##_doc }
Rick Dean623ee362009-07-17 12:22:16 -0500294#define ADD_KW_METHOD(name) \
295 { #name, (PyCFunction)crypto_PKCS12_##name, METH_VARARGS | METH_KEYWORDS, crypto_PKCS12_##name##_doc }
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500296static PyMethodDef crypto_PKCS12_methods[] =
297{
298 ADD_METHOD(get_certificate),
Rick Dean623ee362009-07-17 12:22:16 -0500299 ADD_KW_METHOD(set_certificate),
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500300 ADD_METHOD(get_privatekey),
Rick Dean623ee362009-07-17 12:22:16 -0500301 ADD_KW_METHOD(set_privatekey),
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500302 ADD_METHOD(get_ca_certificates),
Rick Dean623ee362009-07-17 12:22:16 -0500303 ADD_KW_METHOD(set_ca_certificates),
Rick Dean42d69e12009-07-20 11:36:08 -0500304 ADD_METHOD(get_friendlyname),
305 ADD_KW_METHOD(set_friendlyname),
Rick Dean623ee362009-07-17 12:22:16 -0500306 ADD_KW_METHOD(export),
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500307 { NULL, NULL }
308};
309#undef ADD_METHOD
310
311/*
312 * Constructor for PKCS12 objects, never called by Python code directly.
313 * The strategy for this object is to create all the Python objects
314 * corresponding to the cert/key/CA certs right away
315 *
Jean-Paul Calderone32eb0312009-07-25 11:15:55 -0400316 * Arguments: p12 - A "real" PKCS12 object or NULL
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500317 * passphrase - Passphrase to use when decrypting the PKCS12 object
318 * Returns: The newly created PKCS12 object
319 */
320crypto_PKCS12Obj *
Jean-Paul Calderone32eb0312009-07-25 11:15:55 -0400321crypto_PKCS12_New(PKCS12 *p12, char *passphrase) {
Jean-Paul Calderonee58415f2009-07-24 21:12:45 -0400322 crypto_PKCS12Obj *self = NULL;
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500323 PyObject *cacertobj = NULL;
324
Jean-Paul Calderoneb96d13e2009-07-25 11:33:22 -0400325 unsigned char *alias_str;
326 int alias_len;
Jean-Paul Calderone32eb0312009-07-25 11:15:55 -0400327
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500328 X509 *cert = NULL;
329 EVP_PKEY *pkey = NULL;
330 STACK_OF(X509) *cacerts = NULL;
331
332 int i, cacert_count = 0;
333
334 /* allocate space for the CA cert stack */
Jean-Paul Calderone32eb0312009-07-25 11:15:55 -0400335 if((cacerts = sk_X509_new_null()) == NULL) {
Rick Deanaace5e92009-07-24 10:44:49 -0500336 goto error; /* out of memory? */
Jean-Paul Calderone32eb0312009-07-25 11:15:55 -0400337 }
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500338
339 /* parse the PKCS12 lump */
Jean-Paul Calderoneb51bda32011-05-04 16:57:45 -0400340 if (p12) {
341 if (!PKCS12_parse(p12, passphrase, &pkey, &cert, &cacerts)) {
342 /*
343 * If PKCS12_parse fails, and it allocated cacerts, it seems to
344 * free cacerts, but not re-NULL the pointer. Zounds! Make sure
345 * it is re-set to NULL here, else we'll have a double-free below.
346 */
347 cacerts = NULL;
348 exception_from_error_queue(crypto_Error);
349 goto error;
350 } else {
351 /*
352 * OpenSSL 1.0.0 sometimes leaves an X509_check_private_key error in
353 * the queue for no particular reason. This error isn't interesting
354 * to anyone outside this function. It's not even interesting to
355 * us. Get rid of it.
356 */
357 flush_error_queue();
358 }
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500359 }
360
Jean-Paul Calderone32eb0312009-07-25 11:15:55 -0400361 if (!(self = PyObject_GC_New(crypto_PKCS12Obj, &crypto_PKCS12_Type))) {
Rick Deanee568302009-07-24 09:56:29 -0500362 goto error;
Jean-Paul Calderone32eb0312009-07-25 11:15:55 -0400363 }
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500364
Rick Dean8fefeb02009-07-24 10:56:29 -0500365 /* client certificate and friendlyName */
Rick Dean623ee362009-07-17 12:22:16 -0500366 if (cert == NULL) {
367 Py_INCREF(Py_None);
368 self->cert = Py_None;
Rick Dean42d69e12009-07-20 11:36:08 -0500369 Py_INCREF(Py_None);
370 self->friendlyname = Py_None;
Rick Dean623ee362009-07-17 12:22:16 -0500371 } else {
Jean-Paul Calderone32eb0312009-07-25 11:15:55 -0400372 if ((self->cert = (PyObject *)crypto_X509_New(cert, 1)) == NULL) {
Rick Dean623ee362009-07-17 12:22:16 -0500373 goto error;
Jean-Paul Calderone32eb0312009-07-25 11:15:55 -0400374 }
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -0400375
Rick Dean42d69e12009-07-20 11:36:08 -0500376 /* Now we need to extract the friendlyName of the PKCS12
Jean-Paul Calderone304866b2009-07-25 12:03:55 -0400377 * that was stored by PKCS_parse() in the alias of the
Rick Dean42d69e12009-07-20 11:36:08 -0500378 * certificate. */
Jean-Paul Calderoneb96d13e2009-07-25 11:33:22 -0400379 alias_str = X509_alias_get0(cert, &alias_len);
Jean-Paul Calderone304866b2009-07-25 12:03:55 -0400380 if (alias_str) {
Jean-Paul Calderone40dd0992010-08-22 17:52:07 -0400381 self->friendlyname = Py_BuildValue(BYTESTRING_FMT "#", alias_str, alias_len);
Jean-Paul Calderoneadd7bf02010-08-22 17:38:30 -0400382 if (!self->friendlyname) {
Jean-Paul Calderone304866b2009-07-25 12:03:55 -0400383 /*
384 * XXX Untested
385 */
386 goto error;
387 }
Rick Dean42d69e12009-07-20 11:36:08 -0500388 /* success */
389 } else {
390 Py_INCREF(Py_None);
391 self->friendlyname = Py_None;
392 }
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -0400393 }
Rick Dean8fefeb02009-07-24 10:56:29 -0500394
395 /* private key */
Rick Dean623ee362009-07-17 12:22:16 -0500396 if (pkey == NULL) {
397 Py_INCREF(Py_None);
398 self->key = Py_None;
399 } else {
400 if ((self->key = (PyObject *)crypto_PKey_New(pkey, 1)) == NULL)
401 goto error;
402 }
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500403
Rick Dean8fefeb02009-07-24 10:56:29 -0500404 /* CA certs */
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500405 cacert_count = sk_X509_num(cacerts);
Jean-Paul Calderone304866b2009-07-25 12:03:55 -0400406 if (cacert_count <= 0) {
Rick Deanaace5e92009-07-24 10:44:49 -0500407 Py_INCREF(Py_None);
408 self->cacerts = Py_None;
409 } else {
Jean-Paul Calderone304866b2009-07-25 12:03:55 -0400410 if ((self->cacerts = PyTuple_New(cacert_count)) == NULL) {
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500411 goto error;
Jean-Paul Calderone304866b2009-07-25 12:03:55 -0400412 }
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500413
Jean-Paul Calderone304866b2009-07-25 12:03:55 -0400414 for (i = 0; i < cacert_count; i++) {
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500415 cert = sk_X509_value(cacerts, i);
Jean-Paul Calderone304866b2009-07-25 12:03:55 -0400416 if ((cacertobj = (PyObject *)crypto_X509_New(cert, 1)) == NULL) {
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500417 goto error;
Jean-Paul Calderone304866b2009-07-25 12:03:55 -0400418 }
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500419 PyTuple_SET_ITEM(self->cacerts, i, cacertobj);
420 }
421 }
422
Rick Dean8fefeb02009-07-24 10:56:29 -0500423 sk_X509_free(cacerts); /* Don't free the certs, just the container. */
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500424 PyObject_GC_Track(self);
425
426 return self;
Rick Deanee568302009-07-24 09:56:29 -0500427
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500428error:
Rick Dean8fefeb02009-07-24 10:56:29 -0500429 sk_X509_free(cacerts); /* NULL safe. Free just the container. */
Jean-Paul Calderoned0a98762009-07-25 21:23:01 -0400430 if (self) {
431 crypto_PKCS12_clear(self);
432 PyObject_GC_Del(self);
433 }
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500434 return NULL;
435}
436
Rick Deancbeaca02009-07-17 12:50:12 -0500437static char crypto_PKCS12_doc[] = "\n\
438PKCS12() -> PKCS12 instance\n\
439\n\
Rick Deane182f482009-07-17 14:49:48 -0500440Create a new empty PKCS12 object.\n\
Rick Deancbeaca02009-07-17 12:50:12 -0500441\n\
442@returns: The PKCS12 object\n\
443";
444static PyObject *
Jean-Paul Calderoneb1a3af12009-07-25 12:21:18 -0400445crypto_PKCS12_new(PyTypeObject *subtype, PyObject *args, PyObject *kwargs) {
Rick Deancbeaca02009-07-17 12:50:12 -0500446 if (!PyArg_ParseTuple(args, ":PKCS12")) {
447 return NULL;
448 }
449
450 return (PyObject *)crypto_PKCS12_New(NULL, NULL);
451}
452
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500453/*
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500454 * Call the visitproc on all contained objects.
455 *
456 * Arguments: self - The PKCS12 object
457 * visit - Function to call
458 * arg - Extra argument to visit
459 * Returns: 0 if all goes well, otherwise the return code from the first
460 * call that gave non-zero result.
461 */
462static int
463crypto_PKCS12_traverse(crypto_PKCS12Obj *self, visitproc visit, void *arg)
464{
465 int ret = 0;
466
467 if (ret == 0 && self->cert != NULL)
468 ret = visit(self->cert, arg);
469 if (ret == 0 && self->key != NULL)
470 ret = visit(self->key, arg);
471 if (ret == 0 && self->cacerts != NULL)
472 ret = visit(self->cacerts, arg);
Rick Dean42d69e12009-07-20 11:36:08 -0500473 if (ret == 0 && self->friendlyname != NULL)
474 ret = visit(self->friendlyname, arg);
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500475 return ret;
476}
477
478/*
479 * Decref all contained objects and zero the pointers.
480 *
481 * Arguments: self - The PKCS12 object
482 * Returns: Always 0.
483 */
484static int
485crypto_PKCS12_clear(crypto_PKCS12Obj *self)
486{
487 Py_XDECREF(self->cert);
488 self->cert = NULL;
489 Py_XDECREF(self->key);
490 self->key = NULL;
491 Py_XDECREF(self->cacerts);
492 self->cacerts = NULL;
Rick Dean42d69e12009-07-20 11:36:08 -0500493 Py_XDECREF(self->friendlyname);
494 self->friendlyname = NULL;
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500495 return 0;
496}
497
498/*
499 * Deallocate the memory used by the PKCS12 object
500 *
501 * Arguments: self - The PKCS12 object
502 * Returns: None
503 */
504static void
505crypto_PKCS12_dealloc(crypto_PKCS12Obj *self)
506{
507 PyObject_GC_UnTrack(self);
508 crypto_PKCS12_clear(self);
509 PyObject_GC_Del(self);
510}
511
512PyTypeObject crypto_PKCS12_Type = {
Jean-Paul Calderone3fe7f672010-08-11 23:55:10 -0400513 PyOpenSSL_HEAD_INIT(&PyType_Type, 0)
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500514 "PKCS12",
515 sizeof(crypto_PKCS12Obj),
516 0,
517 (destructor)crypto_PKCS12_dealloc,
518 NULL, /* print */
Jean-Paul Calderone2f6c66f2010-08-11 19:53:43 -0400519 NULL, /* getattr */
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500520 NULL, /* setattr */
521 NULL, /* compare */
522 NULL, /* repr */
523 NULL, /* as_number */
524 NULL, /* as_sequence */
525 NULL, /* as_mapping */
526 NULL, /* hash */
527 NULL, /* call */
528 NULL, /* str */
529 NULL, /* getattro */
530 NULL, /* setattro */
531 NULL, /* as_buffer */
532 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,
Jean-Paul Calderonee7901d72009-07-24 18:21:26 -0400533 crypto_PKCS12_doc,
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500534 (traverseproc)crypto_PKCS12_traverse,
535 (inquiry)crypto_PKCS12_clear,
Rick Deancbeaca02009-07-17 12:50:12 -0500536 NULL, /* tp_richcompare */
537 0, /* tp_weaklistoffset */
538 NULL, /* tp_iter */
539 NULL, /* tp_iternext */
540 crypto_PKCS12_methods, /* tp_methods */
541 NULL, /* tp_members */
542 NULL, /* tp_getset */
543 NULL, /* tp_base */
544 NULL, /* tp_dict */
545 NULL, /* tp_descr_get */
546 NULL, /* tp_descr_set */
547 0, /* tp_dictoffset */
548 NULL, /* tp_init */
549 NULL, /* tp_alloc */
550 crypto_PKCS12_new, /* tp_new */
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500551};
552
553/*
554 * Initialize the PKCS12 part of the crypto sub module
555 *
Jean-Paul Calderonedc138fa2009-06-27 14:32:07 -0400556 * Arguments: module - The crypto module
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500557 * Returns: None
558 */
559int
Jean-Paul Calderonedc138fa2009-06-27 14:32:07 -0400560init_crypto_pkcs12(PyObject *module) {
561 if (PyType_Ready(&crypto_PKCS12_Type) < 0) {
562 return 0;
563 }
564
Rick Deancbeaca02009-07-17 12:50:12 -0500565 if (PyModule_AddObject(module, "PKCS12", (PyObject *)&crypto_PKCS12_Type) != 0) {
566 return 0;
567 }
568
Jean-Paul Calderonedc138fa2009-06-27 14:32:07 -0400569 if (PyModule_AddObject(module, "PKCS12Type", (PyObject *)&crypto_PKCS12_Type) != 0) {
570 return 0;
571 }
572
Jean-Paul Calderone897bc252008-02-18 20:50:23 -0500573 return 1;
574}