2.2. 生成 EC CA 根证书
该文章根据 CC-BY-4.0 协议发表,转载请遵循该协议。
本文地址:https://fenying.net/book/pki-tutorials/2.2.generate-ec-ca-root/
本章节介绍如何使用 OpenSSL 生成 EC CA 根证书。
初始化工作目录
假定 EC CA 的工作目录在 /data/ca/EC/Root
,那么执行如下脚本:
1export MY_CA_WORKDIR=/data/ca
2mkdir -p $MY_CA_WORKDIR
3
4MY_CA_ROOT_DIR=$MY_CA_WORKDIR/EC/Root
5
6mkdir -p $MY_CA_ROOT_DIR
7
8cd $MY_CA_ROOT_DIR
9
10MY_CA_RAND_FILE=$MY_CA_ROOT_DIR/.rand
11
12mkdir -p issued_certs crl
13touch index.txt
14
15openssl rand -out $MY_CA_RAND_FILE 65535
16md5sum $MY_CA_RAND_FILE | grep -Po '^\w+' > serial
17
18openssl rand -out $MY_CA_RAND_FILE 1048576
生成 CA 根证书的 EC 私钥
这里有两类密钥选择,一是 NIST P-*
+ ECSDA
,比如 secp521r1
:
1MY_CA_ROOT_KEY_PATH=$MY_CA_ROOT_DIR/key.pem
2
3# 生成 CA 根证书的 EC 私钥
4openssl ecparam -rand $MY_CA_RAND_FILE -genkey -name prime256v1 -noout -out $MY_CA_ROOT_KEY_PATH
5
6# 【可选】为该私钥增加 AES 加密保护。
7openssl ec -aes-256-cfb -in $MY_CA_ROOT_KEY_PATH -out $MY_CA_ROOT_KEY_PATH
如果选择 curve25519
,则使用如下命令:
1MY_CA_ROOT_KEY_PATH=$MY_CA_ROOT_DIR/key.pem
2
3# 生成 CA 根证书的 EC 私钥
4openssl genpkey -algorithm ed25519 -out $MY_CA_ROOT_KEY_PATH
5
6# 【可选】为该私钥增加 AES 加密保护。
7cp $MY_CA_ROOT_KEY_PATH $MY_CA_ROOT_KEY_PATH.raw
8openssl pkcs8 \
9 -topk8 \
10 -inform PEM \
11 -v2 aes256 \
12 -in $MY_CA_ROOT_KEY_PATH.raw \
13 -out $MY_CA_ROOT_KEY_PATH
14rm -f $MY_CA_ROOT_KEY_PATH.raw
生成证书签名申请表文件
1EC_CA_ROOT_REQ_PATH=$MY_CA_ROOT_DIR/ca.csr.cnf
2
3cat > $EC_CA_ROOT_REQ_PATH << EOL
4[ req ]
5
6default_bits = 4096
7distinguished_name = req_distinguished_name
8string_mask = utf8only
9prompt = no
10
11# SHA-1 is deprecated, so use SHA-2 instead.
12default_md = sha384
13
14# Extension to add when the -x509 option is used.
15x509_extensions = v3_ca
16req_extensions = v3_ca
17
18[ req_distinguished_name ]
19# See <https://en.wikipedia.org/wiki/Certificate_signing_request>.
20countryName = CN
210.organizationName = Demo ORG
22organizationalUnitName = www.demo.org
23commonName = Demo CA EC Root
24
25[ v3_ca ]
26
27subjectKeyIdentifier = hash
28authorityKeyIdentifier = keyid:always,issuer:always
29basicConstraints = critical, CA:true
30keyUsage = critical, digitalSignature, cRLSign, keyCertSign
31EOL
签发自签名 CA 根证书
1MY_CA_ROOT_CERT_PATH=$MY_CA_ROOT_DIR/ca.pem
2
3# 生成一个有效期为 30 年的自签名 CA 根证书
4openssl req -config $EC_CA_ROOT_REQ_PATH \
5 -new \
6 -x509 \
7 -days 10950 \
8 -sha256 \
9 -extensions v3_ca \
10 -key $MY_CA_ROOT_KEY_PATH \
11 -out $MY_CA_ROOT_CERT_PATH
如果使用
Ed25519
,则此处的-sha256
没有任何意义,因为Ed25519
一定是使用SHA-512(SHA2)
作为哈希算法的。
然后可以通过如下命令查看生成证书的详细信息。
1openssl x509 -noout -text -in $MY_CA_ROOT_CERT_PATH
通过如下命令验证自签名 CA 证书是否可以自验证。
1openssl verify -CAfile $MY_CA_ROOT_CERT_PATH $MY_CA_ROOT_CERT_PATH
配置 CA
最后对 CA 进行配置,以用于签发其他证书。
1EC_CA_ROOT_CONF_PATH=$MY_CA_ROOT_DIR/ca.cnf
2
3cat > $EC_CA_ROOT_CONF_PATH << EOL
4[ ca ]
5default_ca = CA_default
6
7[ CA_default ]
8# Directory and file locations.
9dir = $MY_CA_ROOT_DIR
10certs = \$dir/certs
11crl_dir = \$dir/crl
12new_certs_dir = \$dir/issued_certs
13database = \$dir/index.txt
14serial = \$dir/serial
15RANDFILE = \$dir/.rand
16
17# The root key and root certificate.
18private_key = \$dir/key.pem
19certificate = \$dir/ca.pem
20
21# For certificate revocation lists.
22crlnumber = \$dir/crlnumber
23crl = \$dir/crl/ca.crl.pem
24crl_extensions = crl_ext
25default_crl_days = 30
26
27# SHA-1 is deprecated, so use SHA-2 instead.
28default_md = sha256
29
30name_opt = ca_default
31cert_opt = ca_default
32default_days = 375
33preserve = no
34policy = policy_strict
35copy_extensions = copy
36
37[ policy_strict ]
38# The root CA should only sign intermediate certificates that match.
39countryName = match
40stateOrProvinceName = optional
41organizationName = match
42organizationalUnitName = optional
43commonName = supplied
44emailAddress = optional
45
46[ policy_loose ]
47# Allow the intermediate CA to sign a more diverse range of certificates.
48countryName = optional
49stateOrProvinceName = optional
50localityName = optional
51organizationName = optional
52organizationalUnitName = optional
53commonName = supplied
54emailAddress = optional
55
56[ req ]
57default_bits = 4096
58distinguished_name = req_distinguished_name
59string_mask = utf8only
60prompt = no
61
62# SHA-1 is deprecated, so use SHA-2 instead.
63default_md = sha384
64
65# Extension to add when the -x509 option is used.
66x509_extensions = v3_ca
67
68[ req_distinguished_name ]
69# See <https://en.wikipedia.org/wiki/Certificate_signing_request>.
70countryName = CN
710.organizationName = Demo ORG
72organizationalUnitName = www.demo.org
73commonName = Demo CA EC Root
74
75[ v3_ca ]
76subjectKeyIdentifier = hash
77authorityKeyIdentifier = keyid:always,issuer:always
78basicConstraints = critical, CA:true
79keyUsage = critical, digitalSignature, cRLSign, keyCertSign
80
81[ v3_intermediate_ca ]
82keyUsage = critical, digitalSignature, cRLSign, keyCertSign
83extendedKeyUsage = critical, clientAuth, serverAuth
84basicConstraints = critical, CA:true, pathlen:0
85subjectKeyIdentifier = hash
86authorityKeyIdentifier = keyid:always,issuer:always
87# authorityInfoAccess = caIssuers;URI:http://demo.org/ca.html
88# crlDistributionPoints = URI:http://demo.org/ca.crl
89# certificatePolicies = 2.23.140.1.2.1,@policy_issuer_info
90
91# [ policy_issuer_info ]
92# policyIdentifier = 1.3.6.1.4.1.44947.1.2.3.4.5.6.7.8
93
94[ crl_ext ]
95authorityKeyIdentifier=keyid:always
96
97[ ocsp ]
98basicConstraints = CA:FALSE
99subjectKeyIdentifier = hash
100authorityKeyIdentifier = keyid:always,issuer:always
101keyUsage = critical, digitalSignature
102extendedKeyUsage = critical, OCSPSigning
103EOL
注意,此时的 CA 不允许重复对同一个 commonName 签发证书,需要改成可以对同一个主体重复颁发证书:
1echo 'unique_subject = no' > $MY_CA_ROOT_DIR/index.txt.attr
至此,EC CA 根证书已经生成完毕。
comments powered by Disqus