From 8f91af4cac0ea777036d4a4db98622504907bf8b Mon Sep 17 00:00:00 2001 From: Brice Figureau Date: Sun, 24 May 2009 17:54:50 +0200 Subject: [PATCH 7/7] Implement some missing SSLSocket methods This changeset provide implementation of: SSLSocket#cipher SSLSocket#cert SSLSocket#peer_cert_chain Signed-off-by: Brice Figureau --- src/java/org/jruby/ext/openssl/SSLSocket.java | 27 +++++++++++++++++++++--- src/java/org/jruby/ext/openssl/X509Cert.java | 6 +++++ 2 files changed, 29 insertions(+), 4 deletions(-) diff --git a/src/java/org/jruby/ext/openssl/SSLSocket.java b/src/java/org/jruby/ext/openssl/SSLSocket.java index 4ac45ae..2e3926c 100644 --- a/src/java/org/jruby/ext/openssl/SSLSocket.java +++ b/src/java/org/jruby/ext/openssl/SSLSocket.java @@ -49,6 +49,7 @@ import javax.net.ssl.SSLPeerUnverifiedException; import javax.net.ssl.SSLSession; import org.jruby.Ruby; +import org.jruby.RubyArray; import org.jruby.RubyClass; import org.jruby.RubyIO; import org.jruby.RubyModule; @@ -499,7 +500,14 @@ public class SSLSocket extends RubyObject { @JRubyMethod public IRubyObject cert() { - System.err.println("WARNING: unimplemented method called: SSLSocket#cert"); + try { + Certificate[] cert = engine.getSession().getLocalCertificates(); + if (cert.length > 0) { + return X509Cert.wrap(getRuntime(), cert[0]); + } + } catch (CertificateEncodingException ex) { + throw X509Cert.newCertificateError(getRuntime(), ex); + } return getRuntime().getNil(); } @@ -520,14 +528,25 @@ public class SSLSocket extends RubyObject { @JRubyMethod public IRubyObject peer_cert_chain() { - System.err.println("WARNING: unimplemented method called: SSLSocket#peer_cert_chain"); + try { + javax.security.cert.Certificate[] certs = engine.getSession().getPeerCertificateChain(); + + RubyArray arr = getRuntime().newArray(certs.length); + for(int i = 0 ; i < certs.length; i++ ) { + arr.add(X509Cert.wrap(getRuntime(), certs[i])); + } + return arr; + } catch (javax.security.cert.CertificateEncodingException e) { + throw X509Cert.newCertificateError(getRuntime(), e); + } catch (SSLPeerUnverifiedException ex) { + Logger.getLogger(SSLSocket.class.getName()).log(Level.SEVERE, null, ex); + } return getRuntime().getNil(); } @JRubyMethod public IRubyObject cipher() { - System.err.println("WARNING: unimplemented method called: SSLSocket#cipher"); - return getRuntime().getNil(); + return getRuntime().newString(engine.getSession().getCipherSuite()); } @JRubyMethod diff --git a/src/java/org/jruby/ext/openssl/X509Cert.java b/src/java/org/jruby/ext/openssl/X509Cert.java index 0e9727f..ac72e1c 100644 --- a/src/java/org/jruby/ext/openssl/X509Cert.java +++ b/src/java/org/jruby/ext/openssl/X509Cert.java @@ -129,6 +129,12 @@ public class X509Cert extends RubyObject { return cr.callMethod(runtime.getCurrentContext(),"new",RubyString.newString(runtime, c.getEncoded())); } + // this is the javax.security counterpart of the previous wrap method + public static IRubyObject wrap(Ruby runtime, javax.security.cert.Certificate c) throws javax.security.cert.CertificateEncodingException { + RubyClass cr = (RubyClass)(((RubyModule)(runtime.getModule("OpenSSL").getConstant("X509"))).getConstant("Certificate")); + return cr.callMethod(runtime.getCurrentContext(),"new",RubyString.newString(runtime, c.getEncoded())); + } + @JRubyMethod(name="initialize", optional = 1, frame=true) public IRubyObject initialize(ThreadContext context, IRubyObject[] args, Block unusedBlock) { Ruby runtime = context.getRuntime(); -- 1.6.0.2