From patchwork Fri Aug 23 20:08:15 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: David Howells X-Patchwork-Id: 13775937 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 kanga.kvack.org (kanga.kvack.org [205.233.56.17]) by smtp.lore.kernel.org (Postfix) with ESMTP id AB94FC531DC for ; Fri, 23 Aug 2024 20:09:18 +0000 (UTC) Received: by kanga.kvack.org (Postfix) id 430176B0369; Fri, 23 Aug 2024 16:09:18 -0400 (EDT) Received: by kanga.kvack.org (Postfix, from userid 40) id 3B6406B036A; Fri, 23 Aug 2024 16:09:18 -0400 (EDT) X-Delivered-To: int-list-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix, from userid 63042) id 208B16B0367; Fri, 23 Aug 2024 16:09:18 -0400 (EDT) X-Delivered-To: linux-mm@kvack.org Received: from relay.hostedemail.com (smtprelay0014.hostedemail.com [216.40.44.14]) by kanga.kvack.org (Postfix) with ESMTP id 0102B6B0364 for ; Fri, 23 Aug 2024 16:09:17 -0400 (EDT) Received: from smtpin17.hostedemail.com (a10.router.float.18 [10.200.18.1]) by unirelay01.hostedemail.com (Postfix) with ESMTP id B2F031C022B for ; Fri, 23 Aug 2024 20:09:17 +0000 (UTC) X-FDA: 82484599554.17.6EDC6E8 Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.133.124]) by imf28.hostedemail.com (Postfix) with ESMTP id 15320C0018 for ; Fri, 23 Aug 2024 20:09:15 +0000 (UTC) Authentication-Results: imf28.hostedemail.com; dkim=pass header.d=redhat.com header.s=mimecast20190719 header.b=WTP+BMBu; spf=pass (imf28.hostedemail.com: domain of dhowells@redhat.com designates 170.10.133.124 as permitted sender) smtp.mailfrom=dhowells@redhat.com; dmarc=pass (policy=none) header.from=redhat.com ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=hostedemail.com; s=arc-20220608; t=1724443691; h=from:from:sender:reply-to:subject:subject:date:date: message-id:message-id:to:to:cc:cc:mime-version:mime-version: content-type:content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references:dkim-signature; bh=QRzYATgp/3eeTZkiFzTxq5j7styCnaCIZoOTDKL0BZk=; b=dUeoWlA62XcERNZcHJMxtcaYiLLi69Rnd9bYW3iz2dp5Lxt0Pu1cOS3aG7GZuu0wPwuN0m t2h3WDo3iLvfI1y8XMWFcM2b/LGQsfRh5SrgicYoC/5BQtVl2+6uABLGvkEHBTeKK9yZ5J aUC2KpCjdKqe9lZHbr0FQRFvfsp4ouI= ARC-Authentication-Results: i=1; imf28.hostedemail.com; dkim=pass header.d=redhat.com header.s=mimecast20190719 header.b=WTP+BMBu; spf=pass (imf28.hostedemail.com: domain of dhowells@redhat.com designates 170.10.133.124 as permitted sender) smtp.mailfrom=dhowells@redhat.com; dmarc=pass (policy=none) header.from=redhat.com ARC-Seal: i=1; s=arc-20220608; d=hostedemail.com; t=1724443691; a=rsa-sha256; cv=none; b=E/yeLbZkKxCYPNOxGfINNCYHsHfJIXyB4zMfo0Ws9lD3UGqFX0RQKtZuIlac0kLgH761xg Kth7ClO+xugA0RPpqh3LHmkAG6VugG4/6HkuL88oGNjU6wdEC6ty/YW6d+LSbqIockD5HJ bDWD7HXHCsALJFtI5CNd15hHi4P51gY= DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1724443755; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=QRzYATgp/3eeTZkiFzTxq5j7styCnaCIZoOTDKL0BZk=; b=WTP+BMBub34R9eWqfAwTSs+LGYdzIyABbxeRcnF4SYsox3QsVL/omeWVHgNenE0gGpPd74 8skG6UrfIHOu8Dv92g8KBimmz1cnUHOXkC4W63ahbw3vgzKWjSmlVI0YdpzU9bTgEYELln 9Fn8Oajp+NL7wepVfUtRZobYALHk/4U= Received: from mx-prod-mc-01.mail-002.prod.us-west-2.aws.redhat.com (ec2-54-186-198-63.us-west-2.compute.amazonaws.com [54.186.198.63]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.3, cipher=TLS_AES_256_GCM_SHA384) id us-mta-146--Hm1Ra-bNfy8Awu75_bZog-1; Fri, 23 Aug 2024 16:09:13 -0400 X-MC-Unique: -Hm1Ra-bNfy8Awu75_bZog-1 Received: from mx-prod-int-03.mail-002.prod.us-west-2.aws.redhat.com (mx-prod-int-03.mail-002.prod.us-west-2.aws.redhat.com [10.30.177.12]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by mx-prod-mc-01.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTPS id CE8F51955BF7; Fri, 23 Aug 2024 20:09:10 +0000 (UTC) Received: from warthog.procyon.org.uk.com (unknown [10.42.28.30]) by mx-prod-int-03.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTP id 76A741954B3E; Fri, 23 Aug 2024 20:09:06 +0000 (UTC) From: David Howells To: Christian Brauner , Steve French Cc: David Howells , Pankaj Raghav , Paulo Alcantara , Jeff Layton , Matthew Wilcox , netfs@lists.linux.dev, linux-afs@lists.infradead.org, linux-cifs@vger.kernel.org, linux-nfs@vger.kernel.org, ceph-devel@vger.kernel.org, v9fs@lists.linux.dev, linux-erofs@lists.ozlabs.org, linux-fsdevel@vger.kernel.org, linux-mm@kvack.org, linux-kernel@vger.kernel.org, Christian Brauner Subject: [PATCH 7/9] netfs, cifs: Fix handling of short DIO read Date: Fri, 23 Aug 2024 21:08:15 +0100 Message-ID: <20240823200819.532106-8-dhowells@redhat.com> In-Reply-To: <20240823200819.532106-1-dhowells@redhat.com> References: <20240823200819.532106-1-dhowells@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 3.0 on 10.30.177.12 X-Stat-Signature: 9cu7x7x9faua5pd7zp3yxm7xg3yn7fnp X-Rspam-User: X-Rspamd-Queue-Id: 15320C0018 X-Rspamd-Server: rspam02 X-HE-Tag: 1724443755-156506 X-HE-Meta: U2FsdGVkX19bTmEcQ9smsDsbhZ/z/xGKFdvF/7gCR9z+1rs+oZUt3G1ouXhDVIfvUqXhqH0RZNCG3J6Z8Pb75M6LbLeH5XaRNIceaH/8CHRxtPgPb8D7j1MS0lzpqYKllWSsCenrK18cL+P4zhwTmPhU8oPW8Dwt8KIdycdyUhVGvqa8YZZi0ikecK+Rg9YnrWgQvmLMBvcRSpaqKQqnZoi435NmLG7T1FysJjVH4xrRy/Cz/MMQCXR7eIplyZRvdhucPPsTt2EVJcBDT3Eg7wQ+gEIqw6PX0wFtS4VATLZTicpxMrRdZAN/x+xACwhtfpblOFzpYXiF3wZdT1w2px/m0/1Tq+i5m78pI231U0GK3XwmPUaxriQfrtzQ4bJIr6atP3d33dlARV7l+HOU4Yl21Bv3pKiZFM1D+kEjr4iMa4SvCIc0saITRFF3QgNOb2AtY+bhwpCDh9jsbxSZ3o39U0fmullk+UidwFjthkPcwIc0gsPm0QHDjCMbctYmc6TSezCawKVZnOYh0hTVTtvrhteRSJeVugkIVspBJI/u3rfHUzYLs6H3w0Vh2V6ZhndUK4p1fCN5RKvZx9gqlFl77AqqMqvdvjob1wMRvxHnUb1BRGBy8nRNUgRwlQ5ddZgdHUF1CCjQaaXs1ccYG7V1x1CJIW8LxuWMILiK23V8Qe/9mJ87noKmt4er10Ef+GF9nOUed0rqSknb6etyEfDGFmx7icR+/CkHSCVPq5LoxtSJXkDJTo8nRdFGOP+Cr1FB3KUqkn/3T/KZeSJTmsR/7sH1yLFyjCklrM8U/L31COWTv8/z7HnfS/vf7rF9Tt/Xi3l1QEco7fMhzoiBZvmXeWksGdnGKaJPP7pmUAUfBn/n1dp4dkoJhVGDsI/4FHPmmP0JdHTgUVrtArr6b/d5M1IpH1EYos/Dt3q0XDp8FgVQHI4Vv3DigZNWyE4sM+iLfiLPa99NNGJIzur wlORInw+ 7Y0QqlqohNA8RddB6bti0SGhNCoHj3mNQQVRH9/3nhU6YTav/0Ik5k9b4bAbAaBXZbh/Wm8MjBot5f2JaRmC0E5t1sfRykXJtrmQF2Se7OZAOdMI485g5ZbqC9pSS7UHcLtWCSjpSTOJIgRWslSSLGimIzV89yaC+7/DAZD7te4OYoUIVpyV2PHi1yV1PhrBwxvsdC46JkX41N0CnIj06BHcPU2NY84uvr9E+YjhKjTGJx4onBgT1pd8faHWhs7c52a+7wZP0Xzt7z+URfcImF1HkDmK053NhgFwtxDZuSuwdDV9fQvCYpmZKi4QgObcQAol6pzA5GYvXEDDgKVYGz6wTSb/rpXfYktSotpnf5Bdpse2QWPRPctn2srMGoaNTKsaRs2m/vNog+MHaBVRdBKGZvmIQIOJVPPk1QOjVX2rEWgcuyRl3b3koE70kUpniBRms/vW7v3xBS1H06wJPUMXOv/nwq3lIZP5g X-Bogosity: Ham, tests=bogofilter, spamicity=0.000000, version=1.2.4 Sender: owner-linux-mm@kvack.org Precedence: bulk X-Loop: owner-majordomo@kvack.org List-ID: List-Subscribe: List-Unsubscribe: Short DIO reads, particularly in relation to cifs, are not being handled correctly by cifs and netfslib. This can be tested by doing a DIO read of a file where the size of read is larger than the size of the file. When it crosses the EOF, it gets a short read and this gets retried, and in the case of cifs, the retry read fails, with the failure being translated to ENODATA. Fix this by the following means: (1) Add a flag, NETFS_SREQ_HIT_EOF, for the filesystem to set when it detects that the read did hit the EOF. (2) Make the netfslib read assessment stop processing subrequests when it encounters one with that flag set. (3) Return rreq->transferred, the accumulated contiguous amount read to that point, to userspace for a DIO read. (4) Make cifs set the flag and clear the error if the read RPC returned ENODATA. (5) Make cifs set the flag and clear the error if a short read occurred without error and the read-to file position is now at the remote inode size. Fixes: 69c3c023af25 ("cifs: Implement netfslib hooks") Signed-off-by: David Howells Link: https://lore.kernel.org/r/20240822220650.318774-3-dhowells@redhat.com cc: Steve French cc: Paulo Alcantara cc: Jeff Layton cc: linux-cifs@vger.kernel.org cc: netfs@lists.linux.dev cc: linux-fsdevel@vger.kernel.org Signed-off-by: Christian Brauner --- fs/netfs/io.c | 17 +++++++++++------ fs/smb/client/smb2pdu.c | 13 +++++++++---- include/linux/netfs.h | 1 + 3 files changed, 21 insertions(+), 10 deletions(-) diff --git a/fs/netfs/io.c b/fs/netfs/io.c index 3303b515b536..943128507af5 100644 --- a/fs/netfs/io.c +++ b/fs/netfs/io.c @@ -368,7 +368,8 @@ static void netfs_rreq_assess_dio(struct netfs_io_request *rreq) if (subreq->error || subreq->transferred == 0) break; transferred += subreq->transferred; - if (subreq->transferred < subreq->len) + if (subreq->transferred < subreq->len || + test_bit(NETFS_SREQ_HIT_EOF, &subreq->flags)) break; } @@ -503,7 +504,8 @@ void netfs_subreq_terminated(struct netfs_io_subrequest *subreq, subreq->error = 0; subreq->transferred += transferred_or_error; - if (subreq->transferred < subreq->len) + if (subreq->transferred < subreq->len && + !test_bit(NETFS_SREQ_HIT_EOF, &subreq->flags)) goto incomplete; complete: @@ -782,10 +784,13 @@ int netfs_begin_read(struct netfs_io_request *rreq, bool sync) TASK_UNINTERRUPTIBLE); ret = rreq->error; - if (ret == 0 && rreq->submitted < rreq->len && - rreq->origin != NETFS_DIO_READ) { - trace_netfs_failure(rreq, NULL, ret, netfs_fail_short_read); - ret = -EIO; + if (ret == 0) { + if (rreq->origin == NETFS_DIO_READ) { + ret = rreq->transferred; + } else if (rreq->submitted < rreq->len) { + trace_netfs_failure(rreq, NULL, ret, netfs_fail_short_read); + ret = -EIO; + } } } else { /* If we decrement nr_outstanding to 0, the ref belongs to us. */ diff --git a/fs/smb/client/smb2pdu.c b/fs/smb/client/smb2pdu.c index d80107d1ba9e..9829784e8ec5 100644 --- a/fs/smb/client/smb2pdu.c +++ b/fs/smb/client/smb2pdu.c @@ -4507,6 +4507,7 @@ static void smb2_readv_callback(struct mid_q_entry *mid) { struct cifs_io_subrequest *rdata = mid->callback_data; + struct netfs_inode *ictx = netfs_inode(rdata->rreq->inode); struct cifs_tcon *tcon = tlink_tcon(rdata->req->cfile->tlink); struct TCP_Server_Info *server = rdata->server; struct smb2_hdr *shdr = @@ -4600,11 +4601,15 @@ smb2_readv_callback(struct mid_q_entry *mid) rdata->got_bytes); if (rdata->result == -ENODATA) { - /* We may have got an EOF error because fallocate - * failed to enlarge the file. - */ - if (rdata->subreq.start < rdata->subreq.rreq->i_size) + __set_bit(NETFS_SREQ_HIT_EOF, &rdata->subreq.flags); + rdata->result = 0; + } else { + if (rdata->got_bytes < rdata->actual_len && + rdata->subreq.start + rdata->subreq.transferred + rdata->got_bytes == + ictx->remote_i_size) { + __set_bit(NETFS_SREQ_HIT_EOF, &rdata->subreq.flags); rdata->result = 0; + } } trace_smb3_rw_credits(rreq_debug_id, subreq_debug_index, rdata->credits.value, server->credits, server->in_flight, diff --git a/include/linux/netfs.h b/include/linux/netfs.h index 983816608f15..c47443e7a97e 100644 --- a/include/linux/netfs.h +++ b/include/linux/netfs.h @@ -198,6 +198,7 @@ struct netfs_io_subrequest { #define NETFS_SREQ_NEED_RETRY 9 /* Set if the filesystem requests a retry */ #define NETFS_SREQ_RETRYING 10 /* Set if we're retrying */ #define NETFS_SREQ_FAILED 11 /* Set if the subreq failed unretryably */ +#define NETFS_SREQ_HIT_EOF 12 /* Set if we hit the EOF */ }; enum netfs_io_origin {