我想检查安装的Android应用程序是否具有自签名或可信证书。问题是我下面列出的代码会为所有已安装的(包括谷歌制作的)应用程序引发CertificateException。你能帮我找一个问题,为什么它不能正常工作?
Intent intent = new Intent();
intent.setAction(Intent.ACTION_VIEW);
List<ResolveInfo> runningServices = getPackageManager().queryIntentActivities(intent, 0);
TrustManagerFactory tmf = TrustManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
KeyStore ks = KeyStore.getInstance("AndroidCaStore");
ks.load(null, null);
tmf.init(ks);
X509TrustManager trustManager = (X509TrustManager)tmf.getTrustManagers()[0];
PackageManager manager = getPackageManager();
try {
for (ResolveInfo runningService : runningServices) {
PackageInfo info = manager.getPackageInfo(runningService.activityInfo.packageName,
PackageManager.GET_SIGNATURES);
Signature signature = info.signatures[0];
Signature[] arrSignatures = info.signatures;
for (Signature sig : arrSignatures) {
byte[] rawCert = sig.toByteArray();
InputStream certStream = new ByteArrayInputStream(rawCert);
CertificateFactory certFactory;
X509Certificate x509Cert;
try {
certFactory = CertificateFactory.getInstance("X509");
x509Cert = (X509Certificate) certFactory.generateCertificate(certStream);
trustManager.checkServerTrusted(new X509Certificate[] { x509Cert }, "RSA");
}
catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (KeyStoreException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (CertificateException e) {
e.printStackTrace();
}
}
}
} catch (PackageManager.NameNotFoundException e) {
e.printStackTrace();
}
答案 0 :(得分:0)
答案非常明显:我们无法使用受信任的证书链验证Android应用程序证书(通常用ssl guts来检查Web资源证书),因为它们是自签名的。这就是checkServerTrusted函数在此类检查期间引发CertificateException的原因。此book提供以下信息:
因为进程与包名绑定,并且包名是 与签名相关联,签名在保护数据方面发挥着作用 属于一个包。包通常用a签名 自签名PKI(公钥基础结构)证书。证书 识别包的作者是谁。这些证书需要 不是由证书颁发机构颁发的。这意味着信息 证书未经任何机构批准或验证。这个 意味着可以创建一个证明其姓名的证书 谷歌。唯一的保证是保留此包名称 该用户如果之前没有人在市场上声称它,那么任何人 该包的后续更新仅提供给该用户 (由该证书确定)。