主密钥计算:master_secret = PRF(pre_master_secret, "master secret",
ClientHello.random + ServerHello.random)
PRF算法:
PRF(secret, label, seed) =
P_MD5(S1, label + seed) XORP_SHA-1(S2, label + seed);
其中P_hash( )函数定义如下:
P_hash(secret, seed) = HMAC_hash(secret, A(1) + seed) +
HMAC_hash(secret, A(2) + seed) +
HMAC_hash(secret, A(3) + seed) + ...
此处 + 表示连接。
A() is defined as:
A(0) = seed
A(i) = HMAC_hash(secret, A(i-1))
P_hash(secret, seed)可以迭代任意多次,用以获得所需数量的数据,因为SHA-1处理20字节的输出,主密钥一般都是48字节,所以这里取到A(3)产生60字节的输出,而12字节将会抛弃,只留下48字节的数据。同理MD5处理16字节输出也需要取到A(3)。
“label”是一个ASCII的字符串,本例中为"master secret",即:
6d 61 73 74 65 72 20 73 65 63 72 65 74
S1、S2是密文的等长的两个部分,S1取自密文第一部分,S2为第二部分,本例中各为24个0x01.
1. 计算key_block
key_block = PRF(SecurityParameters.master_secret,"key expansion", SecurityParameters.server_random +SecurityParameters.client_random);
key expansion的ASCII字符串是:
6B 65 79 20 65 78 70 61 6E 73 69 6F 6E
从而产生密码素材:
client_write_MAC_secret = key_block[0..15]
server_write_MAC_secret = key_block[16..31]
client_write_key = key_block[32..36]
server_write_key = key_block[37..41]
2. 计算得到密钥
final_client_write_key = PRF(client_write_key,
"client write key",
client_random +
server_random)[0..15]
client write key的ASCII字符串为:
63 6c 69 65 6e 74 20 77 72 69 74 65 5f 6b 65 79
final_server_write_key = PRF(server_write_key,
"server write key",
client_random +
server_random)[0..15]
server write key的ASCII字符串为:
73 65 72 76 65 72 20 77 72 69 74 65 5F 6B 65 79
iv_block= PRF("", "IV block",client_random +server_random)[0..15]
client_write_IV = iv_block[0..7]
server_write_IV = iv_block[8..15]
IV block的ASCII字符串为:
49 56 2062 6C 6F 63 6B
最 后根据主密钥计算的到6个实际使用的密 钥:client_write_MAC_secret;server_write_MAC_secret;client_write_key;server_write_key;client_write_IV;server_write_IV;