我们可以为我们的程序进行数字签名,这样就可以证明该程序的作者是可信的.
首先为了签名程序,我们需要先创建一个证书.证书是由证书颁发机构(CA)颁发的,CA 是受信任的第三方机构,它可以为我们颁发证书.当然我们也可以自己创建证书.接下来简单介绍下如何利用 OpenSSL 工具创建证书.
创建证书
下载 openssl 安装包并安装,推荐下载最新 64 位版本.
打开命令行,输入 openssl,如果提示 Openssl 不是内部或外部命令,需要设置一下环境变量,把 Openssl 的安装目录加入到 path 环境变量.
另外新建一个环境变量,如以下所示,名称为:OPENSSL_CONF,指向你安装目录的 openssl.cfg 文件,现在输入 openssl 应该没有问题了.
新建一个文件夹用于放置密钥,在该目录打开命令行.
1.申请一个私钥,在命令行中输入:
openssl genrsa -out private.key 2048
申请一个 2048 位的 RSA 加密私钥.目录下将多了一个名为 private.key 的文件.
2.申请一个 10 年有效期的公钥
openssl req -new -x509 -key private.key -days 3650 -out public.crt
其中 -key private.key 是指定这个公钥的配对私钥,就是第一步申请的私钥.x509 是 X.509 公钥格式标准.
接下来会提示你输入一些信息,用于颁发机构的信息展示,如公司,所在国家,城市等
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) [AU]:CN
State or Province Name (full name) [Some-State]:ShangHai
Locality Name (eg, city) []:ShangHai
Organization Name (eg, company) [Internet Widgits Pty Ltd]:XXXXX
Organizational Unit Name (eg, section) []:XXXXX-XXXXX
Common Name (e.g. server FQDN or YOUR name) []:XXXXX
Email Address []:XXXXX@outlook.com
如果不想每次都输入这些信息,可以使用“-config 配置文件目录”的方式指定配置文件,安装后 Openssl 后,有一个名为 openssl.cnf 的默认的配置文件在安装目录 bin/cnf 目录中.编辑该文件,找到 req_distinguished_name
[ req_distinguished_name ]
countryName = Country Name (2 letter code)
countryName_default = CN
countryName_min = 2
countryName_max = 2
stateOrProvinceName = State or Province Name (full name)
stateOrProvinceName_default = Some-State
localityName = Locality Name (eg, city)
0.organizationName = Organization Name (eg, company)
0.organizationName_default = Internet Widgits Pty Ltd
# we can do this but it is not needed normally :-)
#1.organizationName = Second Organization Name (eg, company)
#1.organizationName_default = World Wide Web Pty Ltd
organizationalUnitName = Organizational Unit Name (eg, section)
#organizationalUnitName_default =
commonName = Common Name (e.g. server FQDN or YOUR name)
commonName_max = 64
emailAddress = Email Address
emailAddress_max = 64
这里可以指定这些参数的默认值,如指定国家默认值为 CN.把 countryName_default 改成 CN 就行了.申请完公钥后,目录下将多了一个 public.crt 的文件.
3.公钥及私钥的提取加密.由于传播安全方面的考虑,需要将公钥及私钥加密,微软支持 PCK12(公钥加密技术 12 号标准:Public Key Cryptography Standards #12),PCK12 将公钥和私钥合在一个 PFX 后缀文件并用密码保护,如要提取公钥和私钥需要密码确认.另一种觉的公钥私钥提取加密方式是 JKS(JAVA Key Store)用于 JAVA 环境的公钥和私钥提取.这两种格式可以相互转换.
在命令行中输入
openssl pkcs12 -export -in public.crt -inkey private.key -out sign.pfx
输入密码和确认密码后,当前目录会多出一个文件:sign.pfx.这就是我们要用的密钥证书了.
签名程序
程序的签名将使用到 Visual Studio 的签名工具 signtool.exe,它位于 Windows SDK 目录的 bin 目录下.
打开命令行,输入 signtool,如果提示 signtool 不是内部或外部命令,需要设置一下环境变量,把 signtool 的安装目录加入到 path 环境变量.
签名程序的命令如下:
signtool sign /f "sign.pfx" /p "密码" /tr "http://timestamp.digicert.com" /td SHA256 /fd SHA256 "程序名.exe"
其中 /f "sign.pfx" 是指定签名证书的路径, /p "密码" 是指定签名证书的密码, /tr "http://timestamp.digicert.com" 是指定时间戳服务器地址, /td SHA256 是指定摘要算法, /fd SHA256 是指定文件摘要算法.
最后 "程序名.exe" 是要签名的程序名.
签名完成后,我们就可以在程序的属性中查看数字签名选项卡的签名信息了.
验证签名
验证签名的命令如下:
signtool verify "程序名.exe"
其中 "程序名.exe" 是要验证签名的程序名.
由于我这里是自签发的证书,所以不可信还没有验证成功过 😂,大佬们可以试试花钱的证书哈!
如果验证失败,输出结果如下:
Index Algorithm Timestamp
========================================
SignTool Error: A certificate chain processed, but terminated in a root
certificate which is not trusted by the trust provider.
Number of errors: 1
参考链接:
SignTool.exe(签名工具)