C语言使用printf编写SHA256测试用例输出异常问题求助
问题根因定位
你遇到的异常是栈缓冲区溢出导致的栈上数据被破坏,具体诱因有两处:
1. 最初版本construct_buf的严重越界写问题
我们先算指针偏移:
你的buf总长度为65字节,每次sprintf写入8个十六进制字符,循环8次刚好写满64个字符,此时buf += sprintf(...)执行完8次后,buf指针已经指向了数组的第64位(即buf[64],是预留的终止符位置)。
此时你执行buf[64] = '\0',等价于访问原始buf数组的64 + 64 = 128位,远超65字节的数组边界,属于典型的栈越界写。
越界写直接破坏了栈上相邻存储的outputs指针数组:你看到的第三个测试用例异常预期值414140de...,刚好是第一个预期字符串跳过前16个字符的子串,说明越界写把outputs[2]的指针篡改为指向第一个字符串偏移16字节的位置,导致第三次比较时取到了错误的预期值。
单独测试用例不会触发问题的原因是:仅执行一次construct_buf时,越界写的内存位置没有刚好覆盖outputs数组的有效指针,因此没有出现异常。
2. 你修改后的代码仍存在笔误
你修改后的循环逻辑已经避免了指针偏移错误,但最后终止符赋值写错了变量:
data[64] = '\0';
你函数参数传入的目标缓冲区是buf,不存在名为data的局部变量,这行代码要么编译失败,要么会非法访问其他内存,应该改为:
buf[64] = '\0';
其他说明
Valgrind输出的大内存范围权限警告是macOS平台Valgrind的已知兼容性问题,和你的代码无关;未初始化值报错是栈溢出破坏内存后,访问被篡改的outputs[2]指针导致的。
另外补充:你当前MRE中的主函数没有调用update_sha256处理测试向量,直接调用了硬编码返回固定哈希的construct_buf,如果要实现正常的SHA256测试逻辑,需要在init_sha256之后补充调用update_sha256(ctx, vectors[i], strlen(vectors[i])),再调用哈希计算和结果导出函数。
内容的提问来源于stack exchange,提问作者gmdev

