diff -r d6c861e00208 jni/native/include/ssl_private.h --- a/jni/native/include/ssl_private.h Fri Sep 21 12:22:41 2012 +0300 +++ b/jni/native/include/ssl_private.h Mon Sep 24 13:10:08 2012 +0300 @@ -258,6 +258,8 @@ int verify_depth; int verify_mode; tcn_pass_cb_t *cb_data; + char *crl_file; + char *crl_dir; }; @@ -314,4 +316,6 @@ int SSL_callback_SSL_verify(int, X509_STORE_CTX *); int SSL_rand_seed(const char *file); +int updateCRL(tcn_ssl_ctxt_t *c); + #endif /* SSL_PRIVATE_H */ diff -r d6c861e00208 jni/native/src/sslcontext.c --- a/jni/native/src/sslcontext.c Fri Sep 21 12:22:41 2012 +0300 +++ b/jni/native/src/sslcontext.c Mon Sep 24 13:10:08 2012 +0300 @@ -58,6 +58,7 @@ SSL_BIO_close(c->bio_os); c->bio_os = NULL; } + } return APR_SUCCESS; } @@ -172,6 +173,9 @@ ssl_context_cleanup, apr_pool_cleanup_null); + c->crl_file = NULL; + c->crl_dir = NULL; + return P2J(c); init_failed: return 0; @@ -272,6 +276,41 @@ return rv; } +int updateCRL(tcn_ssl_ctxt_t *c) +{ + X509_LOOKUP *lookup; + + /* if the store exists we reupdate it */ + if(c->crl) { + X509_STORE_free(c->crl); + c->crl = NULL; + } + if ((c->crl = X509_STORE_new()) == NULL) + return 1; + + if(c->crl_file) { + lookup = X509_STORE_add_lookup(c->crl, X509_LOOKUP_file()); + if (lookup == NULL) { + X509_STORE_free(c->crl); + c->crl = NULL; + return 1; + } + X509_LOOKUP_load_file(lookup, c->crl_file, X509_FILETYPE_PEM); + } + if (c->crl_dir) { + lookup = X509_STORE_add_lookup(c->crl, X509_LOOKUP_hash_dir()); + if (lookup == NULL) { + X509_STORE_free(c->crl); + c->crl = NULL; + return 1; + } + X509_LOOKUP_add_dir(lookup, c->crl_dir, X509_FILETYPE_PEM); + } + + return 0; + +} + TCN_IMPLEMENT_CALL(jboolean, SSLContext, setCARevocation)(TCN_STDARGS, jlong ctx, jstring file, jstring path) @@ -280,42 +319,31 @@ TCN_ALLOC_CSTRING(file); TCN_ALLOC_CSTRING(path); jboolean rv = JNI_FALSE; - X509_LOOKUP *lookup; + char err[256]; + int ret; UNREFERENCED(o); TCN_ASSERT(ctx != 0); if (J2S(file) == NULL && J2S(path) == NULL) return JNI_FALSE; - if (!c->crl) { - if ((c->crl = X509_STORE_new()) == NULL) - goto cleanup; + if(J2S(file)) { + c->crl_file = apr_pstrdup(c->pool, J2S(file)); } - if (J2S(file)) { - lookup = X509_STORE_add_lookup(c->crl, X509_LOOKUP_file()); - if (lookup == NULL) { - ERR_error_string(ERR_get_error(), err); - X509_STORE_free(c->crl); - c->crl = NULL; - tcn_Throw(e, "Lookup failed for file %s (%s)", J2S(file), err); - goto cleanup; - } - X509_LOOKUP_load_file(lookup, J2S(file), X509_FILETYPE_PEM); + if(J2S(path)) { + c->crl_dir = apr_pstrdup(c->pool, J2S(path)); } - if (J2S(path)) { - lookup = X509_STORE_add_lookup(c->crl, X509_LOOKUP_hash_dir()); - if (lookup == NULL) { - ERR_error_string(ERR_get_error(), err); - X509_STORE_free(c->crl); - c->crl = NULL; - tcn_Throw(e, "Lookup failed for path %s (%s)", J2S(file), err); - goto cleanup; - } - X509_LOOKUP_add_dir(lookup, J2S(path), X509_FILETYPE_PEM); + + ret = updateCRL(c); + + if(!ret) { + rv = JNI_TRUE; + } else { + ERR_error_string(ERR_get_error(), err); + tcn_Throw(e, "Lookup failed for file %s or path %s (%s)", J2S(file), J2S(path), err); } - rv = JNI_TRUE; -cleanup: + TCN_FREE_CSTRING(file); TCN_FREE_CSTRING(path); return rv; diff -r d6c861e00208 jni/native/src/sslnetwork.c --- a/jni/native/src/sslnetwork.c Fri Sep 21 12:22:41 2012 +0300 +++ b/jni/native/src/sslnetwork.c Mon Sep 24 13:10:08 2012 +0300 @@ -315,6 +315,7 @@ if (ss->net->type != TCN_SOCKET_SSL) return APR_EINVAL; con = (tcn_ssl_conn_t *)ss->opaque; + while (!SSL_is_init_finished(con->ssl)) { if ((s = SSL_do_handshake(con->ssl)) <= 0) { apr_status_t os = apr_get_netos_error(); diff -r d6c861e00208 jni/native/src/sslutils.c --- a/jni/native/src/sslutils.c Fri Sep 21 12:22:41 2012 +0300 +++ b/jni/native/src/sslutils.c Mon Sep 24 13:10:08 2012 +0300 @@ -548,7 +548,42 @@ X509_LU_CRL, subject, &obj); crl = obj.data.crl; + if ((rc > 0) && crl) { + + /* + * Check date of CRL to make sure it's not expired + * If it is expired we try to reload it once. + */ + i = X509_cmp_current_time(X509_CRL_get_nextUpdate(crl)); + + if (i == 0) { + /* TODO: Log Found CRL has invalid nextUpdate field */ + /* In this case we could just abandon */ + X509_STORE_CTX_set_error(ctx, + X509_V_ERR_ERROR_IN_CRL_NEXT_UPDATE_FIELD); + X509_OBJECT_free_contents(&obj); + return 0; + } + + if (i < 0) { + /* TODO: Log Found CRL is expired */ + /* we also try to reload the CRL and try once more */ + int r; + r = updateCRL(con->ctx); + if (r == 0 ) { + memset((char *)&obj, 0, sizeof(obj)); + rc = ssl_X509_STORE_lookup(con->ctx->crl, + X509_LU_CRL, subject, &obj); + crl = obj.data.crl; + } + else{ + X509_STORE_CTX_set_error(ctx, X509_V_ERR_CRL_HAS_EXPIRED); + X509_OBJECT_free_contents(&obj); + } + return 0; + } + /* * Log information about CRL * (A little bit complicated because of ASN.1 and BIOs...)