Linux系统编程与网络编程——VFS虚拟文件系统以及dup函数(四)

VFS虚拟文件系统

Linux支持各种各样的文件系统格式,如ext2、ext3、reiserfs、FAT、NTFS、iso9660等等,不同的磁盘分区、光盘或其它存储设备都有不同的文件系统格式,然而这些文件系统都可以mount到某个目录下,使我们看到一个统一的目录树,各种文件系统上的目录和文件我们用ls命令看起来是一样的,读写操作用起来也都是一样的,这是怎么做到的呢?

Linux内核在各种不同的文件系统格式之上做了一个抽象层,使得文件、目录、读写访问等概念成为抽象层的概念,因此各种文件系统看起来用起来都一样,这个抽象层称为虚拟文件系统(VFS,VirtualFilesystem)。


dup/dup2
在这里插入图片描述
dup和dup2都可用来复制一个现存的文件描述符,使两个文件描述符指向同一个file结构体。如果两个文件描述符指向同一个file结构体,File Status Flag和读写位置只保存一份在file结构体中,并且file结构体的引用计数是2,引用计数为0的时候file结构体释放。如下图:
在这里插入图片描述
不管是一个进程open同一file文件两次,还是两个进程open同一个file文件,都会产生两个file结构体,但vnode是同一个,inode也是一个。

如果两次open同一文件得到两个文件描述符,则每个描述符对应一个不同的file结构体,可以有不同的File Status Flag和读写位置。请注意区分这两种情况。如下图:
在这里插入图片描述
源码:dup_test.c

#include <unistd.h>
#include <fcntl.h>
#include <stdio.h>

int main(int argc, char *argv[])
{
	int fd, copyfd;
	fd = open("./log.txt", O_RDWR);
	/*复制fd*/
	copyfd = dup(fd);
	char buf1[] = "hello ";
	char buf2[] = "world!";
	/*往fd文件写入内容*/
	if (write(fd, buf1, 6) != 6) {
		printf("write error!");
	}
	/*打印出fd和copyfd的偏移量,经过上面的写操作,都变成6了*/
	printf("%ld\n", lseek(fd, 0, SEEK_CUR));
	printf("%ld\n", lseek(copyfd, 0, SEEK_CUR));
	/*往copyfd写入内容*/
	if (write(copyfd, buf2, 6) != 6) {
		printf("write error!");
	}
	return 0;
}

重定向标准输出标准错误:

#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
int main(int argc, char**argv)
{
	int fd = open("./log", O_WRONLY | O_CREAT, 0755);
	dup2(fd, 1);
	dup2(fd, 2);
	/*这里记住一定要先重定向再关闭*/
	close(fd);
	printf("helloworld\n");
	puts("helloworld\n");
}

dup函数作用

猜你喜欢

转载自blog.csdn.net/Gsunshine24/article/details/88939162