【拜读】《码出高效》之HTTPS

声明本文全文直接摘录自《码出高效》,布局略作调整,夹杂少许本人的注释,强烈推荐阅读孤(尽)、鸣(莎)大侠的
           这本好书!


场景举例说明

       在谍战剧里,情报如何不被截获,不被破译,几乎是全聚德主线剧情之一。某电台通过某个频道发送一串数字,然后潜伏人员一般会那密码本,译码后得到原文。这个密码本就是对称加密中的密钥,发送方和接收方按照密码本分别进行加密和解密工作。如果密码本被敌人截获,则后果极为严重,通常能够做的也就是更换密码本。

       早期计算机都是单机状态,保证素具的安全依赖于加密算法的可靠性。如果机密算法可靠,即时存储介质被窃取,对方想通过密文恢复明文也是十分困难的。DES加密算法是一种对称加密算法,它几乎让破解者无法找到规律,即使暴力破解也很难还原出明文。

       发展到网络时代,整个网络中最频繁。最重要的操作就是网络中各终端之间的通信。在传输层本身不会做任何的加密,这就好比一辆载满黄金的马车在驿道奔驰,很难不让网络上的黑客视而不见。如何保证通信之间数据传输的安全性,成为了计算机网络时代最重要的安全课题。说道对网络传输数据的加密,必须要先说安全套接字层(Secure Socket Layer, SSL)。SSL协议工作于传输层与应用层之间,为应用提供数据的加密传输。而HTTPS的全称是HTTP over SSL,简单的理解就是在之前的HTTP传输上增加了SSL协议的加密能力

       我们可以通过对称加密算法对数据进行加密,比如DES,即一个主站与用户间可以使用相同的密钥对数据传输内容进行加解密。是否可以认为这样就完全没有风险呢?答案显然是否定的。因为密钥几乎没有什么保密性可言,如果是每一个用户之间都约定一个独立的密钥,如何把密钥传输给对方,又是一个安全难题。在互联网上,IP报文好比管道上运送粮草、黄金、物质的载体,很容易被盯上,密钥本身如果被盗,那么再复杂的密钥也是摆设。自然的想法是在密钥之上再加密,这就是递归的穷举问题了。


非对称加密算法、中间人攻击、CA证书

声明此处只是简单说明,更详细更通俗易懂的解释可详见https://blog.c...396490https://blog...95039

       有没有一种方式,使报文被截取之后,黑客依然无计可施呢?一种全新的算法RSA出现了。它把密码革命性的分成公钥和私钥,由于两个密钥并不相同,所以称为非对称加密。私钥是用来对公钥加密的信息进行解密的是需要严格保密的。公钥是对信息进行加密,任何人都可以知道,包括黑客。

       非对称加密的安全性是基于大质数分解的困难性,在非对称的加密中公钥和私钥是一对大质数函数。计算两个大质数的乘积是简单的,但是这个过程的逆运算(即将这个乘积分解为两个质数)是非常困难的。而在RSA的算法中,从一个公钥和密文中解密出明文的难度等同于分解两个大质数的难度。因此在实际传输中,可以把公钥发给对方。一方发送信息时,使用另一方的公钥进行加密生成密文。收到密文的一方再用私钥进行解密,这样一来,传输就相对安全了。

       但是非对称加密并不是完美的,它有一个很明显的缺点是加密和解密耗时长,只适合对少量数据进行处理。回到前面的例子中,我们担心对称加密中的密钥安全问题,那么将密钥的传输使用非对称加密就完全地解决了这个问题。实际上,HTTPS也正是通过这样一种方式来建立安全的SSL连接的。按照上述逻辑,用户甲与用户乙进行非对称加密传输的过程如下:

  1. 甲告诉乙,使用RSA算法进行加密。乙说,好的。

  2. 甲和乙分别根据RSA生成一对密钥,互相发送公钥。

  3. 甲使用乙的公钥给乙加密报文信息。

  4. 乙收到信息,并用自己的密钥进行解密。

  5. 乙使用同样方式给甲发送信息,甲使用同样方式进行解密。

       上述过程看似无懈可击,但是在TCP/IP里,端到端路途遥远,夜长梦多。在步骤2中,如果甲的送信使者中途被强盗截住,在严刑拷打之下,强盗知道使者是去送公钥的,虽然没有办法破解甲的加密信息,但是可以把这个使者关起来,自己生成一对密钥,然后冒充甲的使者到乙家,把自己的公钥给乙。乙信了,把银行卡密码、存款金额统统告诉了中间的强盗。(注:个人感觉此处“中间人攻击”举例没有说得很全,表达不够到位,可参考https://blog.c...396490https://blog...95039。)

       所以,在解决了加密危机之后又产生了信任危机。如何解决信任问题呢?如果有一个具有公信力的组织来证明身份,这个问题就得到了解决。CA(Certificate Authority)就是颁发HTTPS证书的组织。HTTPS是当前网站的主流文本传输协议,在基于HTTPS进行连接时,就需要数字证书。如下图所示,可以看到协议版本、签名方案、签发的组织是GlobalSign,这个证书的有效期至2018年10月31日。


访问一个 HTTPS 的网站的大致流程(简述)

  1. 浏览器向服务器发送请求,请求中包括浏览器支持的协议,并附带一个随机数。

  2. 服务器收到请求后,选择某种非对称加密算法,把CA数字证书签名公钥、身份信息发送给浏览器,同时也附带一个随机数。

  3. 浏览器收到后、验证证书的真实性,用服务器的公钥发送握手信息给服务器。

  4. 服务器解密后,使用主前的随机数计算出一个对称加密的密钥,以此作为加密信息并发送。

  5. 后续所有的信息发送都是以对称加密方式进行的。

       我们注意到在证书的信息中出现了传输层安全协议(Transport Layer Security, TLS)的概念。这里先解释TLS和SSL的区别。TLS可以理解成SSL协议3.0版本的升级,所以TLS的1.0版本也被标识为SSL3.1版本。但对于大的协议枝而言,SSL和TLS并没有太大的区别,因此在 Wireshark里,分层依然用的是安全套接字层(SSL)标识。


HTTPS连接建立过程(即:HTTPS的握手)

       在整个 HTTPS 的传输过程中,主要分为两部分 首先是HTTPS的握手(即:HTTPS的连接建立过程),然后是数据的传输。前者是建立一个HTTPS的通道,并确定连接使用的加密套件及数据传输使用的密钥。而后者主要使用密钥对数据加密并传输。下面主要分析HTTPS的连接建立过程。

第一步

       客户端发送了个ClientHello协议的请求。在ClientHello中最重要的信息是CipherSuites字段,这里客户端会告诉服务端自己支持哪些加密的套件。比如在这次SSL连接中,客户端支持的加密套件协议如下图所示。

第二步

       服务端在收到客户端发来的ClientHello的请求后,会返回一系列的协议数据,并以一个没有数据内容的ServerHelloDone作为结束。这些协议数据有的是单独发送,有的则是合并发送,这里分别解释下几个比较重要的协议,如下图所示(SSL协议)。

Server Hello协议:主要告知客户端后续协议中要使用的TLS协议版本,这个版本主要和客户端与服务端支持的
                                最高版本有关。比如本次确认后续的TLS协议版本是TLSvl.2,并为本次连接分配个会话
                                ID(SessionID)。此外,还会确认后续采用的加密套件(CipherSuite),这里确认使用的加密套
                                件为TLS_ECDHERSAWITHAES128GCMSHA256。该加密套件的基本含义为,使用非对称
                                协议加密(RSA)进行对称协议加密(AES)密钥的加密,并使用对称加密协议(AES)进行信息
                                的加密。

Certificate协议:主要传输服务端的证书内容。

Server Key Exchange:如果在Certificate协议中未给出客户端足够的信息,则会在ServerKeyExchange进行补
                                        充,如下图所示。比如在本次连接中Certificate未给出证书的公钥(Publick Key),这个
                                        公钥的信息将会通过ServerKeyExchange发送给客户端。

Certificate Request:这个协议是一个可选项,当服务端需要对客户端进行证书验证的时候,才会向客户端发送一个
                                     证书请求(CertificateRequest)。

Server Hello Done:最后以Server Hello Done作为结束信息,告知客户端整个ServerHello过程结束。

第三步

       客户端在收到服务端的握手信息后,根据服务端的请求,也会发送系列的协议。

Certificate:它是可选项。因为上文中服务端发送了CertificateRequest需要对客户端进行证书验证,所以客户端要发
                      送自己的证书信息。

Client Key Exchange:它与上文中ServerKeyExchange类似,是对客户端Certificate信息的补充,在本次请求中同
                                        样是补充了客户端证书的公钥信息,如下图所示。

Certification Verity:对服务端发送的证书信息进行确认。

Change Cipher Spec:该协议不同于其他握手协议(Handshake Protocol),而是作为一个独立协议告知服务端,客户
                                       端己经接收之前服务端确认的加密套件,并会在后续通信中使用该加密套件进行加密。

Encrypted Handshake Message:用于客户端给服务端加密套件加密一段Finish的数据,用以验证这条建立起来的加
                                                          解密通道的正确性。

第四步

       服务端在接收客户端的确认信息及验证信息后,会对客户端发送的数据进行确认,这里也分为几个协议进行回复。

Change Cipher Spec:通过使用私钥对客户端发送的数据进行解密,并告知后续将使用协商好的加密套件进行加密传
                                       输数据。

Encrypted Handshake Message:与客户端的操作相同,发送一段Finish的加密数据验证加密通道的正确性。

 

最后,如果客户端和服务端都确认加解密无误后,各自按照之前约定的Session Secret对Application Data进行加密传输

 

说明:因为是摘录自书籍,所以此篇博客定位为转载。

^_^ 如有不当之处,欢迎指正

^_^ 本文摘录自
             
《码出高效》, 杨冠宝(孤尽)  高海慧(鸣莎)  著

^_^ 本文已经被收录进《程序员成长笔记(五)》,笔者JustryDeng

  • 3
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
System.arraycopy是Java中的一个方法,用于将一个数组的内容复制到另一个数组中。它的用法是:System.arraycopy(Object src, int srcPos, Object dest, int destPos, int length)。其中,src是源数组,srcPos是源数组的起始位置,dest是目标数组,destPos是目标数组的起始位置,length是要复制的元素个数。 System.arraycopy是一种浅拷贝方式,它只是将源数组的引用复制给目标数组,而不会复制源数组中的元素的值。因此,如果原始数组改变了,复制的数组也会发生相应的改变。 关于System.arraycopy的具体实现,可以参考引用中的源码拜读部分。另外,引用中也提到了System.arraycopy是对数组进行复制的常用方法。 在引用的代码示例中,可以看到System.arraycopy的具体用法。首先定义了一个二维数组src,然后使用System.arraycopy将src复制给了dest数组。接着,通过修改src数组的元素,可以观察到dest数组也发生了相应的改变,这正是浅拷贝的特性。 总之,System.arraycopy是Java中用于数组复制的方法,它是一种浅拷贝方式,可以将源数组的内容复制到目标数组中。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* *2* *3* [System.arraycopy详解](https://blog.csdn.net/yangruidage21/article/details/128519021)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 100%"] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值