TLS1.2 AEAD GCM

TLS1.2 AEAD GCM的计算

TLS1.2中记录层协议对数据的保护方法支持三种算法:
(源自RFC 5246中6.2.3)

  1. Null or Standard Stream Cipher
  2. CBC Block Cipher
  3. AEAD Ciphers
    我在抓包的过程中,发现算法套件是AES_GCM, 因此是属于AEAD Ciphers,AEAD的另一种算法是CCM,这里不做介绍,感兴趣的可以去看RFC.
    TLS 记录层协议在进行数据加密保护时,过程是:
    fragment —》compress ----》encrypt
    即分段、压缩、加密
    分段的数据要小于2^14
    压缩算法因为存在安全问题,目前一般不压缩

下面重点分析AESGCM的加密过程:

首先看抓包数据,我们分析加密的第一条,即handshake的最后一条,Finished数据包,如下图所示:
TLS1.2 AEAD GCM
图中可以看出整个TLS包的数据为:
16030300280000000000000000b75315d8ce17033a17c67bc7f6818873a9bd1adb0a5e0516ced403d83f173d1e
其中,1603030028为报头,剩余为加密的数据段
RFC5246中6.2.3.3中TLSCiphertext.fragment的数据结果如下:
TLS1.2 AEAD GCM
数据结构分为两部分,结合RFC5246的介绍,可对
0000000000000000b75315d8ce17033a17c67bc7f6818873a9bd1adb0a5e0516ced403d83f173d1e
进行解析,
其中前八个字节0000000000000000为seq_num,根据RFC的介绍,seq_num为64位,从0开始,单调递增。
而剩余的32字节数据:b75315d8ce17033a17c67bc7f6818873a9bd1adb0a5e0516ced403d83f173d1e
即为opaque content[TLSCompressed.length]

根据RFC5246, AESGCM有4个输入,write_key, nonce, plaintext,
additional_data:
TLS1.2 AEAD GCM
write_key:数据发送端的加密工作**
nonce:
salt + seq_num
plaintext:明文
additional_data:
TLS1.2 AEAD GCM
这里write_key和plaintext 不用过多介绍,比较简单。nonce和additional_data的来源不是特别清楚。
先说additional_data吧,如上图所示,RFC5246是给出了additional_data的结构组成,但是由于没有使用压缩算法,type和version是何值不是确定,后来仔细看了RFC5246,有这样的介绍:
TLS1.2 AEAD GCM
TLS1.2 AEAD GCM
一开始没有结合上下文准确理解这里的identical的对象,后来经专家指点,发现这个type和version就是TLS的报头中的信息。
因此对于上面的抓包数据,
additional_data = ‘0000000000000000’+‘160303’+‘0010’
上文机密的数据长度为32(0x20)字节,为什么这里是‘0010’?
这是因为上文的32字节数据,包含MAC数据,AES_128_GCM的MAC长度为16,所以实际的密文数据为16(0x10)字节。

最后剩下了nonce,nonce在RFC5116里有详细介绍,nonce一般有两部分组成,隐式部分+显示部分,最小长度为12字节。隐式部分一般使用发送方的4字节IV值(salt),显示部分一般使用seq_num。
因此这里的nonce = IV + seq_num。

AES_128_GCM的counter(IV)是16字节,而这里只有12字节?
经百度查询,有专家指出,AES_128_GCM在计算时会在12字节nonce后面加上4字节的00000001。

最后,调用AESGCM的解密函数,得到明文:
1400000cda12b5318bc16ac3dcf86d53
(bingo!!!)
一看格式就证明基本没问题,数据结构如下图所示。
1400000c为密文结构的报头。
0x14(20)为Finished. 0x00000c为数据长度。
TLS1.2 AEAD GCM
da12b5318bc16ac3dcf86d53为12字节的明文数据,即为下图数据结构的verify_data.
TLS1.2 AEAD GCM