Search code examples
clinux-kernellinux-device-driverread-write

Reason why use loff_t *offp instead of direct filp->f_pos usage


In following functions, taken from LDD:

ssize_t read(struct file *filp, char __user *buff, size_t count, loff_t *offp);
ssize_t write(struct file *filp, const char __user *buff, size_t count, loff_t *offp);

Why there is the need of loff_t *offp? Can't I use directly filp to update f_pos?

Moreover in page 54 the author says:

Read and write should update a position using the pointer they receive as the last argument instead of acting on filp->f_pos directly. The one exception to this...

OK, so it's better to use the offp pointer, but why?


Solution

  • filp->f_pos is current pointer position in file, whereas offp is where user does access to file. You advance file pointer on successful read/write operation, if you failed you should not change file pointer. Kernel does it itself, if you successfully did read/write it will change filp->f_pos to offp. Citing LDD3:

    Whatever the amount of data the methods transfer, they should generally update the file position at *offp to represent the current file position after successful completion of the system call. The kernel then propagates the file position change back into the file structure when appropriate.