openssl加密入门资料整理

最近在搞grpc ssl双向验证加密传输,刚好把最近网上搜索的资料与个人理解整理一下。

一、背景介绍

使用HTTP(超文本传输)协议访问互联网上的数据是没有经过加密的。也就是说,任何人都可以通过适当的工具拦截或者监听到在网络上传输的数据流。但是有时候,我们需要在网络上传输一些安全性或者私秘性的数据,譬如:包含信用卡及商品信息的电子订单。这个时候,如果仍然使用HTTP协议,势必会面临非常大的风险!相信没有人能接受自己的信用卡号在互联网上裸奔。

HTTPS(超文本传输安全)协议无疑可以有效的解决这一问题。所谓HTTPS,其实就是HTTP和SSL/TLS的组合,用以提供加密通讯及对网络服务器的身份鉴定。HTTPS的主要思想是在不安全的网络上创建一安全信道,防止黑客的窃听和攻击。

SSL是Secure Sockets Layer(安全套接层协议)的缩写,可以在Internet上提供秘密性传输。
TLS是传输层安全协议 Transport Layer Security的缩写。
TLS简单看成SSL的升级版。
详细差异见
SSL与TLS的区别以及介绍_知识库_博客园

二、常见术语

1.CA
CA(Certification Authority)证书颁发机构。

2.KEY
通常指私钥。

3.CSR
是Certificate Signing Request的缩写,即证书签名请求,这不是证书,证书请求文件包含可以公钥和一些身份信息。可以简单理解成公钥,生成证书时要把这个提交给权威的证书颁发机构。

4.CRT
certificate的缩写,即证书。

5.X.509
是一种证书格式.对X.509证书来说,认证者总是CA或由CA指定的人,一份X.509证书是一些标准字段的集合,这些字段包含有关用户或设备及其相应公钥的信息。
X.509的证书文件,一般以.crt结尾。
openssl 当使用x509选项的时候,说明是要生成自签名证书。
X.509证书包含三个文件:key,csr,crt

key是服务器上的私钥文件,用于对发送给客户端数据的加密,以及对从客户端接收到数据的解密

csr是证书签名请求文件,用于提交给证书颁发机构(CA)对证书签名。

crt是由证书颁发机构(CA)签名后的证书,或者是开发者自签名的证书,包含证书持有人的信息,持有人的公钥,以及签署者的签名等信息

备注:在密码学中,X.509是一个标准,规范了公开秘钥认证、证书吊销列表、授权凭证、凭证路径验证算法等。

6.对称加密
使用相同的密码进行加密和解密。
缺点,安全性得不到保证。
常见的对称加密算法:DES,3DES,AES,Blowfish,Twofish,IDEA,RC6,CAST5 等。

7.非对称加密:
使用两组不同的密钥,密钥是成对出现,“私钥-公钥”,一个用于加密,一个用于解密。不同密码能够解密成功的原理是,利用数学上的一个素数积求因子。

8.加密与解密/签名与验证签名
一把钥匙一把锁,并且加密可以使用公钥也可以使用私钥。
公钥加密数据,然后私钥解密的情况被称为加密解密,私钥加密数据,公钥解密一般被称为签名和验证签名.
常见的非对称加密有 RSA、ESA、ECC 等。

公钥:公开给所有人。不能通过公钥反推出私钥;public key
私钥:自己留存,不公开。有且只有一个对应的私钥;secret key
特点:通过私钥加密的密文只能通过公钥能解密,通过公钥加密的密文也只能通过私钥能解密。
缺点:但由于算法强度比对称加密复杂,加解密的速度比对称加解密的速度要慢。

目前使用的是RSA加密算法,RSA可以用于加密/解密,也可以签名/验证签名。

三、加密通讯流程

简单的加密通讯流程
服务端公钥或私钥加密或签名数据发送给客户端;
客户端私钥或公钥解密或者验证签名服务端数据。

身份验证和密钥协商是TLS的基础功能,要求的前提是合法的服务器掌握着对应的私钥,但无法确保服务器身份的合法性,因为公钥并不包含服务器的信息,存在安全隐患:

  1. 中间人攻击:
    (1)客户端C和服务器S进行通信,中间节点M截获了二者的通信;
    (2)节点M自己计算产生一对公钥pub_M和私钥pri_M;
    (3)C向S请求公钥时,M把自己的公钥pub_M发给了C;
    (4)C使用公钥 pub_M加密的数据能够被M解密,因为M掌握对应的私钥pri_M,而 C无法根据公钥信息判断服务器的身份,从而 C和 M之间建立了"可信"加密连接;
    (5)中间节点M和服务器S之间再建立合法的连接,因此 C和 S之间通信被M完全掌握,M可以进行信息的窃听、篡改等操作。

  2. 信息抵赖
     服务器也可以对自己的发出的信息进行否认,不承认相关信息是自己发出。


使用gpg和openssl加密公钥进行安全数据通讯的场景。可是,网络中总是有不怀好意的角色存在,别以为你以公钥加密了就是安全的,有没有想过,你得到的这个公钥是不是真正要跟你通讯的服务器公钥呢?万一被伪造了?那将会如下图,黑客能打开加密的文件,而真正的ServerB却无法解开密文。


所以,就如现实生活中,大家都要确认某样东西的真实性的时候,找第三方权威机构,把各自己的信息交回权威机构进行验证后,再由权威机构公布各自需要的信息。

如下图,CA证书机构就是用来做这事的。


既然有了第三方的权威机构颁发的证书,那么通讯的过程也需要加密保护以便防止过程被窃取篡改。
SSL/TLS 握手是为了安全地协商出一份对称加密的秘钥。

想要深入理解可参考该博客。
安全与加密-使用gpg和openssl实现加密与解密-金色之谜-51CTO博客

四、CA证书

CA(Certification Authority)证书颁发机构。

CA签发证书的流程

  1. 服务方 S 向第三方机构CA提交公钥、组织信息、个人信息(域名)等信息并申请认证;

  2. CA 通过线上、线下等多种手段验证申请者提供信息的真实性,如组织是否存在、企业是否合法,是否拥有域名的所有权等;

  3. 如信息审核通过,CA 会向申请者签发认证文件-证书。
    证书包含以下信息:
    申请者公钥、申请者的组织信息和个人信息、签发机构 CA 的信息、有效时间、证书序列号等信息的明文,同时包含一个签名;

    签名的产生算法:首先,使用散列函数计算公开的明文信息的信息摘要,然后,采用 CA 的私钥对信息摘要进行加密,密文即签名;

  4. 客户端 C 向服务器 S 发出请求时,S 返回证书文件;

  5. 客户端 C 读取证书中的相关的明文信息,采用相同的散列函数计算得到信息摘要,然后,利用对应 CA 的公钥解密签名数据,对比证书的信息摘要,如果一致,则可以确认证书的合法性,即公钥合法;

    证书实际是由证书签证机关(CA)签发的对用户的公钥的认证。证书的内容包括:电子签证机关的信息、公钥用户信息、公钥、权威机构的签字和有效期等等。

    目前,证书的格式和验证方法普遍遵循X.509 国际标准。

  6. 客户端然后验证证书相关的域名信息、有效时间等信息;

  7. 客户端会内置信任 CA 的证书信息(包含公钥),如果CA不被信任,则找不到对应 CA 的证书,证书也会被判定非法。

在这个过程注意几点

  1. 申请证书不需要提供私钥,确保私钥永远只能服务器掌握
  2. 证书的合法性仍然依赖于非对称加密算法,证书主要是增加了服务器信息以及签名;
  3. 内置 CA 对应的证书称为根证书,颁发者和使用者相同,自己为自己签名,即自签名证书
  4. 证书=公钥+申请者与颁发者信息+签名;

五、SSL交互和握手过程

单项认证:

双向认证:

双向认证简单理解为客户端与服务端分别验证对方的证书,用来核实身份。确认过是对的人。根据约定的加密方法协商出一对会话密钥,该密钥是对称密钥。
双向认证比单项认证多了验证客户端身份的步骤。

更深入理解TLS/SSL交互流程可以参考博客。
图解SSL/TLS协议 - 阮一峰的网络日志

这篇专栏详细讲解了TLS协议
TLS_Protocol/Linux Kernel/ Optimization_Mrpre-CSDN博客

六、openssl生成证书及签名

实际应用中,一般人都不会找CA去签名,因为那是收钱的,所以自己可以通过openssl做一个自签名的证书文件。

CA证书也可以称为根证书。

1.生成CA私钥

openssl genrsa -passout pass:1111 -des3 -out ca.key 2048

说明:
genrsa 产生rsa密钥命令。
因为生成私钥需要输入密码。

所以使用 passout 代替shell 进行密码输入,否则会提示输入密码
-des3 为加密算法
2048 为私钥长度
默认的密钥长度一般都不够安全,老版本的 OpenSSL 默认 RSA 私钥是1024位,所以我们需要指定密钥长度,2048位是效率和安全的平衡点。如果 RSA 密钥的长度是512位,非常不安全,***者可以先获取你的证书,再使用暴力方式来算出对应的私钥,之后就可以冒充你的网站了。现在,一般认为2048位的 RSA 密钥是安全的,所以你应该采用这个长度的密钥。


也可以使用openssl rsa -in ca.key -noout -text进行查看。

2.根据CA私钥生成CA的自签名证书

openssl req -passin pass:1111 -new -x509 -days 365 -key ca.key -out ca.crt -subj "/C=CN/ST=FuJian/L=XiaMen/O=YaXon/OU=gRPC/CN=localhost"

使用-subj来替代shell进行身份输入。CN=localhost为域名设置,后续可以根据自己实际情况设置,比如CN=www.helloworld.com。

3.使用CA私钥和证书对服务端证书进行签名

openssl x509 -req -passin pass:1111 -days 365 -in server.csr -CA ca.crt -CAkey ca.key -set_serial 01 -out server.crt

客户端也是相同的操作。具体参数说明还是参考其他大神的总结吧。

OpenSSL 生成服务器及客户端证书_网络_万里归来少年心-CSDN博客

如何使用openssl生成证书及签名 - 简书

使用 openssl 生成证书(含openssl详解)-擡头看世界,低头写代码-51CTO博客

4.完整的密钥生成脚本

#!/bin/sh

echo Generate CA key:
openssl genrsa -passout pass:1111 -des3 -out ca.key 2048

echo Generate CA certificate:
openssl req -passin pass:1111 -new -x509 -days 365 -key ca.key -out ca.crt -subj "/C=CN/ST=FuJian/L=XiaMen/O=YaXon/OU=gRPC/CN=localhost"
 
echo Generate server key:
openssl genrsa -passout pass:1111 -des3 -out server.key 2048
 
echo Generate server signing request:
openssl req -passin pass:1111 -new -key server.key -out server.csr -subj "/C=CN/ST=FuJian/L=XiaMen/O=YaXon/OU=gRPC/CN=localhost"
 
echo Self-sign server certificate:
openssl x509 -req -passin pass:1111 -days 365 -in server.csr -CA ca.crt -CAkey ca.key -set_serial 01 -out server.crt
 
echo Remove passphrase from server key:
openssl rsa -passin pass:1111 -in server.key -out server.key
 
echo Generate client key
openssl genrsa -passout pass:1111 -des3 -out client.key 2048
 
echo Generate client signing request:
openssl req -passin pass:1111 -new -key client.key -out client.csr -subj "/C=CN/ST=FuJian/L=XiaMen/O=YaXon/OU=gRPC/CN=localhost"
 
echo Self-sign client certificate:
openssl x509 -passin pass:1111 -req -days 365 -in client.csr -CA ca.crt -CAkey ca.key -set_serial 01 -out client.crt
 
echo Remove passphrase from client key:
openssl rsa -passin pass:1111 -in client.key -out client.key

chmod 777 ca.crt ca.key client.crt client.csr client.key server.crt server.csr server.key

不修改生成密钥的权限,后续在grpc ssl验证过程会出现异常。

七、参考资料

openssl基本原理 + 生成证书 + 使用实例 - 谦信君 - 博客园

openssl ca(签署和自建CA) - 骏马金龙 - 博客园

openssl 证书请求和自签名命令req详解 - Gordon0918 - 博客园

HTTPS中CA证书的签发及使用过程 - xdyixia - 博客园

搭建私有CA并基于OpenSSL实现双向身份认证 - xdyixia - 博客园

SSL/TLS深度解析–OpenSSL 生成自签证书-斯图尔特-51CTO博客

图解公钥与私钥 | 《Linux就该这么学》

关于数字证书,数字签名,CA证书,Https都在这里了_网络_qq_15022971的博客-CSDN博客

通过openssl验证ssl证书匹配性_C/C++_huakai_sun的博客-CSDN博客

CA认证的原理和流程及https原理 - BruceLong - 博客园

Openssl 查看证书指令_运维_小丑鱼-CSDN博客

如何创建一个自签名的SSL证书(X509) - 简书

OpenSSL 生成服务器及客户端证书_网络_万里归来少年心-CSDN博客

如何使用openssl生成证书及签名 - 简书

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章