最近我遇到了这个练习:
在Linux C语言程序中给出这一系列调用:
fd = open("f123", O_RDWRT | O_CREAT, 0777);
lseek(fd, 0x1000000L, 0);
write(fd, &fd, sizeof(int));
绘制由这些操作修改的文件系统数据结构和磁盘块,考虑4 KB的块大小和4字节的索引块指针。
对于第一个系统调用(open
),我意识到它是如何工作的,并以这种方式对其进行了模式化:
现在,跳过 draw 部分(我意识到这会很难回答),我想了解lseek
和write
的工作原理inode和索引块(无论它们是什么)。
我试图确定lseek
计算正确的inode(因为块大小已知),但仍然不知道它实际上是如何工作的。
答案 0 :(得分:2)
在Linux中,这些系统调用与虚拟文件系统(VFS)交互。 VFS构建了对真实文件系统的抽象,它定义了一些有用的数据结构来组织文件系统。
以下是file
struct:
struct file {
// ... other attributes
struct path f_path;
#define f_dentry f_path.dentry
#define f_vfsmnt f_path.mnt
const struct file_operations *f_op;
};
struct file_operations {
// ... other operations
struct module *owner;
loff_t (*llseek) (struct file *, loff_t, int);
ssize_t (*read) (struct file *, char __user *, size_t, loff_t *);
ssize_t (*write) (struct file *, const char __user *, size_t, loff_t *);
}
这些对象都有一个操作列表字段。 VFS定义了这些操作,并且底层文件系统实现了这些操作或使用VFS提供的一般实现。
Syscall open()
创建文件对象,其他系统调用如lseek()
只需获取file
对象(通过Fd)并调用操作列表中的相应函数,如write()
将调用f->f_op->write(f, ...)
,然后文件系统可以按照file -> d_entry -> inode
路径访问磁盘上的文件。