LCOV - code coverage report
Current view: top level - third_party/heimdal/lib/hx509 - ks_p12.c (source / functions) Hit Total Coverage
Test: coverage report for v4-17-test 1498b464 Lines: 3 307 1.0 %
Date: 2024-06-13 04:01:37 Functions: 1 20 5.0 %

          Line data    Source code
       1             : /*
       2             :  * Copyright (c) 2004 - 2007 Kungliga Tekniska Högskolan
       3             :  * (Royal Institute of Technology, Stockholm, Sweden).
       4             :  * All rights reserved.
       5             :  *
       6             :  * Redistribution and use in source and binary forms, with or without
       7             :  * modification, are permitted provided that the following conditions
       8             :  * are met:
       9             :  *
      10             :  * 1. Redistributions of source code must retain the above copyright
      11             :  *    notice, this list of conditions and the following disclaimer.
      12             :  *
      13             :  * 2. Redistributions in binary form must reproduce the above copyright
      14             :  *    notice, this list of conditions and the following disclaimer in the
      15             :  *    documentation and/or other materials provided with the distribution.
      16             :  *
      17             :  * 3. Neither the name of the Institute nor the names of its contributors
      18             :  *    may be used to endorse or promote products derived from this software
      19             :  *    without specific prior written permission.
      20             :  *
      21             :  * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
      22             :  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
      23             :  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
      24             :  * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
      25             :  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
      26             :  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
      27             :  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
      28             :  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
      29             :  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
      30             :  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
      31             :  * SUCH DAMAGE.
      32             :  */
      33             : 
      34             : #include "hx_locl.h"
      35             : 
      36             : struct ks_pkcs12 {
      37             :     hx509_certs certs;
      38             :     char *fn;
      39             :     unsigned int store_no_priv_keys;
      40             : };
      41             : 
      42             : typedef int (*collector_func)(hx509_context,
      43             :                               struct hx509_collector *,
      44             :                               int,
      45             :                               const void *, size_t,
      46             :                               const PKCS12_Attributes *);
      47             : 
      48             : struct type {
      49             :     const heim_oid *oid;
      50             :     collector_func func;
      51             : };
      52             : 
      53             : static void
      54             : parse_pkcs12_type(hx509_context, struct hx509_collector *, int,
      55             :                   const heim_oid *, const void *, size_t,
      56             :                   const PKCS12_Attributes *);
      57             : 
      58             : 
      59             : static const PKCS12_Attribute *
      60           0 : find_attribute(const PKCS12_Attributes *attrs, const heim_oid *oid)
      61             : {
      62             :     size_t i;
      63           0 :     if (attrs == NULL)
      64           0 :         return NULL;
      65           0 :     for (i = 0; i < attrs->len; i++)
      66           0 :         if (der_heim_oid_cmp(oid, &attrs->val[i].attrId) == 0)
      67           0 :             return &attrs->val[i];
      68           0 :     return NULL;
      69             : }
      70             : 
      71             : static int
      72           0 : keyBag_parser(hx509_context context,
      73             :               struct hx509_collector *c,
      74             :               int flags,
      75             :               const void *data, size_t length,
      76             :               const PKCS12_Attributes *attrs)
      77             : {
      78             :     const PKCS12_Attribute *attr;
      79             :     PKCS8PrivateKeyInfo ki;
      80           0 :     const heim_octet_string *os = NULL;
      81             :     int ret;
      82             : 
      83           0 :     if (flags & HX509_CERTS_NO_PRIVATE_KEYS)
      84           0 :         return 0;
      85             : 
      86           0 :     attr = find_attribute(attrs, &asn1_oid_id_pkcs_9_at_localKeyId);
      87           0 :     if (attr)
      88           0 :         os = &attr->attrValues;
      89             : 
      90           0 :     ret = decode_PKCS8PrivateKeyInfo(data, length, &ki, NULL);
      91           0 :     if (ret)
      92           0 :         return ret;
      93             : 
      94           0 :     _hx509_collector_private_key_add(context,
      95             :                                      c,
      96             :                                      &ki.privateKeyAlgorithm,
      97             :                                      NULL,
      98             :                                      &ki.privateKey,
      99             :                                      os);
     100           0 :     free_PKCS8PrivateKeyInfo(&ki);
     101           0 :     return 0;
     102             : }
     103             : 
     104             : static int
     105           0 : ShroudedKeyBag_parser(hx509_context context,
     106             :                       struct hx509_collector *c,
     107             :                       int flags,
     108             :                       const void *data, size_t length,
     109             :                       const PKCS12_Attributes *attrs)
     110             : {
     111             :     PKCS8EncryptedPrivateKeyInfo pk;
     112             :     heim_octet_string content;
     113             :     int ret;
     114             : 
     115           0 :     memset(&pk, 0, sizeof(pk));
     116             : 
     117           0 :     ret = decode_PKCS8EncryptedPrivateKeyInfo(data, length, &pk, NULL);
     118           0 :     if (ret)
     119           0 :         return ret;
     120             : 
     121           0 :     ret = _hx509_pbe_decrypt(context,
     122             :                              _hx509_collector_get_lock(c),
     123             :                              &pk.encryptionAlgorithm,
     124             :                              &pk.encryptedData,
     125             :                              &content);
     126           0 :     free_PKCS8EncryptedPrivateKeyInfo(&pk);
     127           0 :     if (ret)
     128           0 :         return ret;
     129             : 
     130           0 :     ret = keyBag_parser(context, c, flags, content.data, content.length,
     131             :                         attrs);
     132           0 :     der_free_octet_string(&content);
     133           0 :     return ret;
     134             : }
     135             : 
     136             : static int
     137           0 : certBag_parser(hx509_context context,
     138             :                struct hx509_collector *c,
     139             :                int flags,
     140             :                const void *data, size_t length,
     141             :                const PKCS12_Attributes *attrs)
     142             : {
     143           0 :     heim_error_t error = NULL;
     144             :     heim_octet_string os;
     145             :     hx509_cert cert;
     146             :     PKCS12_CertBag cb;
     147             :     int ret;
     148             : 
     149           0 :     ret = decode_PKCS12_CertBag(data, length, &cb, NULL);
     150           0 :     if (ret)
     151           0 :         return ret;
     152             : 
     153           0 :     if (der_heim_oid_cmp(&asn1_oid_id_pkcs_9_at_certTypes_x509, &cb.certType)) {
     154           0 :         free_PKCS12_CertBag(&cb);
     155           0 :         return 0;
     156             :     }
     157             : 
     158           0 :     ret = decode_PKCS12_OctetString(cb.certValue.data,
     159             :                                     cb.certValue.length,
     160             :                                     &os,
     161             :                                     NULL);
     162           0 :     free_PKCS12_CertBag(&cb);
     163           0 :     if (ret)
     164           0 :         return ret;
     165             : 
     166           0 :     cert = hx509_cert_init_data(context, os.data, os.length, &error);
     167           0 :     der_free_octet_string(&os);
     168           0 :     if (cert == NULL) {
     169           0 :         ret = heim_error_get_code(error);
     170           0 :         heim_release(error);
     171           0 :         return ret;
     172             :     }
     173             : 
     174           0 :     ret = _hx509_collector_certs_add(context, c, cert);
     175           0 :     if (ret) {
     176           0 :         hx509_cert_free(cert);
     177           0 :         return ret;
     178             :     }
     179             : 
     180             :     {
     181             :         const PKCS12_Attribute *attr;
     182           0 :         const heim_oid *oids[] = {
     183             :             &asn1_oid_id_pkcs_9_at_localKeyId, &asn1_oid_id_pkcs_9_at_friendlyName
     184             :         };
     185             :         size_t i;
     186             : 
     187           0 :         for  (i = 0; i < sizeof(oids)/sizeof(oids[0]); i++) {
     188           0 :             const heim_oid *oid = oids[i];
     189           0 :             attr = find_attribute(attrs, oid);
     190           0 :             if (attr)
     191           0 :                 _hx509_set_cert_attribute(context, cert, oid,
     192           0 :                                           &attr->attrValues);
     193             :         }
     194             :     }
     195             : 
     196           0 :     hx509_cert_free(cert);
     197             : 
     198           0 :     return 0;
     199             : }
     200             : 
     201             : static int
     202           0 : parse_safe_content(hx509_context context,
     203             :                    struct hx509_collector *c,
     204             :                    int flags,
     205             :                    const unsigned char *p, size_t len)
     206             : {
     207             :     PKCS12_SafeContents sc;
     208             :     int ret;
     209             :     size_t i;
     210             : 
     211           0 :     memset(&sc, 0, sizeof(sc));
     212             : 
     213           0 :     ret = decode_PKCS12_SafeContents(p, len, &sc, NULL);
     214           0 :     if (ret)
     215           0 :         return ret;
     216             : 
     217           0 :     for (i = 0; i < sc.len ; i++)
     218           0 :         parse_pkcs12_type(context,
     219             :                           c,
     220             :                           flags,
     221           0 :                           &sc.val[i].bagId,
     222           0 :                           sc.val[i].bagValue.data,
     223           0 :                           sc.val[i].bagValue.length,
     224           0 :                           sc.val[i].bagAttributes);
     225             : 
     226           0 :     free_PKCS12_SafeContents(&sc);
     227           0 :     return 0;
     228             : }
     229             : 
     230             : static int
     231           0 : safeContent_parser(hx509_context context,
     232             :                    struct hx509_collector *c,
     233             :                    int flags,
     234             :                    const void *data, size_t length,
     235             :                    const PKCS12_Attributes *attrs)
     236             : {
     237             :     heim_octet_string os;
     238             :     int ret;
     239             : 
     240           0 :     ret = decode_PKCS12_OctetString(data, length, &os, NULL);
     241           0 :     if (ret)
     242           0 :         return ret;
     243           0 :     ret = parse_safe_content(context, c, flags, os.data, os.length);
     244           0 :     der_free_octet_string(&os);
     245           0 :     return ret;
     246             : }
     247             : 
     248             : static int
     249           0 : encryptedData_parser(hx509_context context,
     250             :                      struct hx509_collector *c,
     251             :                      int flags,
     252             :                      const void *data, size_t length,
     253             :                      const PKCS12_Attributes *attrs)
     254             : {
     255             :     heim_octet_string content;
     256             :     heim_oid contentType;
     257             :     int ret;
     258             : 
     259           0 :     memset(&contentType, 0, sizeof(contentType));
     260             : 
     261           0 :     ret = hx509_cms_decrypt_encrypted(context,
     262             :                                       _hx509_collector_get_lock(c),
     263             :                                       data, length,
     264             :                                       &contentType,
     265             :                                       &content);
     266           0 :     if (ret)
     267           0 :         return ret;
     268             : 
     269           0 :     if (der_heim_oid_cmp(&contentType, &asn1_oid_id_pkcs7_data) == 0)
     270           0 :         ret = parse_safe_content(context, c, flags,
     271           0 :                                  content.data, content.length);
     272             : 
     273           0 :     der_free_octet_string(&content);
     274           0 :     der_free_oid(&contentType);
     275           0 :     return ret;
     276             : }
     277             : 
     278             : static int
     279           0 : envelopedData_parser(hx509_context context,
     280             :                      struct hx509_collector *c,
     281             :                      int flags,
     282             :                      const void *data, size_t length,
     283             :                      const PKCS12_Attributes *attrs)
     284             : {
     285             :     heim_octet_string content;
     286             :     heim_oid contentType;
     287             :     hx509_lock lock;
     288             :     int ret;
     289             : 
     290           0 :     memset(&contentType, 0, sizeof(contentType));
     291             : 
     292           0 :     lock = _hx509_collector_get_lock(c);
     293             : 
     294           0 :     ret = hx509_cms_unenvelope(context,
     295             :                                _hx509_lock_unlock_certs(lock),
     296             :                                0,
     297             :                                data, length,
     298             :                                NULL,
     299             :                                0,
     300             :                                &contentType,
     301             :                                &content);
     302           0 :     if (ret) {
     303           0 :         hx509_set_error_string(context, HX509_ERROR_APPEND, ret,
     304             :                                "PKCS12 failed to unenvelope");
     305           0 :         return ret;
     306             :     }
     307             : 
     308           0 :     if (der_heim_oid_cmp(&contentType, &asn1_oid_id_pkcs7_data) == 0)
     309           0 :         ret = parse_safe_content(context, c, flags,
     310           0 :                                  content.data, content.length);
     311             : 
     312           0 :     der_free_octet_string(&content);
     313           0 :     der_free_oid(&contentType);
     314             : 
     315           0 :     return ret;
     316             : }
     317             : 
     318             : 
     319             : struct type bagtypes[] = {
     320             :     { &asn1_oid_id_pkcs12_keyBag, keyBag_parser },
     321             :     { &asn1_oid_id_pkcs12_pkcs8ShroudedKeyBag, ShroudedKeyBag_parser },
     322             :     { &asn1_oid_id_pkcs12_certBag, certBag_parser },
     323             :     { &asn1_oid_id_pkcs7_data, safeContent_parser },
     324             :     { &asn1_oid_id_pkcs7_encryptedData, encryptedData_parser },
     325             :     { &asn1_oid_id_pkcs7_envelopedData, envelopedData_parser }
     326             : };
     327             : 
     328             : static void
     329           0 : parse_pkcs12_type(hx509_context context,
     330             :                   struct hx509_collector *c,
     331             :                   int flags,
     332             :                   const heim_oid *oid,
     333             :                   const void *data, size_t length,
     334             :                   const PKCS12_Attributes *attrs)
     335             : {
     336             :     size_t i;
     337             : 
     338           0 :     for (i = 0; i < sizeof(bagtypes)/sizeof(bagtypes[0]); i++)
     339           0 :         if (der_heim_oid_cmp(bagtypes[i].oid, oid) == 0)
     340           0 :             (*bagtypes[i].func)(context, c, flags, data, length, attrs);
     341           0 : }
     342             : 
     343             : static int
     344           0 : p12_init(hx509_context context,
     345             :          hx509_certs certs, void **data, int flags,
     346             :          const char *residue, hx509_lock lock)
     347             : {
     348             :     struct ks_pkcs12 *p12;
     349             :     size_t len;
     350             :     void *buf;
     351             :     PKCS12_PFX pfx;
     352             :     PKCS12_AuthenticatedSafe as;
     353             :     int ret;
     354             :     size_t i;
     355             :     struct hx509_collector *c;
     356             : 
     357           0 :     *data = NULL;
     358             : 
     359           0 :     if (residue == NULL || residue[0] == '\0') {
     360           0 :         hx509_set_error_string(context, 0, EINVAL,
     361             :                                "PKCS#12 file not specified");
     362           0 :         return EINVAL;
     363             :     }
     364             : 
     365           0 :     if (lock == NULL)
     366           0 :         lock = _hx509_empty_lock;
     367             : 
     368           0 :     ret = _hx509_collector_alloc(context, lock, &c);
     369           0 :     if (ret)
     370           0 :         return ret;
     371             : 
     372           0 :     p12 = calloc(1, sizeof(*p12));
     373           0 :     if (p12 == NULL) {
     374           0 :         ret = ENOMEM;
     375           0 :         hx509_set_error_string(context, 0, ret, "out of memory");
     376           0 :         goto out;
     377             :     }
     378             : 
     379           0 :     p12->fn = strdup(residue);
     380           0 :     if (p12->fn == NULL) {
     381           0 :         ret = ENOMEM;
     382           0 :         hx509_set_error_string(context, 0, ret, "out of memory");
     383           0 :         goto out;
     384             :     }
     385             : 
     386           0 :     if (flags & HX509_CERTS_CREATE) {
     387           0 :         ret = hx509_certs_init(context, "MEMORY:ks-file-create",
     388             :                                0, lock, &p12->certs);
     389           0 :         if (ret == 0)
     390           0 :             *data = p12;
     391           0 :         goto out;
     392             :     }
     393             : 
     394           0 :     ret = rk_undumpdata(residue, &buf, &len);
     395           0 :     if (ret) {
     396           0 :         hx509_clear_error_string(context);
     397           0 :         goto out;
     398             :     }
     399             : 
     400           0 :     ret = decode_PKCS12_PFX(buf, len, &pfx, NULL);
     401           0 :     rk_xfree(buf);
     402           0 :     if (ret) {
     403           0 :         hx509_set_error_string(context, 0, ret,
     404             :                                "Failed to decode the PFX in %s", residue);
     405           0 :         goto out;
     406             :     }
     407             : 
     408           0 :     if (der_heim_oid_cmp(&pfx.authSafe.contentType, &asn1_oid_id_pkcs7_data) != 0) {
     409           0 :         free_PKCS12_PFX(&pfx);
     410           0 :         ret = EINVAL;
     411           0 :         hx509_set_error_string(context, 0, ret,
     412             :                                "PKCS PFX isn't a pkcs7-data container");
     413           0 :         goto out;
     414             :     }
     415             : 
     416           0 :     if (pfx.authSafe.content == NULL) {
     417           0 :         free_PKCS12_PFX(&pfx);
     418           0 :         ret = EINVAL;
     419           0 :         hx509_set_error_string(context, 0, ret,
     420             :                                "PKCS PFX missing data");
     421           0 :         goto out;
     422             :     }
     423             : 
     424             :     {
     425             :         heim_octet_string asdata;
     426             : 
     427           0 :         ret = decode_PKCS12_OctetString(pfx.authSafe.content->data,
     428           0 :                                         pfx.authSafe.content->length,
     429             :                                         &asdata,
     430             :                                         NULL);
     431           0 :         free_PKCS12_PFX(&pfx);
     432           0 :         if (ret) {
     433           0 :             hx509_clear_error_string(context);
     434           0 :             goto out;
     435             :         }
     436           0 :         ret = decode_PKCS12_AuthenticatedSafe(asdata.data,
     437             :                                               asdata.length,
     438             :                                               &as,
     439             :                                               NULL);
     440           0 :         der_free_octet_string(&asdata);
     441           0 :         if (ret) {
     442           0 :             hx509_clear_error_string(context);
     443           0 :             goto out;
     444             :         }
     445             :     }
     446             : 
     447           0 :     for (i = 0; i < as.len; i++)
     448           0 :         parse_pkcs12_type(context,
     449             :                           c,
     450             :                           flags,
     451           0 :                           &as.val[i].contentType,
     452           0 :                           as.val[i].content->data,
     453           0 :                           as.val[i].content->length,
     454             :                           NULL);
     455             : 
     456           0 :     free_PKCS12_AuthenticatedSafe(&as);
     457             : 
     458           0 :     ret = _hx509_collector_collect_certs(context, c, &p12->certs);
     459           0 :     if (ret == 0)
     460           0 :         *data = p12;
     461             : 
     462           0 : out:
     463           0 :     _hx509_collector_free(c);
     464             : 
     465           0 :     if (ret && p12) {
     466           0 :         if (p12->fn)
     467           0 :             free(p12->fn);
     468           0 :         if (p12->certs)
     469           0 :             hx509_certs_free(&p12->certs);
     470           0 :         free(p12);
     471             :     }
     472             : 
     473           0 :     return ret;
     474             : }
     475             : 
     476             : static int
     477           0 : addBag(hx509_context context,
     478             :        PKCS12_AuthenticatedSafe *as,
     479             :        const heim_oid *oid,
     480             :        void *data,
     481             :        size_t length)
     482             : {
     483             :     void *ptr;
     484             :     int ret;
     485             : 
     486           0 :     ptr = realloc(as->val, sizeof(as->val[0]) * (as->len + 1));
     487           0 :     if (ptr == NULL) {
     488           0 :         hx509_set_error_string(context, 0, ENOMEM, "out of memory");
     489           0 :         return ENOMEM;
     490             :     }
     491           0 :     as->val = ptr;
     492             : 
     493           0 :     ret = der_copy_oid(oid, &as->val[as->len].contentType);
     494           0 :     if (ret) {
     495           0 :         hx509_set_error_string(context, 0, ret, "out of memory");
     496           0 :         return ret;
     497             :     }
     498             : 
     499           0 :     as->val[as->len].content = calloc(1, sizeof(*as->val[0].content));
     500           0 :     if (as->val[as->len].content == NULL) {
     501           0 :         der_free_oid(&as->val[as->len].contentType);
     502           0 :         hx509_set_error_string(context, 0, ENOMEM, "malloc out of memory");
     503           0 :         return ENOMEM;
     504             :     }
     505             : 
     506           0 :     as->val[as->len].content->data = data;
     507           0 :     as->val[as->len].content->length = length;
     508             : 
     509           0 :     as->len++;
     510             : 
     511           0 :     return 0;
     512             : }
     513             : 
     514             : struct store_func_ctx {
     515             :     PKCS12_AuthenticatedSafe as;
     516             :     int store_flags;
     517             : };
     518             : 
     519             : static int HX509_LIB_CALL
     520           0 : store_func(hx509_context context, void *d, hx509_cert c)
     521             : {
     522           0 :     struct store_func_ctx *ctx = d;
     523             :     PKCS12_OctetString os;
     524             :     PKCS12_CertBag cb;
     525             :     size_t size;
     526             :     int ret;
     527             : 
     528           0 :     memset(&os, 0, sizeof(os));
     529           0 :     memset(&cb, 0, sizeof(cb));
     530             : 
     531           0 :     os.data = NULL;
     532           0 :     os.length = 0;
     533             : 
     534           0 :     ret = hx509_cert_binary(context, c, &os);
     535           0 :     if (ret)
     536           0 :         return ret;
     537             : 
     538           0 :     ASN1_MALLOC_ENCODE(PKCS12_OctetString,
     539             :                        cb.certValue.data,cb.certValue.length,
     540             :                        &os, &size, ret);
     541           0 :     free(os.data);
     542           0 :     if (ret)
     543           0 :         goto out;
     544           0 :     ret = der_copy_oid(&asn1_oid_id_pkcs_9_at_certTypes_x509, &cb.certType);
     545           0 :     if (ret) {
     546           0 :         free_PKCS12_CertBag(&cb);
     547           0 :         goto out;
     548             :     }
     549           0 :     ASN1_MALLOC_ENCODE(PKCS12_CertBag, os.data, os.length,
     550             :                        &cb, &size, ret);
     551           0 :     free_PKCS12_CertBag(&cb);
     552           0 :     if (ret)
     553           0 :         goto out;
     554             : 
     555           0 :     ret = addBag(context, &ctx->as, &asn1_oid_id_pkcs12_certBag, os.data,
     556             :                  os.length);
     557             : 
     558           0 :     if (_hx509_cert_private_key_exportable(c) &&
     559           0 :         !(ctx->store_flags & HX509_CERTS_STORE_NO_PRIVATE_KEYS)) {
     560           0 :         hx509_private_key key = _hx509_cert_private_key(c);
     561             :         PKCS8PrivateKeyInfo pki;
     562             : 
     563           0 :         memset(&pki, 0, sizeof(pki));
     564             : 
     565           0 :         ret = der_parse_hex_heim_integer("00", &pki.version);
     566           0 :         if (ret)
     567           0 :             return ret;
     568           0 :         ret = _hx509_private_key_oid(context, key,
     569             :                                      &pki.privateKeyAlgorithm.algorithm);
     570           0 :         if (ret) {
     571           0 :             free_PKCS8PrivateKeyInfo(&pki);
     572           0 :             return ret;
     573             :         }
     574           0 :         ret = _hx509_private_key_export(context,
     575             :                                         _hx509_cert_private_key(c),
     576             :                                         HX509_KEY_FORMAT_DER,
     577             :                                         &pki.privateKey);
     578           0 :         if (ret) {
     579           0 :             free_PKCS8PrivateKeyInfo(&pki);
     580           0 :             return ret;
     581             :         }
     582             :         /* set attribute, asn1_oid_id_pkcs_9_at_localKeyId */
     583             : 
     584           0 :         ASN1_MALLOC_ENCODE(PKCS8PrivateKeyInfo, os.data, os.length,
     585             :                            &pki, &size, ret);
     586           0 :         free_PKCS8PrivateKeyInfo(&pki);
     587           0 :         if (ret)
     588           0 :             return ret;
     589             : 
     590           0 :         ret = addBag(context, &ctx->as, &asn1_oid_id_pkcs12_keyBag, os.data,
     591             :                      os.length);
     592           0 :         if (ret)
     593           0 :             return ret;
     594             :     }
     595             : 
     596           0 : out:
     597           0 :     return ret;
     598             : }
     599             : 
     600             : static int
     601           0 : p12_store(hx509_context context,
     602             :           hx509_certs certs, void *data, int flags, hx509_lock lock)
     603             : {
     604           0 :     struct ks_pkcs12 *p12 = data;
     605             :     PKCS12_PFX pfx;
     606             :     struct store_func_ctx ctx;
     607             :     PKCS12_OctetString asdata;
     608             :     size_t size;
     609             :     int ret;
     610             : 
     611           0 :     memset(&ctx, 0, sizeof(ctx));
     612           0 :     memset(&pfx, 0, sizeof(pfx));
     613           0 :     ctx.store_flags = flags;
     614             : 
     615           0 :     ret = hx509_certs_iter_f(context, p12->certs, store_func, &ctx);
     616           0 :     if (ret)
     617           0 :         goto out;
     618             : 
     619           0 :     ASN1_MALLOC_ENCODE(PKCS12_AuthenticatedSafe, asdata.data, asdata.length,
     620             :                        &ctx.as, &size, ret);
     621           0 :     free_PKCS12_AuthenticatedSafe(&ctx.as);
     622           0 :     if (ret)
     623           0 :         return ret;
     624             : 
     625           0 :     ret = der_parse_hex_heim_integer("03", &pfx.version);
     626           0 :     if (ret) {
     627           0 :         free(asdata.data);
     628           0 :         goto out;
     629             :     }
     630             : 
     631           0 :     pfx.authSafe.content = calloc(1, sizeof(*pfx.authSafe.content));
     632             : 
     633           0 :     ASN1_MALLOC_ENCODE(PKCS12_OctetString,
     634             :                        pfx.authSafe.content->data,
     635             :                        pfx.authSafe.content->length,
     636             :                        &asdata, &size, ret);
     637           0 :     free(asdata.data);
     638           0 :     if (ret)
     639           0 :         goto out;
     640             : 
     641           0 :     ret = der_copy_oid(&asn1_oid_id_pkcs7_data, &pfx.authSafe.contentType);
     642           0 :     if (ret)
     643           0 :         goto out;
     644             : 
     645           0 :     ASN1_MALLOC_ENCODE(PKCS12_PFX, asdata.data, asdata.length,
     646             :                        &pfx, &size, ret);
     647           0 :     if (ret)
     648           0 :         goto out;
     649             : 
     650             : #if 0
     651             :     const struct _hx509_password *pw;
     652             : 
     653             :     pw = _hx509_lock_get_passwords(lock);
     654             :     if (pw != NULL) {
     655             :         pfx.macData = calloc(1, sizeof(*pfx.macData));
     656             :         if (pfx.macData == NULL) {
     657             :             ret = ENOMEM;
     658             :             hx509_set_error_string(context, 0, ret, "malloc out of memory");
     659             :             return ret;
     660             :         }
     661             :         if (pfx.macData == NULL) {
     662             :             free(asdata.data);
     663             :             goto out;
     664             :         }
     665             :     }
     666             :     ret = calculate_hash(&aspath, pw, pfx.macData);
     667             : #endif
     668             : 
     669           0 :     rk_dumpdata(p12->fn, asdata.data, asdata.length);
     670           0 :     free(asdata.data);
     671             : 
     672           0 : out:
     673           0 :     free_PKCS12_AuthenticatedSafe(&ctx.as);
     674           0 :     free_PKCS12_PFX(&pfx);
     675             : 
     676           0 :     return ret;
     677             : }
     678             : 
     679             : 
     680             : static int
     681           0 : p12_free(hx509_certs certs, void *data)
     682             : {
     683           0 :     struct ks_pkcs12 *p12 = data;
     684           0 :     hx509_certs_free(&p12->certs);
     685           0 :     free(p12->fn);
     686           0 :     free(p12);
     687           0 :     return 0;
     688             : }
     689             : 
     690             : static int
     691           0 : p12_add(hx509_context context, hx509_certs certs, void *data, hx509_cert c)
     692             : {
     693           0 :     struct ks_pkcs12 *p12 = data;
     694           0 :     return hx509_certs_add(context, p12->certs, c);
     695             : }
     696             : 
     697             : static int
     698           0 : p12_iter_start(hx509_context context,
     699             :                hx509_certs certs,
     700             :                void *data,
     701             :                void **cursor)
     702             : {
     703           0 :     struct ks_pkcs12 *p12 = data;
     704           0 :     return hx509_certs_start_seq(context, p12->certs, cursor);
     705             : }
     706             : 
     707             : static int
     708           0 : p12_iter(hx509_context context,
     709             :          hx509_certs certs,
     710             :          void *data,
     711             :          void *cursor,
     712             :          hx509_cert *cert)
     713             : {
     714           0 :     struct ks_pkcs12 *p12 = data;
     715           0 :     return hx509_certs_next_cert(context, p12->certs, cursor, cert);
     716             : }
     717             : 
     718             : static int
     719           0 : p12_iter_end(hx509_context context,
     720             :              hx509_certs certs,
     721             :              void *data,
     722             :              void *cursor)
     723             : {
     724           0 :     struct ks_pkcs12 *p12 = data;
     725           0 :     return hx509_certs_end_seq(context, p12->certs, cursor);
     726             : }
     727             : 
     728             : static int
     729           0 : p12_destroy(hx509_context context, hx509_certs certs, void *data)
     730             : {
     731           0 :     struct ks_pkcs12 *p12 = data;
     732           0 :     return _hx509_erase_file(context, p12->fn);
     733             : }
     734             : 
     735             : static struct hx509_keyset_ops keyset_pkcs12 = {
     736             :     "PKCS12",
     737             :     0,
     738             :     p12_init,
     739             :     p12_store,
     740             :     p12_free,
     741             :     p12_add,
     742             :     NULL,
     743             :     p12_iter_start,
     744             :     p12_iter,
     745             :     p12_iter_end,
     746             :     NULL,
     747             :     NULL,
     748             :     NULL,
     749             :     p12_destroy
     750             : };
     751             : 
     752             : HX509_LIB_FUNCTION void HX509_LIB_CALL
     753      555816 : _hx509_ks_pkcs12_register(hx509_context context)
     754             : {
     755      555816 :     _hx509_ks_register(context, &keyset_pkcs12);
     756      555816 : }

Generated by: LCOV version 1.13