文件描述符复制函数dup2()详解

dup2()是dup()的“升级版“,原型是int dup2(int oldfd, int newfd),作用是让文件描述符newfd与oldfd所关联的文件(或缓冲区或管道或共享内存等)关联起来,如果一开始newfd已经和某个文件关联了(一个描述符同一时刻只能关联一个文件),那它会先解除newfd和某个文件的关联,然后再关联oldfd关联的那个文件。下面就拿文件描述符0,1做参数来写两个例子。

我们知道,当程序一执行,系统默认为该进程分别分配有一块空间作为标准输入缓冲区、标准输出缓冲区和标准错误输出缓冲区,默认与它们关联的文件描述符分别是0,1,2,程序中各种涉及到缓冲区的操作其实本质上也是通过它们的文件描述来的。

demo1:

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdio.h>
#include <unistd.h>
#include <string.h>

int main(void)
{
    int fd=open("./1.txt",O_RDWR|O_CREAT,0644);
    if(fd<0)
    {
        perror("open the 1.txt");
        goto err0;
    }
     int ret=dup2(fd, 1); // 让本来指向标准输出缓冲区的描述符1指向文件1.txt
     if(ret<0)
     {
         perror("dup2");
		          goto err1;
     }
 
      printf("where am I?\n"); //向输出缓冲区写入数据
 
      close(fd);
      return 0;
err1:
     close(fd);
err0:
     return 1;
} 

上面程序中,先通过open()打开文件1.txt,得到与之关联的文件描述符fd,然后通过dop2()让本来关联着标准输出缓冲区的文件描述符0去关联文件1.txt,结果后面调用printf()向输出缓冲区写入内容时,它把1.txt误当做了输出缓冲区,于是语句“where am I?”被输出到了1.txt文件中:

 

 

demo2:

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdio.h>
#include <unistd.h>
#include <string.h>

int main(void)
{
    int fd=open("./1.txt",O_RDWR|O_CREAT,0644);
    if(fd<0)
    {
        perror("open the 1.txt");
        goto err0;
    }
     int ret=dup2(fd, 0); // 让本来指向标准入缓冲区的描述符0指向文件1.txt
     if(ret<0)
     {
         perror("dup2");
		          goto err1;
     }

     char buf[128]="";
     gets(buf);  // 从输入缓冲区读取数据
     puts(buf);

     close(fd);
     return 0;
err1:
     close(fd);
err0:
     return 1;
}

同理,上面的程序中,让本来关联着标准输入缓冲区的文件描述符0现在关联文件1.txt(文件中只有“where am I?”这一句话),当调用gets()从想输入缓冲区读取数据时,依然把文件1.txt当做了标准输入缓冲区,读取了文件中的“where am I?”并返回,所以终端也并没有给用户输入数据的机会:

  • 2
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值