c - 不一致的 malloc 内存损坏

标签 c pointers memory memory-management malloc

我目前正在编写一个方法,该方法从分配的内存块中读取并打印出从某个偏移量到指定大小的内容,这两者都作为参数传递。我正在使用 char 指针来完成此操作,但在行周围不断出现 malloc 错误

char *content = (char *)malloc(size+1);

方法代码:

int file_read(char *name, int offset, int size)
{
    //First find file and its inode, if existing
    int nodeNum = search_cur_dir(name);
    if(nodeNum < 0) {
            printf("File read error: file does not exist\n");
            return -1;
    }

    //Size check, to avoid overflows/overreads
    if(offset > inode[nodeNum].size || size > inode[nodeNum].size || (offset+size) > inode[nodeNum].size)   {
            printf("File read error: offset and/or size is too large\n");
            return -1;
    }

    int i, read_size, track_size = size, content_offset = 0;
    int target_block = offset / BLOCK_SIZE; //Defined as constant 512
    int target_index = offset % BLOCK_SIZE;


    char *raw_content = (char *)malloc(inode[nodeNum].size+1);
    printf("check1\n"); //Debug statment

    for(i = target_block; i < (inode[nodeNum].blockCount-(size/BLOCK_SIZE)); i++)   {
            disk_read(inode[nodeNum].directBlock[i], raw_content+content_offset);
            content_offset += BLOCK_SIZE;
    }

    printf("check2\n"); //Debug statment
    char *content = (char *)malloc(size+1);

    memcpy(content, raw_content+target_index, size);
    printf("%s\n", content);
    free(raw_content);
    free(content);
    return 0;

}

和 disk_read 的代码:

char disk[MAX_BLOCK][BLOCK_SIZE]; //Defined as 4096 and 512, respectively
int disk_read(int block, char *buf)
{
                if(block < 0 || block >= MAX_BLOCK) {
                                printf("disk_read error\n");
                                return -1;
                }
                memcpy(buf, disk[block], BLOCK_SIZE);

                return 0;
}

节点结构

typedef struct {
                TYPE type;
                int owner;
                int group;
                struct timeval lastAccess;
                struct timeval created;
                int size;
                int blockCount;
                int directBlock[10];
                int indirectBlock;
                char padding[24];
} Inode; // 128 byte

使用此方法时出现的错误是内存损坏

*** glibc detected *** ./fs_sim: malloc(): memory corruption (fast): 0x00000000009f1030 ***

现在奇怪的是,首先这只发生在我使用该方法几次后 - 前两三次尝试它会起作用,然后错误发生。例如,这是一个示例测试运行:

% read new 0 5
z12qY

% read new 0 4
z12q

% read new 0 3
*** glibc detected *** ./fs_sim: malloc(): memory corruption (fast): 0x00000000009f1030 ***

更奇怪的是,当我注释掉时,这个错误就完全消失了

free(raw_content);
free(content);

即使这样也会占用内存。我已经通读了以前关于 malloc 内存损坏的帖子,并理解这通常是由于覆盖内存边界或分配空间不足造成的,但我看不出我可以在哪里做这件事。我也为 malloc 尝试了其他大小,当我注释掉释放两个指针的行时,这些产生了最好的结果。有谁看到我可能会遗漏什么?为什么这种情况会如此不一致地发生?

最佳答案

代码为字符和空字符分配空间,但不确保数组在打印为字符串之前以空字符终止。

char *content = (char *)malloc(size+1);
memcpy(content, raw_content+target_index, size);

// add
content[size] = '\0';

printf("%s\n", content);

可能还有其他问题。

[编辑]

OP 代码容易出现错误编码,并且依赖于 inode[] 以具有一致的值(.blockCount .size)。通过确定循环计数并根据该计数进行分配来阐明和简化。

int loop_count = (inode[nodeNum].blockCount-(size/BLOCK_SIZE)) - target_block;
char *raw_content = malloc(sizeof *raw_content * loop_count * BLOCK_SIZE);
assert(raw_count);
for (loop = 0; loop < loop_count; loop++) {
   i = target_block + loop;
   disk_read(inode[nodeNum].directBlock[i], raw_content + content_offset);
   content_offset += BLOCK_SIZE;
}

同时建议检查disk_read()是否成功

关于c - 不一致的 malloc 内存损坏,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33832901/

相关文章:

c - 如何连接两个字符串,其中源字符串应附加在目标字符串之前?

c - C语言读取内存

python - 编译多个模块时 import_array() 出现 Numpy/CAPI 错误

c - 如何将数组指针传递给函数?

php内存限制垃圾收集器

c - 求五次多项式一次根的代码

c - 任何优化都会删除代码(指向数组的 volatile 指针)

c - 如何以指针格式访问结构内的数组?

ios - 3 我不确定的泄漏?

c++ - 64 位 Windows 上应用程序可用的最大内存是多少