Reputation: 1128
Lately I faced this excercise:
Given this sequence of system calls in a Linux C language program:
fd = open("f123", O_RDWRT | O_CREAT, 0777);
lseek(fd, 0x1000000L, 0);
write(fd, &fd, sizeof(int));
draw the file system data structures and disk blocks that are modified by these operations, considering a 4 KByte block size, and index block pointers of 4 bytes.
For the first system call (open
) I realized how it works and schematized it in this way:
Now, skipping the draw part (I realize it would make difficult to answer), I'd like to understand how lseek
and write
works in term of inodes and index blocks (whatever they are).
I tried figuring that lseek
computes the correct inode (as block size is known), but still no clue on how it actually works.
Upvotes: 3
Views: 1587
Reputation: 66
In Linux, these system calls interact with Virtual File System(VFS). VFS builds an abstraction over real filesystems, it defines some useful data structures to organize filesystem.
Here are snippets from 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 *);
}
These objects all has an operation list field. VFS defines these operations and underlaying filesystems implement these operations or use general implementations provided by VFS.
Syscall open()
creates the file object, other syscalls like lseek()
simply get file
object (through Fd) and call the corresponding function in the operation list, like write()
will call f->f_op->write(f, ...)
, then filesystem may follow the file -> d_entry -> inode
path to access file on disk.
Upvotes: 2