flawopen.com/Teardowns/cve-2014-0160-heartbleed
CVE-2014-0160(心脏出血 / Heartbleed)源码级补丁深度剖析:解析 OpenSSL 的 tls1_process_heartbeat 中因缺失边界检查导致单次请求泄露 64KB 核心服务器内存的完整技术机理。
想象一下,你给一只训练有素的鹦鹉发送了一个 4 个字母的单词 'BIRD',并对它说:'重复我这 4 个字母的单词,但你的回答必须有 64,000 个字母长'。鹦鹉尖叫了一声 'BIRD',紧接着开始喋喋不休地背诵它脑海中储存的后续 63,996 个字符——其中赫然包含其他访客刚说过的绝密密码、私钥和银行账号。在 Heartbleed(心脏出血)漏洞中,OpenSSL 盲目相信了客户端声称的消息长度,却未校验数据包的真实尺寸,将服务器内存中的敏感明文直接倾倒给了攻击者。
Open Source SystemsCWE-SecurityDefense-in-Depth根本原因在于开源系统中未经验证的边界参数,导致状态不同步并绕过安全控制。
Attacker connects to a TLS server and sends a Heartbeat Request containing a 1-byte payload ('A').
Attacker sets the length field to the maximum possible value: 0xFFFF (65,535 bytes).
The server allocates a 64KB response buffer based on the client's claimed size and calls memcpy().
The memory copy overreads past the end of the packet, dumping private SSL keys, user passwords, and active session tokens.
/* Read 16-bit length directly from client packet without bounds check */
n2s(p, payload);
pl = p;
/* Allocate reply buffer based on client's claimed size */
buffer = OPENSSL_malloc(1 + 2 + payload + padding);
bp = buffer;
/* BUG: Copies up to 64KB of adjacent server heap memory! */
memcpy(bp, pl, payload);
r = ssl3_write_bytes(s, TLS1_RT_HEARTBEAT, buffer, 3 + payload + padding);
/* Read 16-bit length from packet */
n2s(p, payload);
pl = p;
/* FIX: Validate that claimed payload does not exceed actual received record length */
if (1 + 2 + payload + 16 > s->s3->rrec.length)
return 0; /* Silently discard malformed heartbeat */
buffer = OPENSSL_malloc(1 + 2 + payload + padding);
bp = buffer;
memcpy(bp, pl, payload);
memcpy().:。