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

fscanf读取Valgrind内存追踪文件时丢失地址前导7的问题

Valgrind内存追踪文件解析问题:前导7丢失的原因与解决

问题现象

读取Valgrind生成的内存追踪文件时,以7开头的内存地址(如7ff000398)被解析后丢失前导7,变成ff000398,导致内存地址识别错误,影响后续分区处理。

重现案例

测试文件内容

S 7ff000398,8
S 7ff000390,8

代码输出

Parsed line: # 0. Operation: S, address:     ff000398, size: 8
Parsed line: # 1. Operation: S, address:     ff000390, size: 8  

问题代码

// some logic before this
FILE * pFile;
pFile = fopen(tracefile, "r");
if (!pFile) {
    fprintf(stderr, "unable to open %s\n", tracefile);
    exit(EXIT_FAILURE);
}
char operation_id;
unsigned address;
int size;
// Line is of format " M 0x3242,4" or "I 0x324234,4"
const char *format = " %c %16x,%d";
int i = 0;
while (fscanf(pFile, format, &operation_id, &address, &size) > 0) {
    printf("Parsed line: # %d. Operation: %c, address: %16x, size: %d\n", i, operation_id, address, size);
    i++;
}

原因分析

核心问题是类型宽度不匹配导致的数值截断:

  • %x格式符用于解析无符号十六进制整数,对应存储类型是unsigned int。在32位系统中,unsigned int仅占4字节(32位),最多能存储8位十六进制数(0~FFFFFFFF)。
  • 要解析的7ff000398是9位十六进制数,对应36位二进制值,远超32位unsigned int的存储范围。fscanf会将超出范围的高位截断,只保留低32位,也就是ff000398,这就导致前导的7丢失了。
  • 之前尝试添加0x前缀无效,是因为前缀仅用于标识十六进制数,但类型宽度不足的核心问题未解决。

解决方案

修改代码中地址的存储类型和对应格式符,适配64位地址:

  1. 将address的类型从unsigned改为unsigned long(或更明确的uint64_t,需包含<stdint.h>头文件)。
  2. 解析和输出时的格式符从%x改为%lx(对应unsigned long),若使用uint64_t则用%lx或%llx(取决于编译器)。

修改后的代码示例:

// some logic before this
#include <stdint.h> // 使用uint64_t需包含此头文件
FILE * pFile;
pFile = fopen(tracefile, "r");
if (!pFile) {
    fprintf(stderr, "unable to open %s\n", tracefile);
    exit(EXIT_FAILURE);
}
char operation_id;
uint64_t address; // 改用64位无符号整数存储地址
int size;
const char *format = " %c %16lx,%d"; // 格式符改为%lx适配64位整数
int i = 0;
while (fscanf(pFile, format, &operation_id, &address, &size) > 0) {
    printf("Parsed line: # %d. Operation: %c, address: %16lx, size: %d\n", i, operation_id, address, size);
    i++;
}

这样就能完整解析9位甚至更长的十六进制内存地址,不会再出现截断丢失前导位的问题。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.23 02:28:23