summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authornahi <nahi@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2011-07-14 05:41:05 +0000
committernahi <nahi@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2011-07-14 05:41:05 +0000
commitab86f1cffb204ab2c51c39926b9c34c4e608c5ad (patch)
treef2d1d7d8e5b18af53b51096c75af41f4908702b8
parentf10ef64f1b969cb7a4af50c6a898bc81d1467b23 (diff)
* ext/openssl/ossl.c (ossl_verify_cb): trap the exception from
verify callback of SSLContext and X509Store and make the verification fail normally. Raising exception directly from callback causes orphan resouces in OpenSSL stack. Patched by Ippei Obayashi. See #4445. * test/openssl/test_ssl.rb (test_exception_in_verify_callback_is_ignored): test it. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@32537 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
-rw-r--r--ChangeLog11
-rw-r--r--ext/openssl/ossl.c7
-rw-r--r--test/openssl/test_pair.rb2
-rw-r--r--test/openssl/test_ssl.rb20
-rw-r--r--test/openssl/utils.rb2
5 files changed, 39 insertions, 3 deletions
diff --git a/ChangeLog b/ChangeLog
index de2a26c94c..b81f351ac2 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,14 @@
+Thu Jul 14 12:19:34 2011 Hiroshi Nakamura <nahi@ruby-lang.org>
+
+ * ext/openssl/ossl.c (ossl_verify_cb): trap the exception from
+ verify callback of SSLContext and X509Store and make the
+ verification fail normally. Raising exception directly from callback
+ causes orphan resouces in OpenSSL stack. Patched by Ippei Obayashi.
+ See #4445.
+
+ * test/openssl/test_ssl.rb
+ (test_exception_in_verify_callback_is_ignored): test it.
+
Tue Jul 12 23:41:49 2011 KOSAKI Motohiro <kosaki.motohiro@gmail.com>
* NEWS: add a description of Signal.trap change.
diff --git a/ext/openssl/ossl.c b/ext/openssl/ossl.c
index c5321b60ae..f3410b64e8 100644
--- a/ext/openssl/ossl.c
+++ b/ext/openssl/ossl.c
@@ -223,8 +223,11 @@ ossl_verify_cb(int ok, X509_STORE_CTX *ctx)
args.proc = proc;
args.preverify_ok = ok ? Qtrue : Qfalse;
args.store_ctx = rctx;
- ret = rb_ensure(ossl_call_verify_cb_proc, (VALUE)&args,
- ossl_x509stctx_clear_ptr, rctx);
+ ret = rb_protect((VALUE(*)(VALUE))ossl_call_verify_cb_proc, (VALUE)&args, &state);
+ ossl_x509stctx_clear_ptr(rctx);
+ if (state) {
+ rb_warn("exception in verify_callback is ignored");
+ }
}
if (ret == Qtrue) {
X509_STORE_CTX_set_error(ctx, X509_V_OK);
diff --git a/test/openssl/test_pair.rb b/test/openssl/test_pair.rb
index d31781f6e7..940fa0c0db 100644
--- a/test/openssl/test_pair.rb
+++ b/test/openssl/test_pair.rb
@@ -238,6 +238,8 @@ class OpenSSL::TestPair < Test::Unit::TestCase
s1.print "a\ndef"
assert_equal("a\n", s2.gets)
ensure
+ s1.close if s1 && !s1.closed?
+ s2.close if s2 && !s2.closed?
serv.close if serv && !serv.closed?
sock1.close if sock1 && !sock1.closed?
sock2.close if sock2 && !sock2.closed?
diff --git a/test/openssl/test_ssl.rb b/test/openssl/test_ssl.rb
index 8c3d00e5e5..07154eac01 100644
--- a/test/openssl/test_ssl.rb
+++ b/test/openssl/test_ssl.rb
@@ -238,6 +238,26 @@ class OpenSSL::TestSSL < OpenSSL::SSLTestCase
}
end
+ def test_exception_in_verify_callback_is_ignored
+ start_server(PORT, OpenSSL::SSL::VERIFY_NONE, true){|server, port|
+ sock = TCPSocket.new("127.0.0.1", port)
+ ctx = OpenSSL::SSL::SSLContext.new
+ ctx.set_params(
+ :verify_callback => Proc.new do |preverify_ok, store_ctx|
+ store_ctx.error = OpenSSL::X509::V_OK
+ raise RuntimeError
+ end
+ )
+ ssl = OpenSSL::SSL::SSLSocket.new(sock, ctx)
+ OpenSSL::TestUtils.silent do
+ # SSLError, not RuntimeError
+ assert_raise(OpenSSL::SSL::SSLError) { ssl.connect }
+ end
+ assert_equal(OpenSSL::X509::V_ERR_CERT_REJECTED, ssl.verify_result)
+ ssl.close
+ }
+ end
+
def test_sslctx_set_params
start_server(PORT, OpenSSL::SSL::VERIFY_NONE, true){|server, port|
sock = TCPSocket.new("127.0.0.1", port)
diff --git a/test/openssl/utils.rb b/test/openssl/utils.rb
index 77a6b3cc77..c4c0a0c040 100644
--- a/test/openssl/utils.rb
+++ b/test/openssl/utils.rb
@@ -275,7 +275,7 @@ aPgwHyJBiK1/ebK3tYcrSKrOoRyrAgEC
server_loop(ctx, ssls, server_proc)
end
- $stderr.printf("%s started: pid=%d port=%d\n", SSL_SERVER, pid, port) if $DEBUG
+ $stderr.printf("%s started: pid=%d port=%d\n", SSL_SERVER, $$, port) if $DEBUG
block.call(server, port.to_i)
ensure