You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C语言手动实现malloc出现段错误,Valgrind报Invalid read of size 4如何解决?

问题原因排查和解决

核心错误原因

  • 拆分空闲块时,若分配的是链表第一个节点(prev == NULL),没有更新全局head指针指向拆分后的新空闲节点,导致head仍然指向已经被分配出去的内存块
  • 后续你给已分配块的前8字节写入头部信息(大小、魔数),直接覆盖了原空闲节点结构体的size和flink字段,导致链表遍历的时候读取到非法的flink指针,触发段错误

这个现象和你测试的表现完全吻合:注释掉写头部的两行代码时,已分配块前8字节还保留着原空闲节点的结构体数据,链表遍历可以正常拿到合法的下一个节点指针,就不会触发段错误。Valgrind打印的非法下一个节点地址0x3e7000000028,其中高32位的0x3e7就是你写入的魔数999的十六进制值,也可以佐证这个判断。

修复方案

在拆分块的逻辑中补充prev == NULL时更新全局head的代码即可:

if (current->size - minimum_chunk_size >= 16) { //  allocate tail end
    // set up new freelistnode
    struct freelistnode * new = (FreeListNode)(ptr + minimum_chunk_size);
    new->size = current->size - minimum_chunk_size;
    if (prev != NULL) {
        prev->flink = new;
    } else {
        // 新增这行:如果是链表首节点拆分,更新head指向新的空闲块
        head = new;
    }
    new->flink = current->flink;
}

同时注意你代码中sbrk申请新内存块的分支也存在同样的head更新遗漏问题,建议同步补上对应判断逻辑,避免后续触发同类错误。

内容的提问来源于stack exchange,提问作者Suds

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.30 10:18:00