从CERT.RSA中提取证书

本文介绍了从Android APK包中的CERT.RSA文件获取证书信息的方法,包括使用Linux命令行工具openssl、Java代码及C++代码结合openssl库的方式。

Apk 包中的META-INF目录下,有一个CERT.RSA,它是一个PKCS7 格式的文件。

下面介绍几种从中获取证书的方法。

Linux command line

[plain]  view plain copy
  1. openssl pkcs7 -inform DER -in CERT.RSA -noout -print_certs -text  

你可以得到一个文本输出:

[plain]  view plain copy
  1. Certificate:  
  2.     Data:  
  3.         Version: 3 (0x2)  
  4.         Serial Number: 1281971851 (0x4c69568b)  
  5.         Signature Algorithm: sha1WithRSAEncryption  
  6.         Issuer: CN=Michael Liu  
  7.         Validity  
  8.             Not Before: Aug 16 15:17:31 2010 GMT  
  9.             Not After : Aug 10 15:17:31 2035 GMT  
  10.         Subject: CN=Michael Liu  
  11.         Subject Public Key Info:  
  12.             Public Key Algorithm: rsaEncryption  
  13.             RSA Public Key: (1024 bit)  
  14.                 Modulus (1024 bit):  
  15.                     00:8d:04:84:a2:1e:c6:56:39:f2:cd:a6:f0:48:a5:  
  16.                     f7:5e:71:8f:e1:a8:af:a7:dc:66:92:a2:b9:cf:da:  
  17.                     0f:32:42:ce:83:fe:bc:e1:4f:0a:fd:d9:a8:b3:73:  
  18.                     f4:ff:97:15:17:87:d6:d0:3c:da:01:fc:11:40:7d:  
  19.                     04:da:31:cc:cd:da:d0:e7:7b:e3:c1:84:30:9f:21:  
  20.                     93:95:20:48:b1:2d:24:02:d2:b9:3c:87:0d:fa:b8:  
  21.                     e1:b1:45:f4:8d:90:0a:3b:9d:d8:8a:9a:96:d1:51:  
  22.                     23:0e:8e:c4:09:68:7d:95:be:c6:42:e9:54:a1:5c:  
  23.                     5d:3f:25:d8:5c:c3:42:73:21  
  24.                 Exponent: 65537 (0x10001)  
  25.     Signature Algorithm: sha1WithRSAEncryption  
  26.         78:3c:6b:ef:71:70:55:68:28:80:4d:f8:b5:cd:83:a9:01:21:  
  27.         2a:c1:e4:96:ad:bc:5f:67:0c:cd:c3:34:51:6d:63:90:a9:f9:  
  28.         d5:5e:c7:ef:34:43:86:7d:68:e1:99:87:92:86:34:91:6d:67:  
  29.         6d:b2:22:e9:5e:28:aa:e8:05:52:04:6e:4e:d4:7f:0f:b0:d6:  
  30.         28:f5:2b:11:38:d5:15:cb:e3:e4:c9:99:23:c1:84:4f:ce:69:  
  31.         e9:b1:59:7b:8e:30:01:1c:e1:92:ee:0d:54:61:29:f5:8e:9e:  
  32.         42:72:26:2b:aa:c7:af:d9:c9:d1:85:95:8e:4c:8d:5c:77:c5:  
  33.         ce:4e  

Java

这是最简单的

[java]  view plain copy
  1. import sun.security.pkcs.PKCS7;  
  2. import java.io.FileInputStream;  
  3. import java.io.IOException;  
  4. import java.security.cert.CertificateException;  
  5. import java.security.cert.X509Certificate;  
  6.   
  7. public class Test {  
  8.     public static void main(String[] args) throws CertificateException, IOException {  
  9.         FileInputStream fis = new FileInputStream("/Users/wangchen/Desktop/CERT.RSA");  
  10.         PKCS7 pkcs7 = new PKCS7(fis);  
  11.         X509Certificate publicKey = pkcs7.getCertificates()[0];  
  12.   
  13.         System.out.println("issuer1:" + publicKey.getIssuerDN());  
  14.         System.out.println("subject2:" + publicKey.getSubjectDN());  
  15.         System.out.println(publicKey.getPublicKey());  
  16.     }  
  17. }  

使用openssl-dev 的C API

[cpp]  view plain copy
  1. #include <openssl/bio.h>  
  2. #include <openssl/x509.h>  
  3. #include <openssl/pkcs7.h>  
  4. #include <string>  
  5. #include <iostream>  
  6. using namespace std;  
  7. string to_string(X509_NAME* name)  
  8. {  
  9.     BIO* mem = BIO_new(BIO_s_mem());  
  10.     if (mem == NULL)  
  11.         return NULL;  
  12.   
  13.     if (X509_NAME_print_ex(mem, name, 0, XN_FLAG_RFC2253) < 0)         return NULL;     string str;     char buf[128];     while((BIO_gets(mem, &buf[0], sizeof(buf))) > 0)  
  14.     {  
  15.         str.append(buf);  
  16.     }  
  17.     BIO_free(mem);  
  18.     return str;  
  19. }  
  20.   
  21. int main()  
  22. {  
  23.     FILE* fp;  
  24.     if (!(fp = fopen("CERT.RSA""rb")))  
  25.     {  
  26.         fprintf(stderr, "Error reading input pkcs7 file\n" );  
  27.         exit(1);  
  28.     }  
  29.     /* todo: 这里可能有内存漏洞,有空查一下文档 */  
  30.     PKCS7* pkcs7 = d2i_PKCS7_fp(fp, NULL);  
  31.     X509* cert = sk_X509_pop(pkcs7->d.sign->cert);  
  32.     string subject = to_string(X509_get_subject_name(cert));  
  33.     string issuer = to_string(X509_get_issuer_name(cert));  
  34.     char *modulus = BN_bn2dec(X509_get_pubkey(cert)->pkey.rsa->n);  
  35.     cout << subject << endl;  
  36.     OPENSSL_free(modulus);  
  37.     fclose(fp);  
  38.     return 0;  
  39. }  
在Linux中,可以使用`openssl`工具从证书文件(如PEM或DER格式的X.509证书)中提取公钥。以下是具体方法: --- ### **1. 从PEM格式证书提取公钥** 假设证书文件为`certificate.pem`(X.509格式): ```bash openssl x509 -in certificate.pem -pubkey -noout > public_key.pem ``` - **参数说明**: - `-in certificate.pem`:指定输入的证书文件。 - `-pubkey`:提取公钥。 - `-noout`:不输出证书本身,仅提取公钥。 - `> public_key.pem`:将公钥保存到文件(PEM格式)。 --- ### **2. 从DER格式证书提取公钥** 若证书是二进制DER格式,先转换为PEM或直接处理: ```bash openssl x509 -inform DER -in certificate.der -pubkey -noout > public_key.pem ``` - **关键参数**: - `-inform DER`:指定输入为DER格式。 --- ### **3. 验证提取的公钥** 查看公钥内容(PEM格式): ```bash cat public_key.pem ``` 输出示例: ``` -----BEGIN PUBLIC KEY----- MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAu1SU1LfVLPHCozMxH2Mo 4lgOEePzNm0tRgeLezV6ffAt0gunVTLw7onLRnrq0/IzW7yWR7QkU2BLjQ== -----END PUBLIC KEY----- ``` --- ### **4. 提取公钥并转换格式(可选)** #### **(1) 导出为DER格式(二进制)** ```bash openssl x509 -in certificate.pem -pubkey -noout | openssl rsa -pubin -outform DER -out public_key.der ``` #### **(2) 导出为OpenSSH格式(用于SSH)** ```bash ssh-keygen -f public_key.pem -i -m PKCS8 -e > public_key_ssh.pub ``` --- ### **5. 处理加密的证书(如需密码)** 若证书中的私钥部分受密码保护(罕见情况),需先解密: ```bash openssl pkcs12 -in certificate.p12 -nocerts -nodes -out temp.pem openssl rsa -in temp.pem -pubout -out public_key.pem rm temp.pem # 清理临时文件 ``` --- ### **常见问题** 1. **错误:`unable to load certificate`** - 检查证书格式是否正确(PEM需以`-----BEGIN CERTIFICATE-----`开头)。 - 如果是DER格式,确保添加`-inform DER`参数。 2. **如何确认证书中的公钥算法?** 查看证书详情: ```bash openssl x509 -in certificate.pem -text -noout | grep "Public Key Algorithm" ``` 3. **提取ECC证书的公钥** 若证书使用ECC算法,提取命令相同,但需确认算法: ```bash openssl ec -in ec_public_key.pem -pubin -text -noout ``` 4. **从PKCS#7/PKCS#12文件中提取公钥** - **PKCS#7**: ```bash openssl pkcs7 -in file.p7b -print_certs -out cert.pem openssl x509 -in cert.pem -pubkey -noout > public_key.pem ``` - **PKCS#12**(.pfx/.p12): ```bash openssl pkcs12 -in file.p12 -nokeys -out cert.pem openssl x509 -in cert.pem -pubkey -noout > public_key.pem ``` --- ### **完整示例** ```bash # 生成自签名证书(测试用) openssl req -x509 -newkey rsa:2048 -keyout key.pem -out cert.pem -days 365 -nodes # 从证书提取公钥 openssl x509 -in cert.pem -pubkey -noout > extracted_pubkey.pem # 验证公钥 openssl rsa -pubin -in extracted_pubkey.pem -text -noout ``` --- 通过上述方法,你可以从各类证书提取公钥,并根据需要转换格式。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值