commit 481c12a8b31c6dd7eba048e8f42d0b9653110621
Author: Oswald Buddenhagen <o...@users.sf.net>
Date:   Wed Jul 29 20:23:54 2020 +0200

    handle CertificateFile more cleanly
    
    properly distribute the certificates between the SSL context's trust
    store and our host cert list.
    
    as a drive-by, clean up some nasty type casts at the cost of including
    a second OpenSSL header into socket.h.

 src/common.h |  1 +
 src/socket.c | 36 ++++++++++++++++++++++++++++--------
 src/socket.h |  3 ++-
 src/util.c   |  2 +-
 4 files changed, 32 insertions(+), 10 deletions(-)

diff --git a/src/common.h b/src/common.h
index 1bf3aa1..359bbbb 100644
--- a/src/common.h
+++ b/src/common.h
@@ -172,6 +172,7 @@ int ATTR_PRINTFLIKE(2, 0) nfvasprintf( char **str, const 
char *fmt, va_list va )
 int ATTR_PRINTFLIKE(2, 3) nfasprintf( char **str, const char *fmt, ... );
 int ATTR_PRINTFLIKE(3, 4) nfsnprintf( char *buf, int blen, const char *fmt, 
... );
 void ATTR_NORETURN oob( void );
+void ATTR_NORETURN oom( void );
 
 char *expand_strdup( const char *s );
 
diff --git a/src/socket.c b/src/socket.c
index 0599aba..ac3c847 100644
--- a/src/socket.c
+++ b/src/socket.c
@@ -194,7 +194,6 @@ verify_cert_host( const server_conf_t *conf, conn_t *sock )
        int i;
        long err;
        X509 *cert;
-       STACK_OF(X509_OBJECT) *trusted;
 
        cert = SSL_get_peer_certificate( sock->ssl );
        if (!cert) {
@@ -202,9 +201,8 @@ verify_cert_host( const server_conf_t *conf, conn_t *sock )
                return -1;
        }
 
-       trusted = (STACK_OF(X509_OBJECT) *)sock->conf->trusted_certs;
-       for (i = 0; i < sk_X509_OBJECT_num( trusted ); i++) {
-               if (!X509_cmp( cert, X509_OBJECT_get0_X509( 
sk_X509_OBJECT_value( trusted, i ) ) )) {
+       for (i = 0; i < sk_X509_num( sock->conf->trusted_certs ); i++) {
+               if (!X509_cmp( cert, sk_X509_value( sock->conf->trusted_certs, 
i ) )) {
                        X509_free( cert );
                        return 0;
                }
@@ -273,11 +271,33 @@ DIAG_POP
                return 0;
        }
 
-       if (conf->cert_file && !SSL_CTX_load_verify_locations( 
mconf->SSLContext, conf->cert_file, NULL )) {
-               print_ssl_errors( "loading certificate file '%s'", 
conf->cert_file );
-               return 0;
+       if (!(mconf->trusted_certs = sk_X509_new_null()))
+               oom();
+       if (conf->cert_file) {
+               X509_STORE *store;
+               if (!(store = X509_STORE_new()))
+                       oom();
+               if (!X509_STORE_load_locations( store, conf->cert_file, NULL )) 
{
+                       print_ssl_errors( "loading certificate file '%s'", 
conf->cert_file );
+                       return 0;
+               }
+               STACK_OF(X509_OBJECT) *objs = X509_STORE_get0_objects( store );
+               for (int i = 0; i < sk_X509_OBJECT_num( objs ); i++) {
+                       X509 *cert = X509_OBJECT_get0_X509( 
sk_X509_OBJECT_value( objs, i ) );
+                       if (cert) {
+                               if (X509_check_ca( cert )) {
+                                       if (!X509_STORE_add_cert( 
SSL_CTX_get_cert_store( mconf->SSLContext ), cert ))
+                                               oom();
+                               } else {
+                                       X509_up_ref( cert );  // Locking 
failure assumed impossible
+                                       if (!sk_X509_push( 
mconf->trusted_certs, cert ))
+                                               oom();
+                               }
+                       }
+               }
+               X509_STORE_free( store );
        }
-       mconf->trusted_certs = (_STACK *)sk_X509_OBJECT_dup( 
X509_STORE_get0_objects( SSL_CTX_get_cert_store( mconf->SSLContext ) ) );
+
        if (mconf->system_certs && !SSL_CTX_set_default_verify_paths( 
mconf->SSLContext )) {
                ulong err;
                while ((err = ERR_get_error()))
diff --git a/src/socket.h b/src/socket.h
index 5334a89..5b1edd0 100644
--- a/src/socket.h
+++ b/src/socket.h
@@ -31,6 +31,7 @@
 
 #ifdef HAVE_LIBSSL
 # include <openssl/ssl.h>
+# include <openssl/x509.h>
 
 enum {
        TLSv1 = 4,
@@ -55,7 +56,7 @@ typedef struct {
 
        /* these are actually variables and are leaked at the end */
        char ssl_ctx_valid;
-       _STACK *trusted_certs;
+       STACK_OF(X509) *trusted_certs;
        SSL_CTX *SSLContext;
 #endif
 } server_conf_t;
diff --git a/src/util.c b/src/util.c
index a4ee67d..7f8c453 100644
--- a/src/util.c
+++ b/src/util.c
@@ -353,7 +353,7 @@ nfsnprintf( char *buf, int blen, const char *fmt, ... )
        return ret;
 }
 
-static void ATTR_NORETURN
+void
 oom( void )
 {
        fputs( "Fatal: Out of memory\n", stderr );


_______________________________________________
isync-devel mailing list
isync-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/isync-devel

Reply via email to