linux mmap返回值问题


   
  #include <sys/mman.h>
  
#include <sys/stat.h>
#include <fcntl.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>

int main(int argc, char* argv[])
{
int fdin, fdout;
void *src, *dst;

struct stat statbuf;

if (argc != 3)
{
printf("./a.out infile outfile");
exit(-1);
}

if ((fdin = open(argv[1], O_RDONLY)) < 0)
{
printf("open %s failed!\n", argv[1]);
exit(-1);
}

if ((fdout = open(argv[2], O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH)) < 0)
{
printf("open %s failed\n", argv[2]);
exit(-1);
}

if (fstat(fdin, &statbuf) < 0)
{
// get size of input file
printf("get file size failed!\n");
exit(-1);
}
printf("fdin file length:%d\n", (int)statbuf.st_size);

// set the size of output
lseek(fdout, statbuf.st_size-1, SEEK_SET);
write(fdout, "", 1);

if ((src=mmap(0, statbuf.st_size, PROT_READ, MAP_SHARED, fdin, 0) == MAP_FAILED))
{
printf("map fdin failed\n");
exit(-1);
}

if ((dst=mmap(0, statbuf.st_size, PROT_READ | PROT_WRITE, MAP_SHARED, fdout, 0) == MAP_FAILED))
{
printf("map fdout failed\n");
exit(-1);
}

printf("before memcpy\ndst=0x%x\nsrc=0x%x\n", dst, src);
memcpy(dst, src, statbuf.st_size);

printf("copy successed!\n");
exit(0);
}

程序的作用很简单,就是通过mmap完成一个文件拷贝。
现在的问题是,mmap能够正常放回,但其返回的值为0x0,从而导致后面memcpy出现段错误。
mmap为什么会返回一个0x0这个用户程序不能访问的地址,问题出在哪里呢?
还请大家帮忙看下,谢谢!

PS:
参考mmap手册: mmap
“如果 addr 是 NULL,内核将挑选一个合适的地址作为起始地址,这通常是最可移植的创建新映射的方法。如果 addr 不是 NULL,内核把作为放置映射的一个暗示;在 Linux 系统里,映射将在附近的页边界创建。新映射的地址将作为这个调用的结果返回。”

Linux IO

左將軍董叔穎 10 years, 4 months ago

两个if里括号的位置写错了。

   
  if ((src=mmap(0, statbuf.st_size, PROT_READ, MAP_SHARED, fdin, 0)) == MAP_FAILED)
  
{
printf("map fdin failed\n");
exit(-1);
}

if ((dst=mmap(0, statbuf.st_size, PROT_READ | PROT_WRITE, MAP_SHARED, fdout, 0)) == MAP_FAILED)
{
printf("map fdout failed\n");
exit(-1);
}

Hamono answered 10 years, 4 months ago

Your Answer