正确使用 OpenSSL 自签发代码|邮件|域名|IP 证书(附免费可信任 IP 证书申请)

小助手读文章 00:00 / 00:00

温馨提示:
本文所述内容具有依赖性,可能因软硬条件不同而与预期有所差异,故请以实际为准,仅供参考。

近期有需求签发 IP 证书,纵观全网,几乎千篇一律都是抄来抄去的,如果能用就算了,偏偏还是错的,真不晓得为什么转发都不能去验证一下。

先看看网上搜到的,基本上是说在 commonName 填入 IP 地址,或者添加 [v3_req] 字段并写入 IP 地址来实现,按此方法也确实可以成功签发证书,直接打开证书也不会报错,但浏览器却会报如下错误:

NET::ERR_CERT_COMMON_NAME_INVALID
此服务器无法证实它就是 x.x.x.x - 它的安全证书没有指定主题备用名称。
这可能是因为某项配置有误或某个攻击者拦截了您的连接。

可见此方式是有缺陷的,下面说说我是如何签发 IP 证书。

依赖

利用 OpenSSL 签发自然是需要 OpenSSL 软件及库,一般情况下 CentOS、Ubuntu 等系统均已内置,可执行 openssl 确认,如果出现 oepnssl: command not found 说明没有内置,需要手动安装,以 CentOS 为例,安装命令如下:

# yum install openssl openssl-devel -y

创建证书保存目录和记录文件,方便后续查找,比如放在用户(root)目录的 demoCA 下:

# cd ~
# mkdir demoCA && cd demoCA
# mkdir private newcerts
# touch index.txt
# echo '01' >serial

修改 OpenSSL 配置文件,使之识别 demoCA 目录

# vim /etc/pki/tls/openssl.cnf
......
[ CA_default ]
#dir            = /etc/pki/CA           # Where everything is kept
dir             = /root/demoCA
......

openssl.cnf 文件中还有很多实用的配置,比如生成证书请求文件(csr)用到的 countryName_default(默认国家)、stateOrProvinceName_default(默认省份)、localityName_default(默认城市)等等,在文件中设置好后续自签证书可以省去输入的步骤,视需求修改。

自建 CA

生成根密钥

# cd private/
# openssl genrsa -out cakey.pem 2048
Generating RSA private key, 2048 bit long modulus
...................................................+++
...............................................................................+++
e is 65537 (0x10001)

生成根 CA 证书

# openssl req -new -x509 -days 3650 -key cakey.pem -out cacert.pem
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [US]:
State or Province Name (full name) [California]:
Locality Name (eg, city) [Mountain View]:
Organization Name (eg, company) [VirCloud, LLC.]:
Organizational Unit Name (eg, section) [Technical Support Dept.]:
Common Name (eg, your name or your server's hostname) []:VirCloud, LLC. Global Root CA
# cd ../ && mv private/cacert.pem ./

最终 cakey.pem 应存放于 demoCA/private/ 目录下,cacert.pem 存放于 demoCA/ 目录下,需确认一下。

添加信任

由于证书是自建的,所以要把根证书添加到受信任的根证书颁发机构,后续利用此 CA 签发的证书才会受信任,否则仍然会提示不可信。

# cat cacert.pem >> /etc/pki/tls/certs/ca-bundle.crt     //centos
# mv cacert.pem /usr/local/share/ca-certificates/cacert.pem && update-ca-certificates
   //ubuntu

Firefox 火狐浏览器是自带证书系统的,通过上述导入安装根证书无法解决报错,所以应该再将证书其导入到 Firefox 浏览器(如有安装)中,将证书拖到地址栏回车确定按提示操作,或者在 选项 - 隐私与安全 - 查看证书 - 证书机构 - 导入,或者在浏览器报错时添加例外即可。

颁发证书

创建 RSA 请求

# cd ..
# openssl genrsa -out 127.0.0.1.key 2048
Generating RSA private key, 2048 bit long modulus
...................................................................................................................................................................+++
................+++
e is 65537 (0x10001)
# openssl req -new -key 127.0.0.1.key -out 127.0.0.1.csr
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [US]:
State or Province Name (full name) [California]:
Locality Name (eg, city) [Mountain View]:
Organization Name (eg, company) [VirCloud, LLC.]:
Organizational Unit Name (eg, section) [Technical Support Dept.]:
Common Name (eg, your name or your server's hostname) []:local.domain       
Email Address [[email protected]]:

Please enter the following 'extra' attributes
to be sent with your certificate request
A challenge password []:
An optional company name []:

创建 ECC 请求

虽然相较 RSA 证书 ECC 证书计算速度快且支持 PFS,但需要注意的是,目前还是有很多服务不支持 ECC 证书,比如群晖 DSM。

# cd ..
# openssl ecparam -name prime256v1 -out ecparam.pem
# openssl req -new -SHA256 -newkey ec:ecparam.pem -nodes -keyout 127.0.0.1.key -out 127.0.0.1.csr -subj "/C=US/ST=California/L=Mountain View/O=VirCloud, LLC./OU=Technical Support Dept./CN=local.domain"
Generating a 256 bit EC private key
writing new private key to '127.0.0.1.key'
-----

附加用途

# vim 127.0.0.1.ext
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
extendedKeyUsage = serverAuth, clientAuth
subjectAltName=@SubjectAlternativeName

[ SubjectAlternativeName ]
IP.1 = 127.0.0.1
DNS.1 = local.domain

与签发域名证书的区别(也是与其他教程的区别)就在于此步骤,在 不改 openssl.cnf 的情况 下(方便签发不同证书),如果是要签发 IP 证书必须参照上述格式执行此步骤。

如果要通过 修改 openssl.cnf 来签发证书,除将上述配置直接改到 openssl.cnf 相应位置外,必须将配置中的 basicConstraints = CA:FLASE 改为 basicConstraints = CA:TRUE,否则修改不生效,这是其他教程没有提到的。

extendedKeyUsage 可以指定证书目的,即用途,一般有:

serverAuth:保证远程计算机的身份
clientAuth:向远程计算机证明你的身份
codeSigning:确保软件来自软件发布者,保护软件在发行后不被更改
emailProtection:保护电子邮件消息
timeStamping:允许用当前时间签名数据
ikeIntermediate:允许 Internet 上的安全通信(OpenVPN)

如果不指定,则默认为 所有应用程序策略

签发证书

# openssl ca -in 127.0.0.1.csr -extfile 127.0.0.1.ext -days 365 -out 127.0.0.1.crt
Using configuration from /etc/pki/tls/openssl.cnf
Check that the request matches the signature
Signature ok
Certificate Details:
        Serial Number: 1 (0x1)
        Validity
            Not Before: Sep 26 05:16:18 2018 GMT
            Not After : Sep 23 05:16:18 2028 GMT
        Subject:
            countryName               = US
            stateOrProvinceName       = California
            organizationName          = VirCloud, LLC.
            organizationalUnitName    = Technical Support Dept.
            commonName                = local.domain
            emailAddress              = [email protected]
        X509v3 extensions:
            X509v3 Subject Alternative Name: 
                IP Address:127.0.0.1
Certificate is to be certified until Sep 23 05:16:18 2028 GMT (365 days)
Sign the certificate? [y/n]:y

1 out of 1 certificate requests certified, commit? [y/n]y
Write out database with 1 new entries
Data Base Updated

使用 openssl.cnf 配置来签发(即不适用附加用途),则命令是:

# openssl ca -in 127.0.0.1.csr -extensions v3_req -days 365 -out 127.0.0.1.crt

证书签发后即可更根据需要给网站或 APP 或代码使用了。

问题排查

  1. 问题:TXT_DB error number 2

解决:原因是已经生成了同名证书,将 common name 设置成不同,或修改 demoCA 下的 index.txt.attr,将 unique_subject = yes 改为 unique_subject = no

吊销证书

OpenSSL 还支持 CRL 吊销证书和吊销列表,主要是为了解决出现在远程桌面 RDP 中的无法对证书执行吊销检查错误。

附加用途

同样使用 v3 拓展属性实现:

# vim 127.0.0.1.ext
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
extendedKeyUsage = serverAuth, clientAuth
subjectAltName=@SubjectAlternativeName
#证书吊销列表
crlDistributionPoints=@crl_section

[ SubjectAlternativeName ]
IP.1 = 127.0.0.1
DNS.1 = local.domain

[ crl_section ]
#证书吊销列表地址
URI.0 = https://local.domain/cer.crl

吊销证书

# echo '00' >crlnumber
# openssl ca -revoke 127.0.0.1.crt     //吊销 127.0.0.1.crt 这张证书
Using configuration from /etc/pki/tls/openssl.cnf
Revoking Certificate 01.
Data Base Updated

吊销列表

先生成吊销列表:

# openssl ca -gencrl -out cer.crl
Using configuration from /etc/pki/tls/openssl.cnf

然后将生成的 cer.crl 放到前面附加用途的证书吊销列表地址目录中。

免费 IP 证书

20230310 更新:
HiCA,已不支持签发免费 IP 证书,仅支持半年免费泛域名。

20221018 更新:
推荐使用 HiCA,支持签发 IP、支持泛域名。

20210222 更新:
TrustOcean Encryption365 在宝塔面板上,以插件形式提供免费 SSL,支持签发 IP。

20200522 更新:
已不再提供。

环洋诚信™ 提供有效期 90 天的免费证书,支持泛域名、IP、单域名或三者组合,申请地址:TrustOcean Encryption365 SSL,看页面提示操作即可,图文申请教程见《获取免费的泛域名证书|IP 证书|多域名证书|单域名证书》。


参考文章:
1、《OPENSSL 制作 Ikev2证书
2、《証明書に x509v3 拡張属性を追加する
3、《附录 A. SSL/TLS 证书配置
4、《使用 OpenSSL为WindowsServer远程桌面(RDP)创建自签名证书 (Self-signed SSL certificate
5、《开始使用 ECC 证书


ArmxMod for Typecho
个性化、自适应、功能强大的响应式主题

推广

 继续浏览关于 SSL代码证书IP自签 的文章

 本文最后更新于 2023/03/10 09:48:46,可能因经年累月而与现状有所差异

 引用转载请注明: VirCloud's Blog > 运维 > 正确使用 OpenSSL 自签发代码|邮件|域名|IP 证书(附免费可信任 IP 证书申请)

精选评论

  1. 生成符合chrome要求的自签名HTTPS证书_Johngo学长
  2. Timochan
    Timochan 回复

    Mac OS X 10_14_5Chrome 101.0.4951.54来自 火星 的大神

    大佬可以试试 HiCA ,可以签 IP 证书 https://www1.hi.cn/

    1. 欧文斯

      是的,不过目前为止我也只签成功 IP 证书 icon_arrow.gif

      1. Timochan
        Timochan 回复

        Mac OS X 10_14_5Chrome 101.0.4951.54来自 火星 的大神

        诶嘿,这个泛域名是 180 天的,不过如果想签 ECC ,就进入收费流程了

  3. 生成符合chrome要求的自签名HTTPS证书_Johngo学长
  4. 生成符合chrome要求的自签名HTTPS证书_Johngo学长
  5. 生成符合chrome要求的自签名HTTPS证书_Johngo学长
  6. 生成符合chrome要求的自签名HTTPS证书 | Coding栈