From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 5030AC433EF for ; Mon, 3 Jan 2022 21:12:51 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229731AbiACVMu (ORCPT ); Mon, 3 Jan 2022 16:12:50 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:46996 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229677AbiACVMu (ORCPT ); Mon, 3 Jan 2022 16:12:50 -0500 Received: from zeniv-ca.linux.org.uk (zeniv-ca.linux.org.uk [IPv6:2607:5300:60:148a::1]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 8B556C061761; Mon, 3 Jan 2022 13:12:50 -0800 (PST) Received: from viro by zeniv-ca.linux.org.uk with local (Exim 4.94.2 #2 (Red Hat Linux)) id 1n4UdJ-00H1C4-0I; Mon, 03 Jan 2022 21:12:45 +0000 Date: Mon, 3 Jan 2022 21:12:44 +0000 From: Al Viro To: Jann Horn Cc: Jens Axboe , Stefan Roesch , Linus Torvalds , io-uring , linux-fsdevel , Pavel Begunkov Subject: Re: [PATCH v7 0/3] io_uring: add getdents64 support Message-ID: References: <20211221164004.119663-1-shr@fb.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: Sender: Al Viro Precedence: bulk List-ID: X-Mailing-List: io-uring@vger.kernel.org On Mon, Jan 03, 2022 at 08:03:51AM +0100, Jann Horn wrote: > io_prep_rw() grabs file->f_pos; then later, io_read() calls > io_iter_do_read() (which will fail with -EINVAL), and then the error > path goes through kiocb_done(), which writes the position back to > req->file->f_pos. So I think the following race might work: Why does it touch ->f_pos on failure, anyway? It's a bug, plain and simple; note that read(2) and write(2) are explicitly requested to leave IO position alone if they return an error. See e.g. fs/read_write.c:ksys_read() - ret = vfs_read(f.file, buf, count, ppos); if (ret >= 0 && ppos) f.file->f_pos = pos; fdput_pos(f); Position update happens only on success (and only for non-stream files, at that). No matter how special io-uring is (it's not covered by POSIX, for obvious reasons), this is simply wrong, directories or no directories.