vfs: atomic f_pos accesses as per POSIX
authorLinus Torvalds <torvalds@linux-foundation.org>
Mon, 3 Mar 2014 17:36:58 +0000 (09:36 -0800)
committerAl Viro <viro@zeniv.linux.org.uk>
Mon, 10 Mar 2014 15:44:41 +0000 (11:44 -0400)
commit9c225f2655e36a470c4f58dbbc99244c5fc7f2d4
tree7cb89dbc82ee1b533ff2d097fed6a4248374bd4b
parent1b56e98990bcdbb20b9fab163654b9315bf158e8
vfs: atomic f_pos accesses as per POSIX

Our write() system call has always been atomic in the sense that you get
the expected thread-safe contiguous write, but we haven't actually
guaranteed that concurrent writes are serialized wrt f_pos accesses, so
threads (or processes) that share a file descriptor and use "write()"
concurrently would quite likely overwrite each others data.

This violates POSIX.1-2008/SUSv4 Section XSI 2.9.7 that says:

 "2.9.7 Thread Interactions with Regular File Operations

  All of the following functions shall be atomic with respect to each
  other in the effects specified in POSIX.1-2008 when they operate on
  regular files or symbolic links: [...]"

and one of the effects is the file position update.

This unprotected file position behavior is not new behavior, and nobody
has ever cared.  Until now.  Yongzhi Pan reported unexpected behavior to
Michael Kerrisk that was due to this.

This resolves the issue with a f_pos-specific lock that is taken by
read/write/lseek on file descriptors that may be shared across threads
or processes.

Reported-by: Yongzhi Pan <panyongzhi@gmail.com>
Reported-by: Michael Kerrisk <mtk.manpages@gmail.com>
Cc: Al Viro <viro@zeniv.linux.org.uk>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
fs/file_table.c
fs/namei.c
fs/open.c
fs/read_write.c
include/linux/file.h
include/linux/fs.h