1 /* This example code is placed in the public domain. */
9 #include <gnutls/gnutls.h>
10 #include <gnutls/pkcs12.h>
14 #define OUTFILE "out.p12"
16 /* This function will write a pkcs12 structure into a file.
17 * cert: is a DER encoded certificate
18 * pkcs8_key: is a PKCS #8 encrypted key (note that this must be
19 * encrypted using a PKCS #12 cipher, or some browsers will crash)
20 * password: is the password used to encrypt the PKCS #12 packet.
23 write_pkcs12 (const gnutls_datum_t * cert,
24 const gnutls_datum_t * pkcs8_key, const char *password)
26 gnutls_pkcs12_t pkcs12;
28 gnutls_pkcs12_bag_t bag, key_bag;
29 char pkcs12_struct[10 * 1024];
30 size_t pkcs12_struct_size;
33 /* A good idea might be to use gnutls_x509_privkey_get_key_id()
34 * to obtain a unique ID.
36 gnutls_datum_t key_id = { (char *) "\x00\x00\x07", 3 };
38 gnutls_global_init ();
40 /* Firstly we create two helper bags, which hold the certificate,
41 * and the (encrypted) key.
44 gnutls_pkcs12_bag_init (&bag);
45 gnutls_pkcs12_bag_init (&key_bag);
47 ret = gnutls_pkcs12_bag_set_data (bag, GNUTLS_BAG_CERTIFICATE, cert);
50 fprintf (stderr, "ret: %s\n", gnutls_strerror (ret));
54 /* ret now holds the bag's index.
58 /* Associate a friendly name with the given certificate. Used
61 gnutls_pkcs12_bag_set_friendly_name (bag, bag_index, "My name");
63 /* Associate the certificate with the key using a unique key
66 gnutls_pkcs12_bag_set_key_id (bag, bag_index, &key_id);
68 /* use weak encryption for the certificate.
70 gnutls_pkcs12_bag_encrypt (bag, password, GNUTLS_PKCS_USE_PKCS12_RC2_40);
75 ret = gnutls_pkcs12_bag_set_data (key_bag,
76 GNUTLS_BAG_PKCS8_ENCRYPTED_KEY,
80 fprintf (stderr, "ret: %s\n", gnutls_strerror (ret));
84 /* Note that since the PKCS #8 key is already encrypted we don't
85 * bother encrypting that bag.
89 gnutls_pkcs12_bag_set_friendly_name (key_bag, bag_index, "My name");
91 gnutls_pkcs12_bag_set_key_id (key_bag, bag_index, &key_id);
94 /* The bags were filled. Now create the PKCS #12 structure.
96 gnutls_pkcs12_init (&pkcs12);
98 /* Insert the two bags in the PKCS #12 structure.
101 gnutls_pkcs12_set_bag (pkcs12, bag);
102 gnutls_pkcs12_set_bag (pkcs12, key_bag);
105 /* Generate a message authentication code for the PKCS #12
108 gnutls_pkcs12_generate_mac (pkcs12, password);
110 pkcs12_struct_size = sizeof (pkcs12_struct);
112 gnutls_pkcs12_export (pkcs12, GNUTLS_X509_FMT_DER, pkcs12_struct,
113 &pkcs12_struct_size);
116 fprintf (stderr, "ret: %s\n", gnutls_strerror (ret));
120 fd = fopen (OUTFILE, "w");
123 fprintf (stderr, "cannot open file\n");
126 fwrite (pkcs12_struct, 1, pkcs12_struct_size, fd);
129 gnutls_pkcs12_bag_deinit (bag);
130 gnutls_pkcs12_bag_deinit (key_bag);
131 gnutls_pkcs12_deinit (pkcs12);