折腾一下午不如半夜 02:23 的随手一敲。
重要的几点是关于支持的椭圆曲线,以及打包 PKCS#12 格式的密钥与证书时必须使用 OpenSSL 1。所以在这里我们以 OpenSSL 1.1 举例,当然关于命令的使用两者都是差不多的。
1 2 3 4
| $ export PATH="/opt/homebrew/opt/[email protected]/bin:$PATH"
$ openssl version OpenSSL 1.1.1u 30 May 2023
|
生成 CA 证书与客户端证书
创建一个 ca.cnf
,内容如下。关于各配置项的意义,见 man x509v3_config
。
ca.cnf1 2 3 4 5
| basicConstraints = critical, CA:TRUE, pathlen:3 subjectKeyIdentifier = hash authorityKeyIdentifier = keyid, issuer:always keyUsage = digitalSignature keyUsage = critical, keyCertSign
|
然后生成 CA 证书。
对于 RSA,最大 8192,最小 512,在这之间的任何 bit 数都是可以的(奇数自动调整),你甚至可以生成一个 2984 bits 的 key。
对于 ECDSA,目前 iOS 与 macOS 仅支持 4 种类型的椭圆曲线:secp192r1
,secp256r1
,secp384r1
和 secp521r1
。
CA 证书和客户端证书都需要满足这些条件。
1 2 3 4 5 6 7 8
| openssl genpkey -algorithm RSA -out ca.key \ -pkeyopt rsa_keygen_bits:2048
openssl req -new -key ca.key -out ca.csr \ -subj "/C=CN/O=45gfg9/CN=Client Cert CA"
openssl x509 -req -days 1460 -extfile ca.cnf \ -signkey ca.key -in ca.csr -out ca.pem
|
genrsa
子命令已经被弃用(虽然很方便),genpkey
是新的用于统一生成所有类型的私钥的子命令。关于 genpkey
的用法,以及 -pkeyopt
选项,可以查询 man openssl-genpkey
。
-subj
可以按需求设置,FQDN 不需要设置为域名(甚至可以不设置)。
对于客户端证书,需要一个类似如下的 client.cnf
:
client.cnf1 2 3 4 5
| basicConstraints = critical, CA:FALSE subjectKeyIdentifier = hash authorityKeyIdentifier = keyid, issuer:always keyUsage = digitalSignature, keyEncipherment, dataEncipherment, keyAgreement extendedKeyUsage = clientAuth
|
keyUsage
那一块最少需要哪些信息我也没搞懂,但是这样写肯定能用喵 (∠·ω< )⌒★
extendedKeyUsage = clientAuth
是重要的。如果没有,这个证书就无法用于客户端认证。
然后 CA 给客户端 CSR 签发证书就可以了。
1 2 3 4 5 6 7 8 9
| openssl genpkey -algorithm EC -out client.key \ -pkeyopt ec_paramgen_curve:prime256v1
openssl req -new -key client.key -out client.csr \ -subj "/C=CN/O=45gfg9/OU=Devices/CN=45gfg9's iPhone"
openssl x509 -req -days 1460 -extfile client.cnf \ -CA ca.pem -CAkey ca.key \ -in client.csr -out client.pem
|
打包 PKCS#12 并安装至客户端
请再次确保正在使用 OpenSSL 1!OpenSSL 3 所生成的 PKCS#12 文件无法导入 Apple 设备!
1 2 3
| openssl pkcs12 -export -out client.p12 \ -in client.pem -inkey client.key \ -chain -CAfile ca.pem
|
这样就得到了一个 PKCS#12 文件。Export password 可以随意设置,但不能为空,否则无法导入 iOS / iPadOS。
macOS
可以直接打开 client.p12
文件导入哦。CA 证书 ca.pem
也需要导入,密码就是刚才输入的 Export password。
或者,如果你更喜欢命令行的话:
1 2 3
| $ security import client.p12 1 identity imported. 1 certificate imported.
|
最后的结果应该像这样。
iOS / iPadOS
client.p12
和 ca.pem
都需要传输到设备上(AirDrop / iCloud 云盘 / 本地起个服务器通过 http 下载)。虽然 CA 证书已经打包进 client.p12
文件了但 iOS 似乎不能处理这种情况的说。
按照安装配置描述文件的步骤走就可以了。密码也是刚才的 Export password。
完成!
服务器的配置就不写了,在网上很多地方都可以找到(笑)
现在访问新鲜配置的服务器!如果一切顺利的话就会有这样的弹窗。大功告成!
curl
也可以哦!
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| $ curl -I https://45gfg9-kali.local HTTP/1.1 400 Bad Request Server: nginx/1.22.1 Date: Fri, 21 Jul 2023 15:57:23 GMT Content-Type: text/html Content-Length: 237 Connection: close
$ curl -I https://45gfg9-kali.local -E client.pem --key client.key HTTP/1.1 200 OK Server: nginx/1.22.1 Date: Fri, 21 Jul 2023 15:57:32 GMT Content-Type: text/html; charset=UTF-8 Connection: keep-alive
|
后记
这么简单的东西折腾了好几天(瘫)
只用调库不用学数学的感觉真好
为什么 0721 日的我在做这种事啊(望天)