C语言文件映射读取出现冗余字符问题排查请求
问题排查与原因分析
核心原因1:未处理字符串终止符
直接读取文件时,通常会在读取内容末尾手动追加'\0'保证字符串正常结束,但mmap是直接将文件内容映射到内存。若文件本身没有以空字符结尾,映射区域后续属于同内存页但超出文件实际大小的空间会包含随机脏数据(比如你看到的DEL、乱码字符),程序将这部分误判为字符串内容输出,就会出现冗余字符。
核心原因2:映射大小计算错误
如果计算文件大小的逻辑有误(比如误用st_blksize而非st_size,或未正确处理文件大小的内存页对齐),会导致映射的内存区域大于实际文件内容,超出部分的内存数据是不确定的垃圾值,输出时会被一并读取。
验证与修复方案
- 映射文件后,在文件实际大小的位置手动写入
'\0'(需确保映射区域有可写权限,或读取时仅取前st_size个字节) - 严格使用
stat()获取的st_size作为映射长度,避免映射超出文件实际内容的内存区域 - 输出时限定读取长度为文件实际大小,不要直接把映射地址当作无长度限制的C字符串处理
修复后的关键代码片段示例:
struct stat sb; int fd = open("test.txt", O_RDONLY); fstat(fd, &sb); // 多映射1字节用于存放终止符 char *addr = mmap(NULL, sb.st_size + 1, PROT_READ | PROT_WRITE, MAP_PRIVATE, fd, 0); if (addr != MAP_FAILED) { addr[sb.st_size] = '\0'; // 手动添加字符串终止符 printf("%s\n", addr); munmap(addr, sb.st_size + 1); } close(fd);
内容的提问来源于stack exchange,提问作者Joy
相关产品推荐
相关产品推荐

