3434import java .security .*;
3535import java .security .interfaces .DSAPrivateKey ;
3636import java .security .interfaces .DSAPublicKey ;
37+ import java .security .interfaces .ECPublicKey ;
3738import java .security .interfaces .RSAPrivateCrtKey ;
3839import java .security .interfaces .RSAPublicKey ;
3940import java .security .spec .InvalidKeySpecException ;
@@ -88,6 +89,20 @@ public static RaiseException newPKeyError(Ruby runtime, String message) {
8889 return Utils .newError (runtime , (RubyClass ) _PKey (runtime ).getConstantAt ("PKeyError" ), message );
8990 }
9091
92+ public static PKey newInstance (final Ruby runtime , final PublicKey publicKey ) {
93+ if (publicKey instanceof RSAPublicKey ) {
94+ return new PKeyRSA (runtime , (RSAPublicKey ) publicKey );
95+ }
96+ if (publicKey instanceof DSAPublicKey ) {
97+ return new PKeyDSA (runtime , (DSAPublicKey ) publicKey );
98+ }
99+ if (publicKey instanceof ECPublicKey ) {
100+ return new PKeyEC (runtime , publicKey );
101+ }
102+ assert publicKey != null ;
103+ throw runtime .newNotImplementedError ("public key algorithm: " + (publicKey != null ? publicKey .getAlgorithm () : "nil" ));
104+ }
105+
91106 static RubyModule _PKey (final Ruby runtime ) {
92107 return (RubyModule ) runtime .getModule ("OpenSSL" ).getConstantAt ("PKey" );
93108 }
@@ -122,20 +137,15 @@ public static IRubyObject read(final ThreadContext context, IRubyObject recv, IR
122137 if (keyPair != null ) {
123138 final String alg = getAlgorithm (keyPair );
124139 if ( "RSA" .equals (alg ) ) {
125- return new PKeyRSA (runtime , _PKey (runtime ).getClass ("RSA" ),
126- (RSAPrivateCrtKey ) keyPair .getPrivate (), (RSAPublicKey ) keyPair .getPublic ()
127- );
140+ return new PKeyRSA (runtime , _PKey (runtime ).getClass ("RSA" ), (RSAPrivateCrtKey ) keyPair .getPrivate (), (RSAPublicKey ) keyPair .getPublic ());
128141 }
129142 if ( "DSA" .equals (alg ) ) {
130- return new PKeyDSA (runtime , _PKey (runtime ).getClass ("DSA" ),
131- (DSAPrivateKey ) keyPair .getPrivate (), (DSAPublicKey ) keyPair .getPublic ()
132- );
143+ return new PKeyDSA (runtime , _PKey (runtime ).getClass ("DSA" ), (DSAPrivateKey ) keyPair .getPrivate (), (DSAPublicKey ) keyPair .getPublic ());
133144 }
134- if ( "EC" .equals (alg ) ) {
135- return new PKeyEC (runtime , _PKey (runtime ).getClass ("EC" ),
136- keyPair .getPrivate (), keyPair .getPublic ()
137- );
145+ if ( "EC" .equals (alg ) || "ECDSA" .equals (alg ) ) { // Sun vs BC provider naming
146+ return new PKeyEC (runtime , _PKey (runtime ).getClass ("EC" ), keyPair .getPrivate (), keyPair .getPublic ());
138147 }
148+ debug (runtime , "PKey readPrivateKey unexpected key pair algorithm: " + alg );
139149 }
140150
141151 PublicKey pubKey = null ;
@@ -168,16 +178,14 @@ public static IRubyObject read(final ThreadContext context, IRubyObject recv, IR
168178 }
169179 }
170180
171- if (pubKey != null ) {
172- if ( "RSA" .equals (pubKey .getAlgorithm ()) ) {
173- return new PKeyRSA (runtime , (RSAPublicKey ) pubKey );
174- }
175- if ( "DSA" .equals (pubKey .getAlgorithm ()) ) {
176- return new PKeyDSA (runtime , (DSAPublicKey ) pubKey );
177- }
178- if ( "EC" .equals (pubKey .getAlgorithm ()) ) {
179- return new PKeyEC (runtime , pubKey );
180- }
181+ if (pubKey instanceof RSAPublicKey ) {
182+ return new PKeyRSA (runtime , (RSAPublicKey ) pubKey );
183+ }
184+ if (pubKey instanceof DSAPublicKey ) {
185+ return new PKeyDSA (runtime , (DSAPublicKey ) pubKey );
186+ }
187+ if (pubKey instanceof ECPublicKey ) {
188+ return new PKeyEC (runtime , pubKey );
181189 }
182190
183191 throw newPKeyError (runtime , "Could not parse PKey: unsupported" );
@@ -188,7 +196,6 @@ private static String getAlgorithm(final KeyPair key) {
188196 if ( key .getPublic () != null ) return key .getPublic ().getAlgorithm ();
189197 return null ;
190198 }
191-
192199 }
193200
194201 public PKey (Ruby runtime , RubyClass type ) {
0 commit comments