OpenSSL使用S/MIME发送签名和加密邮件#
1. 通信双方的证书生成#
1.1 生成根节点证书#
openssl genrsa -out cakey.pem 2048
openssl req -utf8 -new -key cakey.pem -subj "/CN=abc.com" -out cacsr.pem
openssl x509 -req -in cacsr.pem -days 999 -signkey cakey.pem -out cacert.pem
1.2 生成alice的证书#
openssl genrsa -out alicekey.pem 2048
openssl req -utf8 -new -key cakey.pem -subj "/emailAddress=alice@163.com" -out alicecsr.pem
openssl x509 -req -in alicecsr.pem -days 999 -CA cacert.pem -CAKey cakey.pem -set_serial 01 -name "alice" -out alicecert.pem
openssl pkcs12 -export -in alicecert.pem -inkey alicekey.pem -certfile cacert.pem -out alice.p12
1.3 生成bob的证书#
openssl genrsa -out bobkey.pem 2048
openssl req -new -key bobkey.pem -subj "/emailAddress=bob@126.com" -out bobcsr.pem
openssl x509 -req -in bobcsr.pem -days 999 -CA cacert.pem -CAkey cakey.pem -set_serial 02 -name "bob" -out bobcert.pem
openssl pkcs12 -export -in bobcert.pem -inkey bobkey.pem -certfile cacert.pem -out bob.p12
2. 邮件签名#
openssl smime -sign -in /tmp/msg.txt -signer alicecert.pem -inkey alicekey.pem -nocerts -nodetach -text -out /tmp/alicesigned.eml
提醒: -nodetach 把信息原文也包含到base64块里面,而不是用mime格式的分隔符单独放置,比较容易保证信息不被邮件收发服务器重构,导致验证失败。 -nocerts 是一个可选选项,如果设置的话,alice的证书(公钥等)不会被包含到签名信息里面(base64块) -signer 在签发邮件的时候,指定发送人的证书位置,这里指定alice的证书
3. 签名验证#
openssl smime -verify -in /tmp/alicesigned.eml -certfile alicecert.pem -CAfile cacert.pem
注意: -signer 参数这个时候的意思:导出签发邮件的证书保存。所以要小心覆盖原有证书 -CAfile 设置信任的ca位置,否则验证不通过 -certfile 是一个可选选项,如果签名的时候指定了-nocerts,这里可以指定验证证书(alice),这样网络传输经济。
4. 邮件加密#
smime -encrypt -in /tmp/msg.txt -from alice@163.com -to bob@126.com -des3 -out /tmp/msg.eml bobcert.pem
5. 邮件解密#
openssl smime -decrypt -in /tmp/msg.eml -recip bobcert.pem -inkey bobkey.pem
6. 签名并加密#
openssl smime -sign -in msg.txt -signer alicecert.pem -inkey alicekey.pem -nocerts -nodetach -text | openssl smime -encrypt -des3 -from alice@163.com -to bob@126.com -subject HiBob bobcert.pem
To: bob@126.com
From: alice@163.com
Subject: HiBob
MIME-Version: 1.0
Content-Disposition: attachment; filename=”smime.p7m”
Content-Type: application/x-pkcs7-mime; smime-type=enveloped-data; name="smime.p7m"
Content-Transfer-Encoding: base64
MIIGKQYJKoZIhvcNAQcDoIIGGjCCBhYCAQAxggFmMIIBYgIBADBKMEUxCzAJBgNV
BAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5ldCBX
aWRnaXRzIFB0eSBMdGQCAQMwDQYJKoZIhvcNAQEBBQAEggEAdmR6L5KWIhmIFBwj
。。。。
7.解密并验证#
openssl smime -decrypt -in enc.eml -recip bobcert.pem -inkey bobkey.pem | openssl smime -verify -certfile alicecert.pem -CAfile cacert.pem
Content-Type: text/plain
Hello, World !
Verification successful
管道命令
openssl smime -sign -in msg.txt -signer alicecert.pem -inkey alicekey.pem -nocerts -nodetach -text | \
openssl smime -encrypt -des3 -from alice@163.com -to bob@126.com -subject HiBob bobcert.pem | \
openssl smime -decrypt -recip bobcert.pem -inkey bobkey.pem | \
openssl smime -verify -certfile alicecert.pem -CAfile cacert.pem