Hi,

(2010/01/12 9:38), Dr. Stephen Henson wrote:
> On Mon, Jan 11, 2010, NARUSE, Yui wrote:
>> So I request X509_STORE_set_default_paths call this.
>> When this is merge, both Unix user and Windows user can use
>> the system's default root certificates.
>>
>> I should file this to Request Tracker as a bug? (even if this is feature 
>> request)
>>
> 
> Some CryptoAPI handling code already exists in the CryptoAPI ENGINE and I'd
> suggest that a ctrl for that would be the best place to put it. There are some
> debug options already that can dump a whole store to standard output.
> 
> However some additional code would be needed because that just adds the whole
> store without any purpose setting code. This could cause security issues if
> for example client certificate authorities are used for server signing for
> example.

Thank you for your comment.
So I rewrite my patch as you said: use CryptoAPI ENGINE.

How about is this?

-- 
NARUSE, Yui  <nar...@airemix.jp>
Index: crypto/x509/x509_d2.c
===================================================================
RCS file: /v/openssl/cvs/openssl/crypto/x509/x509_d2.c,v
retrieving revision 1.7
diff -p -u -r1.7 x509_d2.c
--- crypto/x509/x509_d2.c       19 Feb 2001 16:02:21 -0000      1.7
+++ crypto/x509/x509_d2.c       15 Jan 2010 01:00:16 -0000
@@ -59,9 +59,28 @@
 #include <stdio.h>
 #include "cryptlib.h"
 #include <openssl/crypto.h>
+#include <openssl/engine.h>
 #include <openssl/x509.h>
 
 #ifndef OPENSSL_NO_STDIO
+static void X509_STORE_load_windows_systemstore(X509_STORE *ctx)
+       {
+       ENGINE *e;
+       const char *engine_id = "capi";
+       ENGINE_load_builtin_engines();
+       e = ENGINE_by_id(engine_id);
+       if (!e) return;
+       if (!ENGINE_init(e))
+               {
+               ENGINE_free(e);
+               return;
+               }
+       ENGINE_ctrl_cmd_string(e, "store_name", "ROOT", 0);
+       ENGINE_ctrl_cmd(e, "load_certs", 0, ctx, NULL, 0);
+       ENGINE_finish(e);
+       ENGINE_free(e);
+        }
+
 int X509_STORE_set_default_paths(X509_STORE *ctx)
        {
        X509_LOOKUP *lookup;
@@ -77,6 +96,8 @@ int X509_STORE_set_default_paths(X509_ST
        /* clear any errors */
        ERR_clear_error();
 
+       X509_STORE_load_windows_systemstore(ctx);
+
        return(1);
        }
 
Index: engines/e_capi.c
===================================================================
RCS file: /v/openssl/cvs/openssl/engines/e_capi.c,v
retrieving revision 1.28
diff -u -p -r1.28 e_capi.c
--- engines/e_capi.c    30 Dec 2009 11:46:54 -0000      1.28
+++ engines/e_capi.c    15 Jan 2010 15:18:36 -0000
@@ -121,6 +121,7 @@ static void CAPI_trace(CAPI_CTX *ctx, ch
 static int capi_list_providers(CAPI_CTX *ctx, BIO *out);
 static int capi_list_containers(CAPI_CTX *ctx, BIO *out);
 int capi_list_certs(CAPI_CTX *ctx, BIO *out, char *storename);
+static int capi_enum_certs(CAPI_CTX *ctx, char *id, void *ptr, int ptype);
 void capi_free_key(CAPI_KEY *key);
 
 static PCCERT_CONTEXT capi_find_cert(CAPI_CTX *ctx, const char *id, HCERTSTORE 
hstore);
@@ -225,6 +226,7 @@ static int capi_ctx_set_provname_idx(CAP
 #define CAPI_CMD_LOOKUP_METHOD         (ENGINE_CMD_BASE + 11)
 #define CAPI_CMD_STORE_NAME            (ENGINE_CMD_BASE + 12)
 #define CAPI_CMD_STORE_FLAGS           (ENGINE_CMD_BASE + 13)
+#define CAPI_CMD_LOAD_CERTS            (ENGINE_CMD_BASE + 14)
 
 static const ENGINE_CMD_DEFN capi_cmd_defns[] = {
        {CAPI_CMD_LIST_CERTS,
@@ -284,6 +286,10 @@ static const ENGINE_CMD_DEFN capi_cmd_de
                "store_flags",
                "Certificate store flags: 1 = system store",
                ENGINE_CMD_FLAG_NUMERIC},
+       {CAPI_CMD_LOAD_CERTS,
+               "load_certs",
+               "Load certificates in store",
+               ENGINE_CMD_FLAG_NO_INPUT},
 
        {0, NULL, NULL, 0}
        };
@@ -315,6 +321,10 @@ static int capi_ctrl(ENGINE *e, int cmd,
                ret = capi_list_certs(ctx, out, NULL);
                break;
 
+               case CAPI_CMD_LOAD_CERTS:
+               ret = capi_enum_certs(ctx, NULL, p, CAPI_CMD_LOAD_CERTS);
+               break;
+
                case CAPI_CMD_LOOKUP_CERT:
                ret = capi_list_certs(ctx, out, p);
                break;
@@ -1331,13 +1341,38 @@ HCERTSTORE capi_open_store(CAPI_CTX *ctx
        return hstore;
        }
 
-int capi_list_certs(CAPI_CTX *ctx, BIO *out, char *id)
+void capi_store_cert(CAPI_CTX *ctx, X509_STORE *xstore, PCCERT_CONTEXT cert)
+       {
+       X509 *x509 = NULL;
+       x509 = d2i_X509(NULL, (const unsigned char**)&cert->pbCertEncoded, 
cert->cbCertEncoded);
+       if (x509)
+               {
+               X509_STORE_add_cert(xstore, x509);
+               X509_free(x509);
+               }
+       }
+
+static int capi_enum_certs(CAPI_CTX *ctx, char *id, void *ptr, int ptype)
        {
        char *storename;
        int idx;
        int ret = 1;
        HCERTSTORE hstore;
        PCCERT_CONTEXT cert = NULL;
+       BIO *out = NULL;
+       X509_STORE *xstore = NULL;
+
+       switch (ptype) {
+         case CAPI_CMD_LIST_CERTS:
+           out = (BIO *)ptr;
+           break;
+         case CAPI_CMD_LOAD_CERTS:
+           xstore = (X509_STORE *)ptr;
+           break;
+         default:
+           return 0;
+           break;
+       }
 
        storename = ctx->storename;
        if (!storename)
@@ -1355,7 +1390,8 @@ int capi_list_certs(CAPI_CTX *ctx, BIO *
                        ret = 0;
                        goto err;
                        }
-               capi_dump_cert(ctx, out, cert);
+               if (out) capi_dump_cert(ctx, out, cert);
+               if (xstore) capi_store_cert(ctx, xstore, cert);
                CertFreeCertificateContext(cert);
                }
        else
@@ -1366,8 +1402,12 @@ int capi_list_certs(CAPI_CTX *ctx, BIO *
                        cert = CertEnumCertificatesInStore(hstore, cert);
                        if (!cert)
                                break;
-                       BIO_printf(out, "Certificate %d\n", idx);
-                       capi_dump_cert(ctx, out, cert);
+                       if (out)
+                               {
+                               BIO_printf(out, "Certificate %d\n", idx);
+                               capi_dump_cert(ctx, out, cert);
+                               }
+                       if (xstore) capi_store_cert(ctx, xstore, cert);
                        }
                }
        err:
@@ -1375,6 +1415,11 @@ int capi_list_certs(CAPI_CTX *ctx, BIO *
        return ret;
        }
 
+int capi_list_certs(CAPI_CTX *ctx, BIO *out, char *id)
+       {
+               return capi_enum_certs(ctx, id, (void *)out, 
CAPI_CMD_LIST_CERTS);
+       }
+
 static PCCERT_CONTEXT capi_find_cert(CAPI_CTX *ctx, const char *id, HCERTSTORE 
hstore)
        {
        PCCERT_CONTEXT cert = NULL;

Reply via email to