安卓版本:
final SSLContext context = SSLContext.getInstance("TLS");
final KeyStore keystore = KeyStore.getInstance("PKCS12");
keystore.load(ctx.getAssets().open("ca_cli.pkcs12"), "password".toCharArray());
final KeyManagerFactory keyManagerFactory = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
keyManagerFactory.init(keystore, "password".toCharArray());
context.init(keyManagerFactory.getKeyManagers(), new TrustManager[] { new X509TrustManager() {
@Override
public X509Certificate[] getAcceptedIssuers() { return new X509Certificate[] {}; }
@Override
public void checkClientTrusted(final X509Certificate[] arg0, final String arg1) throws CertificateException {
// TODO Auto-generated method stub
}
@Override
public void checkServerTrusted(final X509Certificate[] arg0, final String arg1) throws CertificateException {
// TODO Auto-generated method stub
}
} }, new SecureRandom());
JVM 版本:
final SSLContext context = SSLContext.getInstance("TLS");
final KeyStore keystore = KeyStore.getInstance("pkcs12");
keystore.load(new FileInputStream(new File("ca-cli.pkcs12")), "password".toCharArray());
final KeyManagerFactory keyManagerFactory = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
keyManagerFactory.init(keystore, "password".toCharArray());
context.init(keyManagerFactory.getKeyManagers(), new TrustManager[] {
new X509TrustManager() {
@Override
public X509Certificate[] getAcceptedIssuers() { return new X509Certificate[]{}; }
@Override
public void checkClientTrusted(final X509Certificate[] arg0, final String arg1) throws CertificateException {
// TODO Auto-generated method stub
}
@Override
public void checkServerTrusted(final X509Certificate[] arg0, final String arg1) throws CertificateException {
// TODO Auto-generated method stub
}
}
}, new SecureRandom());
代码完全相同,但 JVM 版本运行良好,Android 版本生成:
09-16 12:24:17.024: E/AuthByPasswordLoader(14580): Got unexpected error
09-16 12:24:17.024: E/AuthByPasswordLoader(14580):
javax.net.ssl.SSLHandshakeException:
javax.net.ssl.SSLProtocolException: SSL handshake terminated:
ssl=0x656b0148: Failure in SSL library, usually a protocol error
09-16 12:24:17.024: E/AuthByPasswordLoader(14580): error:14094410:SSL
routines:SSL3_READ_BYTES:sslv3 alert handshake failure
(external/openssl/ssl/s3_pkt.c:1290 0x40086500:0x00000003)
我已经尝试转换 PKCS12 -> BKS 但它没有帮助...
最佳答案
所以,如果有人遇到同样的问题 - 结果证明这是一个错误,在 Android 3.0 中引入。
引用 Kenny Root ( Android Security Discussion thread ):
Thanks, it looks like a bug that was introduced in Android 3.0. It will require that client key types have the same CA type. You are seeing this because your client certificate is RSA and the CA is EC.
You can work around this bug for your situation by wrapping the KeyManager and intercepting calls to chooseClientAlias to add "RSA_EC" to the keyTypes.
If you're interested in the particular fix that will be in a future release: https://android-review.googlesource.com/66581
关于java - SSLContext 和 PKCS12 keystore - 适用于 JVM 但不适用于 Android,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18824733/