生成本地CA根證書(shū)、p12流程 算法為RSA ECC算法移步這里
安裝 OpenSSL:首先,確保你的系統(tǒng)上安裝了 OpenSSL 工具。如果尚未安裝,你可以通過(guò) Homebrew 或從 OpenSSL 官方網(wǎng)站下載并安裝。
創(chuàng)建根證書(shū)私鑰:使用 OpenSSL 生成一個(gè)根證書(shū)的私鑰文件。運(yùn)行以下命令生成一個(gè) 2048 位的 RSA 私鑰文件(root.key):
openssl genrsa -out root.key 2048
此命令將生成一個(gè)新的 RSA 私鑰文件,用于根證書(shū)的簽名和加密。
創(chuàng)建根證書(shū):使用根證書(shū)私鑰生成自簽名的根證書(shū)。運(yùn)行以下命令生成一個(gè)自簽名的根證書(shū)文件(root.crt):
openssl req -x509 -new -key root.key -out root.crt
在終端中執(zhí)行以下命令來(lái)生成私鑰:
生成密碼保護(hù)的私鑰
openssl genpkey -algorithm RSA -out private.pem -aes256
或者生成無(wú)密碼的私鑰
penssl genpkey -algorithm RSA -out private.pem
創(chuàng)建證書(shū)請(qǐng)求文件:對(duì)于每個(gè)需要頒發(fā)證書(shū)的實(shí)體(例如服務(wù)器或客戶端),你需要?jiǎng)?chuàng)建一個(gè)證書(shū)請(qǐng)求文件(CSR 文件)。運(yùn)行以下命令生成一個(gè)證書(shū)請(qǐng)求文件
openssl req -new -key private.pem -out certificate.csr
簽署證書(shū):使用根證書(shū)的私鑰簽署證書(shū)請(qǐng)求,生成證書(shū)文件(certificate.crt)。運(yùn)行以下命令生成簽署的證書(shū)文件:(下級(jí)證書(shū))
openssl x509 -req -in certificate.csr -CA root.crt -CAkey root.key -CAcreateserial -out certificate.crt
生成一個(gè)p12并設(shè)置密碼
openssl pkcs12 -export -in certificate.crt -inkey private.pem -out certificate.p12
下面是OC使用p12做簽名驗(yàn)簽的簡(jiǎn)單示例
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
NSData *p12Data = [NSData dataWithContentsOfFile:[[NSBundle mainBundle] pathForResource:@"certificate" ofType:@"p12"]];
NSDictionary *options = @{(__bridge id)kSecImportExportPassphrase: @"123456"};
CFArrayRef items = NULL;
OSStatus status = SecPKCS12Import((__bridge CFDataRef)p12Data, (__bridge CFDictionaryRef)options, &items);
if (status == errSecSuccess) {
CFDictionaryRef identityDict = CFArrayGetValueAtIndex(items, 0);
SecIdentityRef identity = (SecIdentityRef)CFDictionaryGetValue(identityDict, kSecImportItemIdentity);
SecCertificateRef certificate = NULL;
SecIdentityCopyCertificate(identity, &certificate);
// 獲取私鑰
SecKeyRef privateKey = NULL;
SecIdentityCopyPrivateKey(identity, &privateKey);
// 獲取公鑰
SecPolicyRef policy = SecPolicyCreateBasicX509();
SecTrustRef trust;
SecTrustCreateWithCertificates(certificate, policy, &trust);
SecTrustResultType trustResult;
SecTrustEvaluate(trust, &trustResult);
SecKeyRef publicKey = SecTrustCopyPublicKey(trust);
NSString *testBase64 = @"Cy4JAEFCQ0QjMTIzNA4uBwAAAAEBAAABCi4gAJjruIAtnUTW0IkHex7/gCKJUb+927IrBoD40CP+nZjdCS4uAHpoYW5nMyZKREpoSkRFd0pFcGpaVGc0V0ZsSE9HZHpkRWcyZWtGeVFXRnZMbVUNLggAAAABAAAAAQAMLkEABHTznz0bpFsvbiYz7gwwVwZEBU2hcRHEwKNDdyGCfKc1IktkBlDqUogUnfqJPUrnkKQCDaEU91zB2aQrBqoAvUo=";
NSData *signData = [[NSData alloc] initWithBase64EncodedString:testBase64 options:0];
SecKeyAlgorithm algorithm = kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA256;
CFErrorRef error = NULL;
NSData *signature = (NSData *)CFBridgingRelease(SecKeyCreateSignature(privateKey, algorithm, (__bridge CFDataRef)signData, &error));
if (error == NULL) {
// 加簽成功,使用 signature 進(jìn)行后續(xù)操作
SecKeyAlgorithm algorithm = kSecKeyAlgorithmRSASignatureMessagePKCS1v15SHA256;
BOOL result = SecKeyVerifySignature(publicKey, algorithm, (__bridge CFDataRef)signData, (__bridge CFDataRef)signature, NULL);
if (result) {
// 驗(yàn)簽成功
NSLog(@"使用p12加簽、驗(yàn)簽成功");
} else {
// 驗(yàn)簽失敗
}
} else {
// 加簽失敗,處理錯(cuò)誤
}
// 釋放內(nèi)存
if (identity) CFRelease(identity);
if (certificate) CFRelease(certificate);
if (privateKey) CFRelease(privateKey);
if (publicKey) CFRelease(publicKey);
}
});