/ proc / self / maps使用fwrite错误地址错误将内存写入文件

时间:2016-01-17 01:31:06

标签: linux memory fwrite memory-address proc

我尝试使用fwrite将内存写入文件,但它得到了错误的地址"。我不知道原因。

代码如下所示

static struct MmapHeader* mmap_headers[HEADER_MAX];

struct MmapHeader
{
    bool isContext; // used to mark the end of maps
    size_t start; //process memory start address
    size_t len; // process memory size
    int prot; // permission
    size_t offset; //offset
    char file_name[FILE_NAME_MAX]; //file name
};

for(i=0;mmap_headers[i]!=NULL;i++)
{
    if(mmap_headers[i]->prot & PROT_READ)
    {
        printf("save map information start:%zx,len:%zx\n",mmap_headers[i]->start,mmap_headers[i]->len);
        if(fwrite(mmap_headers[i],sizeof(struct MmapHeader),1,save_file)<1)
            perror("following error occur:");
        fflush(save_file);
        //******
        //error is in fwrite below, mmap_headers[i]->start is the address of
        //memory, the address is read from file /proc/self/maps the value is
        //7ffea6de4000(hex), the mmap_headers[i]->len is 2000(hex). 
        if(fwrite((void*)mmap_headers[i]->start,mmap_headers[i]->len,1,save_file)<1)
            perror("following error occur:");//here is "bad address error only for address 7ffea6de4000(hex)"
        fflush(save_file);
    }
}

输出是:

save map information start:400000,len:c1000
save map information start:6c0000,len:3000
save map information start:6c3000,len:3000
save map information start:1921000,len:23000
save map information start:2b7d46805000,len:2000
save map information start:7ffea6dc3000,len:21000
save map information start:7ffea6de4000,len:2000
following error occur:: Bad address
save map information start:7ffea6de6000,len:200

mmap_headers存储从文件/ proc / self / maps读取的进程信息,mmap_headers的大小为8,其他7个地址写成功除了地址7ffea6de4000(hex),有人有想法吗?

1 个答案:

答案 0 :(得分:0)

&#34;地址错误&#34;对应于错误代码EFAULT。如果您阅读基础系统调用的手册页man 2 write,您将找到错误的描述:

EFAULT buf is outside your accessible address space.

这意味着您传递给fwrite(因此传递给write)的地址无效。

如果您运行cat /proc/self/maps,即使在像cat这样的程序中,也会看到有不可读的页面:

00400000-0040c000 r-xp 00000000 00:11 6447384                            /usr/bin/cat
0060b000-0060c000 r--p 0000b000 00:11 6447384                            /usr/bin/cat
0060c000-0060d000 rw-p 0000c000 00:11 6447384                            /usr/bin/cat
0060d000-0062e000 rw-p 00000000 00:00 0                                  [heap]
34ddd837000-34dddba0000 r--p 00000000 00:11 6755848                      /usr/lib/locale/locale-archive
34dddba0000-34dddd3b000 r-xp 00000000 00:11 6904408                      /usr/lib/libc-2.22.so
34dddd3b000-34dddf3a000 ---p 0019b000 00:11 6904408                      /usr/lib/libc-2.22.so
34dddf3a000-34dddf3e000 r--p 0019a000 00:11 6904408                      /usr/lib/libc-2.22.so
34dddf3e000-34dddf40000 rw-p 0019e000 00:11 6904408                      /usr/lib/libc-2.22.so
34dddf40000-34dddf44000 rw-p 00000000 00:00 0 
34dddf44000-34dddf66000 r-xp 00000000 00:11 6904407                      /usr/lib/ld-2.22.so
34dde119000-34dde11c000 rw-p 00000000 00:00 0 
34dde13f000-34dde161000 rw-p 00000000 00:00 0 
34dde161000-34dde163000 r--p 00000000 00:00 0                            [vvar]
34dde163000-34dde165000 r-xp 00000000 00:00 0                            [vdso]
34dde165000-34dde166000 r--p 00021000 00:11 6904407                      /usr/lib/ld-2.22.so
34dde166000-34dde167000 rw-p 00022000 00:11 6904407                      /usr/lib/ld-2.22.so
34dde167000-34dde168000 rw-p 00000000 00:00 0 
3fd669db000-3fd669fd000 rw-p 00000000 00:00 0                            [stack]
ffffffffff600000-ffffffffff601000 r--p 00000000 00:00 0                  [vsyscall]

此处属于libc的第二页不可被程序读取。如果程序试图将此作为write系统调用的参数传递,则不会成功,我怀疑这正是代码中发生的事情。