From patchwork Wed Nov 4 16:16:22 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881479 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id BB528921 for ; Wed, 4 Nov 2020 16:27:04 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 889C2206D9 for ; Wed, 4 Nov 2020 16:27:04 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="kONCFN3K" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731106AbgKDQ1E (ORCPT ); Wed, 4 Nov 2020 11:27:04 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36086 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728999AbgKDQ1D (ORCPT ); Wed, 4 Nov 2020 11:27:03 -0500 Received: from mail-qt1-x844.google.com (mail-qt1-x844.google.com [IPv6:2607:f8b0:4864:20::844]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 54FFEC0613D3 for ; Wed, 4 Nov 2020 08:27:03 -0800 (PST) Received: by mail-qt1-x844.google.com with SMTP id r8so12562512qtp.13 for ; Wed, 04 Nov 2020 08:27:03 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=iVOPQh/Nw9au0O2zbDnw8gr6il9f7JgK6I5cvBRdmLQ=; b=kONCFN3KdretUHUraqryE4iv2IhWxZN4rCHMJ33daWrcT5w5IX76WWufUMufpCGXJL F7YeA9C4zXeHkV6ERr5i1svwramXESH+vUgnsy6keVQm9yMQ0aLK3F4x3rmnVdw3CsgC 82IeyOG0AwQCDa2wDcgR56O11tXFBSjyYAUJdIF9zO5LkkLN0CixeXNuEy/EHZNQRysJ H6L3kvG1qUax16rrLlvKNXk+AmCfcQ+EYHg+yF82mcPsRUjczNoIt5/hlHsidzUw9NKK 2+4Ki9cHcwncjjoZCHsPLFflPOSH1N0M7ZmAYjz9yb7ZedcwCfZj5Mp3YDx1LYD1VPbP IU2w== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=iVOPQh/Nw9au0O2zbDnw8gr6il9f7JgK6I5cvBRdmLQ=; b=fmhRLKlQo6sprSzFu9nY8pdwPZR76SnMICHJmMP4hLSvT8fwFkv1He02GzOJ9rm0VT b9j3GJSljfzWFQtOKTs3oSOAdDximLPiSaIyJ4dbutMzjf9a9iUnl+8PyveiT0R8vtm4 aYrEayE1jkyptDiNUmtJnuCLmS7+3FMhFr0CkV6q6RclLpEK5xtwz96hx0Zt+fDneVC3 olOr7joPv5VHjlvn1a5qf7NmtUMQkQQzCkkCZt/g9MO74gVYIFY1UflakDsoEV8nH9LS RGQcStIVmPhe97J3JwtMFaGKXaZAIgl5f/Ak0ZteRpnEFs6wkOVxmrDcHj0+IPqb6Qu3 tecA== X-Gm-Message-State: AOAM532bMHk7gaB7ysq85NkUU6wIxo6qfEmbl0Xb6gNHasd5+weHTkBL Gq5Nyqwp6WzH69tr68SyVgrvR25azQbj X-Google-Smtp-Source: ABdhPJwdVrEOMYwmRma9aqDCzE/vyfXvWVVUc5O1zZCO8ZT+HUQSsWrMBSNx6F2YehcuQ5dcKj55CQ== X-Received: by 2002:ac8:6752:: with SMTP id n18mr2325975qtp.204.1604507222141; Wed, 04 Nov 2020 08:27:02 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.00 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:01 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 01/17] NFS: Ensure contents of struct nfs_open_dir_context are consistent Date: Wed, 4 Nov 2020 11:16:22 -0500 Message-Id: <20201104161638.300324-2-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-1-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust Ensure that the contents of struct nfs_open_dir_context are consistent by setting them under the file->f_lock from a private copy (that is known to be consistent). Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 72 +++++++++++++++++++++++++++++++--------------------- 1 file changed, 43 insertions(+), 29 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 4e011adaf967..67d8595cd6e5 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -144,20 +144,23 @@ struct nfs_cache_array { struct nfs_cache_array_entry array[]; }; -typedef struct { +typedef struct nfs_readdir_descriptor { struct file *file; struct page *page; struct dir_context *ctx; unsigned long page_index; - u64 *dir_cookie; + u64 dir_cookie; u64 last_cookie; + u64 dup_cookie; loff_t current_index; loff_t prev_index; unsigned long dir_verifier; unsigned long timestamp; unsigned long gencount; + unsigned long attr_gencount; unsigned int cache_entry_index; + signed char duped; bool plus; bool eof; } nfs_readdir_descriptor_t; @@ -273,7 +276,7 @@ int nfs_readdir_search_for_pos(struct nfs_cache_array *array, nfs_readdir_descri } index = (unsigned int)diff; - *desc->dir_cookie = array->array[index].cookie; + desc->dir_cookie = array->array[index].cookie; desc->cache_entry_index = index; return 0; out_eof: @@ -298,33 +301,32 @@ int nfs_readdir_search_for_cookie(struct nfs_cache_array *array, nfs_readdir_des int status = -EAGAIN; for (i = 0; i < array->size; i++) { - if (array->array[i].cookie == *desc->dir_cookie) { + if (array->array[i].cookie == desc->dir_cookie) { struct nfs_inode *nfsi = NFS_I(file_inode(desc->file)); - struct nfs_open_dir_context *ctx = desc->file->private_data; new_pos = desc->current_index + i; - if (ctx->attr_gencount != nfsi->attr_gencount || + if (desc->attr_gencount != nfsi->attr_gencount || !nfs_readdir_inode_mapping_valid(nfsi)) { - ctx->duped = 0; - ctx->attr_gencount = nfsi->attr_gencount; + desc->duped = 0; + desc->attr_gencount = nfsi->attr_gencount; } else if (new_pos < desc->prev_index) { - if (ctx->duped > 0 - && ctx->dup_cookie == *desc->dir_cookie) { + if (desc->duped > 0 + && desc->dup_cookie == desc->dir_cookie) { if (printk_ratelimit()) { pr_notice("NFS: directory %pD2 contains a readdir loop." "Please contact your server vendor. " "The file: %.*s has duplicate cookie %llu\n", desc->file, array->array[i].string.len, - array->array[i].string.name, *desc->dir_cookie); + array->array[i].string.name, desc->dir_cookie); } status = -ELOOP; goto out; } - ctx->dup_cookie = *desc->dir_cookie; - ctx->duped = -1; + desc->dup_cookie = desc->dir_cookie; + desc->duped = -1; } if (nfs_readdir_use_cookie(desc->file)) - desc->ctx->pos = *desc->dir_cookie; + desc->ctx->pos = desc->dir_cookie; else desc->ctx->pos = new_pos; desc->prev_index = new_pos; @@ -334,7 +336,7 @@ int nfs_readdir_search_for_cookie(struct nfs_cache_array *array, nfs_readdir_des } if (array->eof_index >= 0) { status = -EBADCOOKIE; - if (*desc->dir_cookie == array->last_cookie) + if (desc->dir_cookie == array->last_cookie) desc->eof = true; } out: @@ -349,7 +351,7 @@ int nfs_readdir_search_array(nfs_readdir_descriptor_t *desc) array = kmap(desc->page); - if (*desc->dir_cookie == 0) + if (desc->dir_cookie == 0) status = nfs_readdir_search_for_pos(array, desc); else status = nfs_readdir_search_for_cookie(array, desc); @@ -801,7 +803,6 @@ int nfs_do_filldir(nfs_readdir_descriptor_t *desc) int i = 0; int res = 0; struct nfs_cache_array *array = NULL; - struct nfs_open_dir_context *ctx = file->private_data; array = kmap(desc->page); for (i = desc->cache_entry_index; i < array->size; i++) { @@ -814,22 +815,22 @@ int nfs_do_filldir(nfs_readdir_descriptor_t *desc) break; } if (i < (array->size-1)) - *desc->dir_cookie = array->array[i+1].cookie; + desc->dir_cookie = array->array[i+1].cookie; else - *desc->dir_cookie = array->last_cookie; + desc->dir_cookie = array->last_cookie; if (nfs_readdir_use_cookie(file)) - desc->ctx->pos = *desc->dir_cookie; + desc->ctx->pos = desc->dir_cookie; else desc->ctx->pos++; - if (ctx->duped != 0) - ctx->duped = 1; + if (desc->duped != 0) + desc->duped = 1; } if (array->eof_index >= 0) desc->eof = true; kunmap(desc->page); dfprintk(DIRCACHE, "NFS: nfs_do_filldir() filling ended @ cookie %Lu; returning = %d\n", - (unsigned long long)*desc->dir_cookie, res); + (unsigned long long)desc->dir_cookie, res); return res; } @@ -851,10 +852,9 @@ int uncached_readdir(nfs_readdir_descriptor_t *desc) struct page *page = NULL; int status; struct inode *inode = file_inode(desc->file); - struct nfs_open_dir_context *ctx = desc->file->private_data; dfprintk(DIRCACHE, "NFS: uncached_readdir() searching for cookie %Lu\n", - (unsigned long long)*desc->dir_cookie); + (unsigned long long)desc->dir_cookie); page = alloc_page(GFP_HIGHUSER); if (!page) { @@ -863,9 +863,9 @@ int uncached_readdir(nfs_readdir_descriptor_t *desc) } desc->page_index = 0; - desc->last_cookie = *desc->dir_cookie; + desc->last_cookie = desc->dir_cookie; desc->page = page; - ctx->duped = 0; + desc->duped = 0; status = nfs_readdir_xdr_to_array(desc, page, inode); if (status < 0) @@ -894,7 +894,6 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) nfs_readdir_descriptor_t my_desc = { .file = file, .ctx = ctx, - .dir_cookie = &dir_ctx->dir_cookie, .plus = nfs_use_readdirplus(inode, ctx), }, *desc = &my_desc; @@ -915,13 +914,20 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) if (res < 0) goto out; + spin_lock(&file->f_lock); + desc->dir_cookie = dir_ctx->dir_cookie; + desc->dup_cookie = dir_ctx->dup_cookie; + desc->duped = dir_ctx->duped; + desc->attr_gencount = dir_ctx->attr_gencount; + spin_unlock(&file->f_lock); + do { res = readdir_search_pagecache(desc); if (res == -EBADCOOKIE) { res = 0; /* This means either end of directory */ - if (*desc->dir_cookie && !desc->eof) { + if (desc->dir_cookie && !desc->eof) { /* Or that the server has 'lost' a cookie */ res = uncached_readdir(desc); if (res == 0) @@ -946,6 +952,14 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) if (res < 0) break; } while (!desc->eof); + + spin_lock(&file->f_lock); + dir_ctx->dir_cookie = desc->dir_cookie; + dir_ctx->dup_cookie = desc->dup_cookie; + dir_ctx->duped = desc->duped; + dir_ctx->attr_gencount = desc->attr_gencount; + spin_unlock(&file->f_lock); + out: if (res > 0) res = 0; From patchwork Wed Nov 4 16:16:23 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881481 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 22D6614B4 for ; Wed, 4 Nov 2020 16:27:06 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 0074E206D4 for ; Wed, 4 Nov 2020 16:27:05 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="KH87ngbs" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731114AbgKDQ1F (ORCPT ); Wed, 4 Nov 2020 11:27:05 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36092 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728999AbgKDQ1E (ORCPT ); Wed, 4 Nov 2020 11:27:04 -0500 Received: from mail-qt1-x841.google.com (mail-qt1-x841.google.com [IPv6:2607:f8b0:4864:20::841]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 9D1D5C0613D3 for ; Wed, 4 Nov 2020 08:27:04 -0800 (PST) Received: by mail-qt1-x841.google.com with SMTP id t5so4017512qtp.2 for ; Wed, 04 Nov 2020 08:27:04 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=Za2MbFKOf0ZIVMwa6n7rZb8vFe0Gn0ItEgc063hxwd8=; b=KH87ngbsXicGB2rpmOuSdMdXu9J0t0W2LG0/kHRfzXoWe3FpTis7WsYw4IMx7DSOGV FqmJdGshWQs33aEmBWgrcauyfdCRoPB/rNy9DoDLbEcMgtfjGlWp5daOs1dm1HHEG/No LKjk/xZqAKkxrCxdRTkQSYjk5n/AYXxNhKA9b/rZeM9Lqe4dfD+7vM+mv3Zu1gm9Hal+ wdMWKU7xaUPcyybT11AKC1Ze2N6fGvEE9NzIim9KhOMbG+zRfhMRAxVpx2BSAyOhnjHF 9jt7Q8DDFbgVXlKPGAydtFzzCXP2V0Lq8phofCzwIcv5CJBQKPYAB8VBq9TpuWAf36Gm ZE/A== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=Za2MbFKOf0ZIVMwa6n7rZb8vFe0Gn0ItEgc063hxwd8=; b=RQlFWS+1I3+aF4Nf8PfclX8bD3VUyZ5/simi61gE4pB4D/UN25ymiJcXfQLF7ruwa9 5x15RqwkqzYb0+/2WDHYUt4Ex1h7ERq1s/rjaPsIQvIBHzp1DwcuqsXKm7IYXZJ5JKxM XePfvxctpuvaEsT83VQaew3DcVcStd7881bVjL8JYA7M0GJC3WHGNkYVq0kip6cISmss YcXdBrfeP3pJkzx5mJdeLnivClKWVPE2LmPZBn2OZBmjy3lAzGTYC4nFU1Ju7SKN9LYs AKZNJtomRH5qm6DJGRgtMAcm89oM7qDimMts6hzAx/e3xpzNPuKo27fXPLtWd2wNSsi+ fOnw== X-Gm-Message-State: AOAM532DpFamwVlmPzS0nb3J6sVTz43Jlk7Dy7DP0ZpTpwOD9pBPktHD 2R9E2tzXlVSFJF8J+pWOzyGt6yM49rgl X-Google-Smtp-Source: ABdhPJxZcZnFrn9k84546CHQchTO+t8kLkLzjjUbe0kfYbQket5Bv7o8F8I64Tr9gVw2z+gSVOsZCQ== X-Received: by 2002:ac8:41d4:: with SMTP id o20mr9396491qtm.313.1604507223473; Wed, 04 Nov 2020 08:27:03 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.02 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:02 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 02/17] NFS: Clean up readdir struct nfs_cache_array Date: Wed, 4 Nov 2020 11:16:23 -0500 Message-Id: <20201104161638.300324-3-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-2-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust Since the 'eof_index' is only ever used as a flag, make it so. Also add a flag to detect if the page has been completely filled. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 66 ++++++++++++++++++++++++++++++++++++++-------------- 1 file changed, 49 insertions(+), 17 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 67d8595cd6e5..604ebe015387 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -138,9 +138,10 @@ struct nfs_cache_array_entry { }; struct nfs_cache_array { - int size; - int eof_index; u64 last_cookie; + unsigned int size; + unsigned char page_full : 1, + page_is_eof : 1; struct nfs_cache_array_entry array[]; }; @@ -172,7 +173,6 @@ void nfs_readdir_init_array(struct page *page) array = kmap_atomic(page); memset(array, 0, sizeof(struct nfs_cache_array)); - array->eof_index = -1; kunmap_atomic(array); } @@ -192,6 +192,17 @@ void nfs_readdir_clear_array(struct page *page) kunmap_atomic(array); } +static void nfs_readdir_array_set_eof(struct nfs_cache_array *array) +{ + array->page_is_eof = 1; + array->page_full = 1; +} + +static bool nfs_readdir_array_is_full(struct nfs_cache_array *array) +{ + return array->page_full; +} + /* * the caller is responsible for freeing qstr.name * when called by nfs_readdir_add_to_array, the strings will be freed in @@ -213,6 +224,23 @@ int nfs_readdir_make_qstr(struct qstr *string, const char *name, unsigned int le return 0; } +/* + * Check that the next array entry lies entirely within the page bounds + */ +static int nfs_readdir_array_can_expand(struct nfs_cache_array *array) +{ + struct nfs_cache_array_entry *cache_entry; + + if (array->page_full) + return -ENOSPC; + cache_entry = &array->array[array->size + 1]; + if ((char *)cache_entry - (char *)array > PAGE_SIZE) { + array->page_full = 1; + return -ENOSPC; + } + return 0; +} + static int nfs_readdir_add_to_array(struct nfs_entry *entry, struct page *page) { @@ -220,13 +248,11 @@ int nfs_readdir_add_to_array(struct nfs_entry *entry, struct page *page) struct nfs_cache_array_entry *cache_entry; int ret; - cache_entry = &array->array[array->size]; - - /* Check that this entry lies within the page bounds */ - ret = -ENOSPC; - if ((char *)&cache_entry[1] - (char *)page_address(page) > PAGE_SIZE) + ret = nfs_readdir_array_can_expand(array); + if (ret) goto out; + cache_entry = &array->array[array->size]; cache_entry->cookie = entry->prev_cookie; cache_entry->ino = entry->ino; cache_entry->d_type = entry->d_type; @@ -236,12 +262,21 @@ int nfs_readdir_add_to_array(struct nfs_entry *entry, struct page *page) array->last_cookie = entry->cookie; array->size++; if (entry->eof != 0) - array->eof_index = array->size; + nfs_readdir_array_set_eof(array); out: kunmap(page); return ret; } +static void nfs_readdir_page_set_eof(struct page *page) +{ + struct nfs_cache_array *array; + + array = kmap_atomic(page); + nfs_readdir_array_set_eof(array); + kunmap_atomic(array); +} + static inline int is_32bit_api(void) { @@ -270,7 +305,7 @@ int nfs_readdir_search_for_pos(struct nfs_cache_array *array, nfs_readdir_descri if (diff < 0) goto out_eof; if (diff >= array->size) { - if (array->eof_index >= 0) + if (array->page_is_eof) goto out_eof; return -EAGAIN; } @@ -334,7 +369,7 @@ int nfs_readdir_search_for_cookie(struct nfs_cache_array *array, nfs_readdir_des return 0; } } - if (array->eof_index >= 0) { + if (array->page_is_eof) { status = -EBADCOOKIE; if (desc->dir_cookie == array->last_cookie) desc->eof = true; @@ -566,7 +601,6 @@ int nfs_readdir_page_filler(nfs_readdir_descriptor_t *desc, struct nfs_entry *en struct xdr_stream stream; struct xdr_buf buf; struct page *scratch; - struct nfs_cache_array *array; unsigned int count = 0; int status; @@ -604,10 +638,8 @@ int nfs_readdir_page_filler(nfs_readdir_descriptor_t *desc, struct nfs_entry *en out_nopages: if (count == 0 || (status == -EBADCOOKIE && entry->eof != 0)) { - array = kmap(page); - array->eof_index = array->size; + nfs_readdir_page_set_eof(page); status = 0; - kunmap(page); } put_page(scratch); @@ -689,7 +721,7 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, status = 0; break; } - } while (array->eof_index < 0); + } while (!nfs_readdir_array_is_full(array)); nfs_readdir_free_pages(pages, array_size); out_release_array: @@ -825,7 +857,7 @@ int nfs_do_filldir(nfs_readdir_descriptor_t *desc) if (desc->duped != 0) desc->duped = 1; } - if (array->eof_index >= 0) + if (array->page_is_eof) desc->eof = true; kunmap(desc->page); From patchwork Wed Nov 4 16:16:24 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881483 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 18CD814B4 for ; Wed, 4 Nov 2020 16:27:07 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id E6090206D4 for ; Wed, 4 Nov 2020 16:27:06 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="KY/Ly0Hi" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1729744AbgKDQ1G (ORCPT ); Wed, 4 Nov 2020 11:27:06 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36096 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728999AbgKDQ1F (ORCPT ); Wed, 4 Nov 2020 11:27:05 -0500 Received: from mail-qk1-x744.google.com (mail-qk1-x744.google.com [IPv6:2607:f8b0:4864:20::744]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 9C6AAC0613D3 for ; Wed, 4 Nov 2020 08:27:05 -0800 (PST) Received: by mail-qk1-x744.google.com with SMTP id 12so15909650qkl.8 for ; Wed, 04 Nov 2020 08:27:05 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=uIT7c42oLJhGuQ4MC0Mb1wvuxjVAQj6q8C6vaQFmtk4=; b=KY/Ly0Hi6NaqdG30f1semQEZQ+ig0BkfaLHMconNvFHm8QwHjmGUIsYYUVwlbf8Ra7 RD2FLBArIL446DkXMrTSsA7BucqmcpC8nOGSJKLENLWlEZtebBTF8HrEca+Eyd/OhFzl 9z2Hd3bgbiHdj3Z4WGSv3aMiJ2APVrgWyE5uKY3ApmB3w+ekwvOrGeQbWTxoagFHPt3Z Y2BJTsGc8zGGzMHUvDAv1AkLCwbY8CvWBKL5sxT/Y+ojXP/vpknman0VDsSCN3EFCqk6 Y4h5Z0dCnscTYxAzE47wcIyVqlByElKRiPB/4VPQUjBTC8peOKuvN6ztrgHnQYpNeJaN TdsA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=uIT7c42oLJhGuQ4MC0Mb1wvuxjVAQj6q8C6vaQFmtk4=; b=JBPnO6URKIrSItUVVz+dmbKwo5FS8WhYHQKCTQrvZTMTw4RcWjDd0i6r4AcsT5X4Uh ZeQLplXsR50l/BotxxcoXkbLDk1krLmE/ZrXedZiHM8Pn6W75OTbiTWNQM+voYavJ5p2 G8vh4t3zQRCP0znTLxv60BJ2m9deyiL//wxVy4HG5IOkXrfHw7pKAjcCsWUtgZVEaih5 B5kO29ZgFV3qHQnAtXtwjLzlEvlGhyOqZo2kLUMA7K24uuii3oGEGbz2p/9a0bjSin1/ zGWsQFUhbzBhsdZ+LvXaA1YjSWq/Zy202kacfYJiZhUwieDEaazGkRQIafmzV3Y6Tgma XXVA== X-Gm-Message-State: AOAM533B7odrQGByV4ArTxpEvoZ9QlfhUGKfMN18t9Yghf1zpGJENH+Z OzN3v4mTQkwmCTGVKsBCIOLQUj5pzz3u X-Google-Smtp-Source: ABdhPJyEdl7/rcsu59YeOhubvflZQffn5s/tm5PTqU1BvLeoBPynTWiUFi/H3aLPzogAhigZWTVuEA== X-Received: by 2002:a37:9acb:: with SMTP id c194mr26297149qke.288.1604507224549; Wed, 04 Nov 2020 08:27:04 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.03 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:03 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 03/17] NFS: Clean up nfs_readdir_page_filler() Date: Wed, 4 Nov 2020 11:16:24 -0500 Message-Id: <20201104161638.300324-4-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-3-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust Clean up handling of the case where there are no entries in the readdir reply. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 39 ++++++++++++++++++--------------------- 1 file changed, 18 insertions(+), 21 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 604ebe015387..68acbde3f914 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -601,16 +601,12 @@ int nfs_readdir_page_filler(nfs_readdir_descriptor_t *desc, struct nfs_entry *en struct xdr_stream stream; struct xdr_buf buf; struct page *scratch; - unsigned int count = 0; int status; scratch = alloc_page(GFP_KERNEL); if (scratch == NULL) return -ENOMEM; - if (buflen == 0) - goto out_nopages; - xdr_init_decode_pages(&stream, &buf, xdr_pages, buflen); xdr_set_scratch_buffer(&stream, page_address(scratch), PAGE_SIZE); @@ -619,27 +615,27 @@ int nfs_readdir_page_filler(nfs_readdir_descriptor_t *desc, struct nfs_entry *en entry->label->len = NFS4_MAXLABELLEN; status = xdr_decode(desc, entry, &stream); - if (status != 0) { - if (status == -EAGAIN) - status = 0; + if (status != 0) break; - } - - count++; if (desc->plus) nfs_prime_dcache(file_dentry(desc->file), entry, desc->dir_verifier); status = nfs_readdir_add_to_array(entry, page); - if (status != 0) - break; - } while (!entry->eof); + } while (!status && !entry->eof); -out_nopages: - if (count == 0 || (status == -EBADCOOKIE && entry->eof != 0)) { - nfs_readdir_page_set_eof(page); + switch (status) { + case -EBADCOOKIE: + if (entry->eof) { + nfs_readdir_page_set_eof(page); + status = 0; + } + break; + case -ENOSPC: + case -EAGAIN: status = 0; + break; } put_page(scratch); @@ -714,14 +710,15 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, if (status < 0) break; + pglen = status; - status = nfs_readdir_page_filler(desc, &entry, pages, page, pglen); - if (status < 0) { - if (status == -ENOSPC) - status = 0; + if (pglen == 0) { + nfs_readdir_page_set_eof(page); break; } - } while (!nfs_readdir_array_is_full(array)); + + status = nfs_readdir_page_filler(desc, &entry, pages, page, pglen); + } while (!status && !nfs_readdir_array_is_full(array)); nfs_readdir_free_pages(pages, array_size); out_release_array: From patchwork Wed Nov 4 16:16:25 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881485 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 5826D921 for ; Wed, 4 Nov 2020 16:27:08 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 2EFCE206D9 for ; Wed, 4 Nov 2020 16:27:08 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="YXzs7v1q" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730821AbgKDQ1H (ORCPT ); Wed, 4 Nov 2020 11:27:07 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36102 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728999AbgKDQ1H (ORCPT ); Wed, 4 Nov 2020 11:27:07 -0500 Received: from mail-qk1-x741.google.com (mail-qk1-x741.google.com [IPv6:2607:f8b0:4864:20::741]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id DD35EC0613D3 for ; Wed, 4 Nov 2020 08:27:06 -0800 (PST) Received: by mail-qk1-x741.google.com with SMTP id 11so233502qkd.5 for ; Wed, 04 Nov 2020 08:27:06 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=eO4ZArDyu+ZJfn/p+xFmiVG0Khc/7s1KCX+UczswKpc=; b=YXzs7v1qcjubqB6lqjBI/EkH8Ew5ePJ/+qs7DUDiUZtQHkHUl8CDiWTDxHMjEtVAEq y4DPEZGdMgikiCCz1iyoEBCACTTj5NfGBqSBxtM4YhASJmjPzw3Ru1sW1/DvnieRwjTY 4W98oB17g5t4pTfldW/XY9g8XZz54SIVyNEA+eDHIcdTgOtv5P0p5xDKWB96QJhBjlTG 7vF50/aNDIq9TfCV6mwLSugUN/DNAAwFZx1LqbaVrBZqJuYQx5mKey+iKOAqomZn4u0p zBLv07vp9g3sK/N9lDG12as7K9XEJwMIIw642FeU7yR2RQOcTHRliOOpraIaU7RXo3eM jkBg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=eO4ZArDyu+ZJfn/p+xFmiVG0Khc/7s1KCX+UczswKpc=; b=l7rqcUs7Soo4G9mhLKKxeowCN+EI//QbXdOgYkJPFi/TY9LH+myQMRJId0+M+IJrIQ CTwG1E02iQkWLoXbrfACCZxPKBL/NNCnnuC1BU+4yhmFqW2ExDrznwm/6YJKHsAkHVfD j+F83Yuz4AHBFsju+r0CvQlAKK+wFbH5GjuQr/YE7Zut5okK5Xie3lRdqekj6DhWiuA3 mZDb3S+NhbUfZhrbS0BGpT7DKvLkBL2IaJDCTCdINHIFgGz3nWP2zYOSj7beXIyuQj1R mESvtbaKIqDbEM/CmDxn6B6Zt9rvq9ZY1/5+7NQP8U8Py/DFpVgHMQZkdPYC8C1L7Mup jMfQ== X-Gm-Message-State: AOAM5320XNFMMMRGXKzq9w2BS2S6hIH0MOvgoN0GAOE141HRB51ks5lM 49z/6H6W8jE8na2WEzHWH/fey1TQxxeR X-Google-Smtp-Source: ABdhPJzaQ2ewvrj5i5bzEvHHn6xoaf9cZJUFKtk9MIxXvX6xcaouJZMD+AXPTTLhfL0ezubnT85EEw== X-Received: by 2002:a37:c44c:: with SMTP id h12mr23189908qkm.166.1604507225709; Wed, 04 Nov 2020 08:27:05 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.04 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:04 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 04/17] NFS: Clean up directory array handling Date: Wed, 4 Nov 2020 11:16:25 -0500 Message-Id: <20201104161638.300324-5-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-4-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust Refactor to use pagecache_get_page() so that we can fill the page in multiple stages. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 138 ++++++++++++++++++++++++++++----------------------- 1 file changed, 77 insertions(+), 61 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 68acbde3f914..842f69120a01 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -149,7 +149,7 @@ typedef struct nfs_readdir_descriptor { struct file *file; struct page *page; struct dir_context *ctx; - unsigned long page_index; + pgoff_t page_index; u64 dir_cookie; u64 last_cookie; u64 dup_cookie; @@ -166,13 +166,18 @@ typedef struct nfs_readdir_descriptor { bool eof; } nfs_readdir_descriptor_t; -static -void nfs_readdir_init_array(struct page *page) +static void nfs_readdir_array_init(struct nfs_cache_array *array) +{ + memset(array, 0, sizeof(struct nfs_cache_array)); +} + +static void nfs_readdir_page_init_array(struct page *page, u64 last_cookie) { struct nfs_cache_array *array; array = kmap_atomic(page); - memset(array, 0, sizeof(struct nfs_cache_array)); + nfs_readdir_array_init(array); + array->last_cookie = last_cookie; kunmap_atomic(array); } @@ -188,7 +193,7 @@ void nfs_readdir_clear_array(struct page *page) array = kmap_atomic(page); for (i = 0; i < array->size; i++) kfree(array->array[i].string.name); - array->size = 0; + nfs_readdir_array_init(array); kunmap_atomic(array); } @@ -268,6 +273,44 @@ int nfs_readdir_add_to_array(struct nfs_entry *entry, struct page *page) return ret; } +static struct page *nfs_readdir_page_get_locked(struct address_space *mapping, + pgoff_t index, u64 last_cookie) +{ + struct page *page; + + page = grab_cache_page(mapping, index); + if (page && !PageUptodate(page)) { + nfs_readdir_page_init_array(page, last_cookie); + if (invalidate_inode_pages2_range(mapping, index + 1, -1) < 0) + nfs_zap_mapping(mapping->host, mapping); + SetPageUptodate(page); + } + + return page; +} + +static u64 nfs_readdir_page_last_cookie(struct page *page) +{ + struct nfs_cache_array *array; + u64 ret; + + array = kmap_atomic(page); + ret = array->last_cookie; + kunmap_atomic(array); + return ret; +} + +static bool nfs_readdir_page_needs_filling(struct page *page) +{ + struct nfs_cache_array *array; + bool ret; + + array = kmap_atomic(page); + ret = !nfs_readdir_array_is_full(array); + kunmap_atomic(array); + return ret; +} + static void nfs_readdir_page_set_eof(struct page *page) { struct nfs_cache_array *array; @@ -682,10 +725,8 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, int status = -ENOMEM; unsigned int array_size = ARRAY_SIZE(pages); - nfs_readdir_init_array(page); - entry.prev_cookie = 0; - entry.cookie = desc->last_cookie; + entry.cookie = nfs_readdir_page_last_cookie(page); entry.eof = 0; entry.fh = nfs_alloc_fhandle(); entry.fattr = nfs_alloc_fattr(); @@ -730,48 +771,25 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, return status; } -/* - * Now we cache directories properly, by converting xdr information - * to an array that can be used for lookups later. This results in - * fewer cache pages, since we can store more information on each page. - * We only need to convert from xdr once so future lookups are much simpler - */ -static -int nfs_readdir_filler(void *data, struct page* page) +static void nfs_readdir_page_put(struct nfs_readdir_descriptor *desc) { - nfs_readdir_descriptor_t *desc = data; - struct inode *inode = file_inode(desc->file); - int ret; - - ret = nfs_readdir_xdr_to_array(desc, page, inode); - if (ret < 0) - goto error; - SetPageUptodate(page); - - if (invalidate_inode_pages2_range(inode->i_mapping, page->index + 1, -1) < 0) { - /* Should never happen */ - nfs_zap_mapping(inode, inode->i_mapping); - } - unlock_page(page); - return 0; - error: - nfs_readdir_clear_array(page); - unlock_page(page); - return ret; + put_page(desc->page); + desc->page = NULL; } -static -void cache_page_release(nfs_readdir_descriptor_t *desc) +static void +nfs_readdir_page_unlock_and_put_cached(struct nfs_readdir_descriptor *desc) { - put_page(desc->page); - desc->page = NULL; + unlock_page(desc->page); + nfs_readdir_page_put(desc); } -static -struct page *get_cache_page(nfs_readdir_descriptor_t *desc) +static struct page * +nfs_readdir_page_get_cached(struct nfs_readdir_descriptor *desc) { - return read_cache_page(desc->file->f_mapping, desc->page_index, - nfs_readdir_filler, desc); + return nfs_readdir_page_get_locked(desc->file->f_mapping, + desc->page_index, + desc->last_cookie); } /* @@ -785,23 +803,21 @@ int find_and_lock_cache_page(nfs_readdir_descriptor_t *desc) struct nfs_inode *nfsi = NFS_I(inode); int res; - desc->page = get_cache_page(desc); - if (IS_ERR(desc->page)) - return PTR_ERR(desc->page); - res = lock_page_killable(desc->page); - if (res != 0) - goto error; - res = -EAGAIN; - if (desc->page->mapping != NULL) { - res = nfs_readdir_search_array(desc); - if (res == 0) { - nfsi->page_index = desc->page_index; - return 0; - } + desc->page = nfs_readdir_page_get_cached(desc); + if (!desc->page) + return -ENOMEM; + if (nfs_readdir_page_needs_filling(desc->page)) { + res = nfs_readdir_xdr_to_array(desc, desc->page, inode); + if (res < 0) + goto error; + } + res = nfs_readdir_search_array(desc); + if (res == 0) { + nfsi->page_index = desc->page_index; + return 0; } - unlock_page(desc->page); error: - cache_page_release(desc); + nfs_readdir_page_unlock_and_put_cached(desc); return res; } @@ -896,6 +912,7 @@ int uncached_readdir(nfs_readdir_descriptor_t *desc) desc->page = page; desc->duped = 0; + nfs_readdir_page_init_array(page, desc->dir_cookie); status = nfs_readdir_xdr_to_array(desc, page, inode); if (status < 0) goto out_release; @@ -904,7 +921,7 @@ int uncached_readdir(nfs_readdir_descriptor_t *desc) out_release: nfs_readdir_clear_array(desc->page); - cache_page_release(desc); + nfs_readdir_page_put(desc); out: dfprintk(DIRCACHE, "NFS: %s: returns %d\n", __func__, status); @@ -976,8 +993,7 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) break; res = nfs_do_filldir(desc); - unlock_page(desc->page); - cache_page_release(desc); + nfs_readdir_page_unlock_and_put_cached(desc); if (res < 0) break; } while (!desc->eof); From patchwork Wed Nov 4 16:16:26 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881487 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 4CE0314B4 for ; Wed, 4 Nov 2020 16:27:09 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 27213206D9 for ; Wed, 4 Nov 2020 16:27:09 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="HpVuAUY3" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731175AbgKDQ1I (ORCPT ); Wed, 4 Nov 2020 11:27:08 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36108 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728999AbgKDQ1I (ORCPT ); Wed, 4 Nov 2020 11:27:08 -0500 Received: from mail-qv1-xf44.google.com (mail-qv1-xf44.google.com [IPv6:2607:f8b0:4864:20::f44]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id F2F5CC0613D3 for ; Wed, 4 Nov 2020 08:27:07 -0800 (PST) Received: by mail-qv1-xf44.google.com with SMTP id da2so7969943qvb.0 for ; Wed, 04 Nov 2020 08:27:07 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=Ba9tEIiRCHCzAnjBVsi/HZFF1pWE6pK3yXz5LGvGLco=; b=HpVuAUY3RRQ6YTHbCTcIkF8SYFYVdOcRS72m3lveFz9M8Ys8bUcd2FAHSpkUVX0yPY xj7bgHH5gxAppkoR7QPz1ah8eCS6Y/Y+Wv82FGOwjTkg30w7nvF6xxGL5/DpKAUiqY9w aUpP66438XEl85fexAg4WQYYU899rgQeacw0jCrZNHTsPD7nivZdlrWb2S9qvB+D/YE+ WNyfkrJ7LbRLVF8K1M1XU/Nqb0GBL/McIfVt9NcmlBjI/iZ1GwDV4vSd7/rTjg5t/anS pOLZ4cGtn4tVcVaLG41E7F/b5oUa+tXZYFlmNxmVKJ2UeKk4+vi6GLHTaMfeloRuYOGo MqCw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=Ba9tEIiRCHCzAnjBVsi/HZFF1pWE6pK3yXz5LGvGLco=; b=Aura9e3/6z5LI1sJh0vB+VTxNlpHJ/4wlZwrpPglDs1nhG+V6E8RPeSzz2PmRF+BV/ BwFBoBNygzg8DoeU3AdgmXpLi8coUwSGbSpbYDxVaOALNbZGgWAsH1BfUg7KOF9FGs5H F2LerK3gJR/ycl7bb4efD78mDSRAnaBX/ls4JFf7x4IfEEfj8xZPUcD8OaAaBYBy+saG y21K0L3jvDNmY00eDL3R8K0GH5SfwtceLy0Pu4Qqh9Z/pbPnbd17ZK5oXtKzcUiTuafx HEnGN+jVwx5Xn70zQY6J0n6pEJYCbuKRoEqSILPEY8T3q+vXYNzefA+5KepEHmNQURHa 84SA== X-Gm-Message-State: AOAM532/WkvSnQ1AeYdM/R7uhXbw2g6wQjT74mvBbXRXM556J1jap2xw Oh4nDyaCaTKN9H1YfOZDjryR4d88NAXx X-Google-Smtp-Source: ABdhPJyNKYUgY10qxi6C1OQW4rBqO0sZ3xQaJ77NZALSofiBpjOEhBH0WwseKbB43stsgmeA6h/2FQ== X-Received: by 2002:ad4:4e2b:: with SMTP id dm11mr3327551qvb.41.1604507226804; Wed, 04 Nov 2020 08:27:06 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.05 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:06 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 05/17] NFS: Don't discard readdir results Date: Wed, 4 Nov 2020 11:16:26 -0500 Message-Id: <20201104161638.300324-6-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-5-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust If a readdir call returns more data than we can fit into one page cache page, then allocate a new one for that data rather than discarding the data. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 46 ++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 42 insertions(+), 4 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 842f69120a01..f7248145c333 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -320,6 +320,26 @@ static void nfs_readdir_page_set_eof(struct page *page) kunmap_atomic(array); } +static void nfs_readdir_page_unlock_and_put(struct page *page) +{ + unlock_page(page); + put_page(page); +} + +static struct page *nfs_readdir_page_get_next(struct address_space *mapping, + pgoff_t index, u64 cookie) +{ + struct page *page; + + page = nfs_readdir_page_get_locked(mapping, index, cookie); + if (page) { + if (nfs_readdir_page_last_cookie(page) == cookie) + return page; + nfs_readdir_page_unlock_and_put(page); + } + return NULL; +} + static inline int is_32bit_api(void) { @@ -637,13 +657,15 @@ void nfs_prime_dcache(struct dentry *parent, struct nfs_entry *entry, } /* Perform conversion from xdr to cache array */ -static -int nfs_readdir_page_filler(nfs_readdir_descriptor_t *desc, struct nfs_entry *entry, - struct page **xdr_pages, struct page *page, unsigned int buflen) +static int nfs_readdir_page_filler(struct nfs_readdir_descriptor *desc, + struct nfs_entry *entry, + struct page **xdr_pages, + struct page *fillme, unsigned int buflen) { + struct address_space *mapping = desc->file->f_mapping; struct xdr_stream stream; struct xdr_buf buf; - struct page *scratch; + struct page *scratch, *new, *page = fillme; int status; scratch = alloc_page(GFP_KERNEL); @@ -666,6 +688,19 @@ int nfs_readdir_page_filler(nfs_readdir_descriptor_t *desc, struct nfs_entry *en desc->dir_verifier); status = nfs_readdir_add_to_array(entry, page); + if (status != -ENOSPC) + continue; + + if (page->mapping != mapping) + break; + new = nfs_readdir_page_get_next(mapping, page->index + 1, + entry->prev_cookie); + if (!new) + break; + if (page != fillme) + nfs_readdir_page_unlock_and_put(page); + page = new; + status = nfs_readdir_add_to_array(entry, page); } while (!status && !entry->eof); switch (status) { @@ -681,6 +716,9 @@ int nfs_readdir_page_filler(nfs_readdir_descriptor_t *desc, struct nfs_entry *en break; } + if (page != fillme) + nfs_readdir_page_unlock_and_put(page); + put_page(scratch); return status; } From patchwork Wed Nov 4 16:16:27 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881489 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 63C7914B4 for ; Wed, 4 Nov 2020 16:27:10 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 3EA27206D4 for ; Wed, 4 Nov 2020 16:27:10 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="ZGdxe8CO" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731180AbgKDQ1J (ORCPT ); Wed, 4 Nov 2020 11:27:09 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36112 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728999AbgKDQ1J (ORCPT ); Wed, 4 Nov 2020 11:27:09 -0500 Received: from mail-qk1-x743.google.com (mail-qk1-x743.google.com [IPv6:2607:f8b0:4864:20::743]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 2366AC0613D3 for ; Wed, 4 Nov 2020 08:27:09 -0800 (PST) Received: by mail-qk1-x743.google.com with SMTP id 11so233638qkd.5 for ; Wed, 04 Nov 2020 08:27:09 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=d4SBKQY4D3SrCP5hjy6CzKLVkGZfG5JmNrqa2naVuXg=; b=ZGdxe8CO4I9std1kg2XmPfD0kVU1rgdXYrIYkg5HyResRYNkmIEBPJH0HvdkwBxPit MGuF3AhoiqY3GiMswMLqOpXxNtiW2eUbPLK1FZUSZ8zjXr5R01wraCl85FYXWy/Kvd8T HfQa4znxVYSuESy4mi9juViPBN+5+Gu97BscR55mlSXiFZlgOeNQQKhejn1WtjETFC42 7w7vpAm79cpDJdwx+DH0P4l+6btXxUB34ORA9CKoAU0w7ZFyr9xbrZ8GlnIboNyB9zE/ e1ddXzymyhAQF2Z0HKECkNecfSZfftxM7JGfSbBSlL4scdNvFQOPsl7CbJ/8P6rhyxy3 tfhQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=d4SBKQY4D3SrCP5hjy6CzKLVkGZfG5JmNrqa2naVuXg=; b=dKztAJp8+2BXEu/h5NargafUj7c2w5pafDKnul63fVbBClgxKZmTB2ETya4+C0i8AK rzG1cC3zACGAbA2M864gj60X0ijz73uB7ZKgbhfipDIYw87+eD3jgb+B5BZc9ShBXFdn q7+Rx0wZyPLOUKRtHEOYZ2skp5OEdobmTrzeVJGji5z7Qy2AIfhiUONFnoz22bvUEkAi idTcLSwUa9V1qhQsj5ca+zWkbVN9x+T6tRtNcWAk1Ltc9GTGk7bFPjJUVd0CKaf9Dyp+ KfRiLxVxeSXhAx9t9dGfQ5AncjkFRJvmWeFc6mVUOCeBqAxmVeQdzSUlAbIJI0EQj03i 3VWQ== X-Gm-Message-State: AOAM533xa9e3uwHpzpTfGPaqC7tvJ9FfX/iTYB0ACMrZVBc/6PhzyFsx Tbupt5/m3gBe7+bBYtDTLKVe3Rp1c4I4 X-Google-Smtp-Source: ABdhPJxYGXHnE2IQ6j5Azfaduj2Ze4C2lAkT4JvwJQyR7yhqSafqISPxLmBUuIn7fYM88egMX4iorQ== X-Received: by 2002:ae9:ee15:: with SMTP id i21mr24394904qkg.76.1604507228067; Wed, 04 Nov 2020 08:27:08 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.06 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:07 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 06/17] NFS: Remove unnecessary kmap in nfs_readdir_xdr_to_array() Date: Wed, 4 Nov 2020 11:16:27 -0500 Message-Id: <20201104161638.300324-7-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-6-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust The kmapped pointer is only used once per loop to check if we need to exit. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 10 +++------- 1 file changed, 3 insertions(+), 7 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index f7248145c333..e8b0fcc1bc9e 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -759,7 +759,6 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, struct page *pages[NFS_MAX_READDIR_PAGES]; struct nfs_entry entry; struct file *file = desc->file; - struct nfs_cache_array *array; int status = -ENOMEM; unsigned int array_size = ARRAY_SIZE(pages); @@ -778,11 +777,9 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, goto out; } - array = kmap(page); - status = nfs_readdir_alloc_pages(pages, array_size); if (status < 0) - goto out_release_array; + goto out_release_label; do { unsigned int pglen; status = nfs_readdir_xdr_filler(pages, desc, &entry, file, inode); @@ -797,11 +794,10 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, } status = nfs_readdir_page_filler(desc, &entry, pages, page, pglen); - } while (!status && !nfs_readdir_array_is_full(array)); + } while (!status && nfs_readdir_page_needs_filling(page)); nfs_readdir_free_pages(pages, array_size); -out_release_array: - kunmap(page); +out_release_label: nfs4_label_free(entry.label); out: nfs_free_fattr(entry.fattr); From patchwork Wed Nov 4 16:16:28 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881493 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id C580F14C0 for ; Wed, 4 Nov 2020 16:27:11 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id A701B206DB for ; Wed, 4 Nov 2020 16:27:11 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="db5F/CTl" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730889AbgKDQ1L (ORCPT ); Wed, 4 Nov 2020 11:27:11 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36116 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728999AbgKDQ1K (ORCPT ); Wed, 4 Nov 2020 11:27:10 -0500 Received: from mail-qv1-xf41.google.com (mail-qv1-xf41.google.com [IPv6:2607:f8b0:4864:20::f41]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 3844DC0613D3 for ; Wed, 4 Nov 2020 08:27:10 -0800 (PST) Received: by mail-qv1-xf41.google.com with SMTP id w5so10147779qvn.12 for ; Wed, 04 Nov 2020 08:27:10 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=cQWnqdY1gDuNcCekRbuBF1v/3ZoPLijNeC7jWYYnvtc=; b=db5F/CTl9J2G9prXbl50VGBnX2gnu7dekvyQWA8kj/T3eSRLuh8Gyb1u80WAr3Jgsy 70emfNd4aETR5W02qSGspedDqFNQA9S0Y+ggRss946lAODF5sG+zGbYvI6q6D2DI4Yyu LH9cB0sPNe+TlnKlGjH0MiId7sudQPmkZhr+GDpd0d1n+X/bFtoCMbHXwZYFDceXB5p6 NbY/lR2YJd0cIk+hEeFpJyuWPKuFXRikqUc9QoVZbb2cZGWVIqbMIE9FalgY1O2UGuqK Vy60HEFjd2MDkBKts85BaR4Bi+lx4Qhu8EUKOP6+9oaHceWiz7IMT3qo3ePpbrF4LGEw e6kw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=cQWnqdY1gDuNcCekRbuBF1v/3ZoPLijNeC7jWYYnvtc=; b=V3hR/SZ+uR+3NI7TpXUR+AbXuqt/l45aB1oWhcvNS8fkZQdEFbrXv3ShkELe2ygoqh qdHclx6UECI5KAiyAEFrSqcbezs9jV4RAh39sRVgrlrGDbDGvAxlS2kuiW2KRaSopfOc 9ajC71Tqa0GMAdknhnu28mPPX+fXcufdwOI6GgxSlXBmiasIqY+nipFezfUVQwQ6VOdt IMX026INCrvC4IvJKrDL4krGtmAbMcPZFzA3GCXP2eMHKbGSBVy96KWqu4bKiQOn7Ydh o4gUFdebTlLhyDb2dyh3qR3qjEKnPDR/Y4+lTiGRPVRTcCnke6lg/Oaed8IHBdVxUpwI 2/ig== X-Gm-Message-State: AOAM531qdmACLQ+E9q5tKxCaYjkHBCvAfb7Yf9UFwN3HmnjgFQLrmYDy pKTqfISNFDXOmG9EkRJUBclHW/3snh6L X-Google-Smtp-Source: ABdhPJyO4rB0tRS6uW3MczgcdLTfXRRC3D60NornRhqtzAS/fsxmTM5JSyH4LRvE5y8dQzp87cErbg== X-Received: by 2002:a0c:ecc8:: with SMTP id o8mr32915864qvq.54.1604507229119; Wed, 04 Nov 2020 08:27:09 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.08 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:08 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 07/17] NFS: Replace kmap() with kmap_atomic() in nfs_readdir_search_array() Date: Wed, 4 Nov 2020 11:16:28 -0500 Message-Id: <20201104161638.300324-8-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-7-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index e8b0fcc1bc9e..b9001123ec84 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -447,7 +447,7 @@ int nfs_readdir_search_array(nfs_readdir_descriptor_t *desc) struct nfs_cache_array *array; int status; - array = kmap(desc->page); + array = kmap_atomic(desc->page); if (desc->dir_cookie == 0) status = nfs_readdir_search_for_pos(array, desc); @@ -459,7 +459,7 @@ int nfs_readdir_search_array(nfs_readdir_descriptor_t *desc) desc->current_index += array->size; desc->page_index++; } - kunmap(desc->page); + kunmap_atomic(array); return status; } From patchwork Wed Nov 4 16:16:29 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881495 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 7D23914C0 for ; Wed, 4 Nov 2020 16:27:14 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 561AF2080D for ; Wed, 4 Nov 2020 16:27:14 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="FSeJ8ZGY" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731189AbgKDQ1L (ORCPT ); Wed, 4 Nov 2020 11:27:11 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36120 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728999AbgKDQ1L (ORCPT ); Wed, 4 Nov 2020 11:27:11 -0500 Received: from mail-qk1-x744.google.com (mail-qk1-x744.google.com [IPv6:2607:f8b0:4864:20::744]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 44327C0613D3 for ; Wed, 4 Nov 2020 08:27:11 -0800 (PST) Received: by mail-qk1-x744.google.com with SMTP id 12so15909975qkl.8 for ; Wed, 04 Nov 2020 08:27:11 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=cKSCPDB+ZJlQ0/xbh0s71VG8EqQc1gl1B4gKjfQUU6o=; b=FSeJ8ZGYtXi2/DIxDjnZy/tPw/iZ6FDlpFa0KTwbpmWplhJhO/VOzMPRLmwfApUK5u gCON5VeKjL3Ams7TvX4B80KsPxt3iVD0U8HZK3rfPqHqkaEE6/nfxiQ5l6vybmWDy3cT qruidVmuADl86K27umJELkbvLHGcveiGRsSeqMZsVbOIhgKOiIjoHn/AtzrV6SzzTRLz taYmSNM72NQcgk4eGwB5WMUjwbWmFFeXC7Nk/zPJsy2FWaFisWPFc3/APkRy42IgVr58 Sbh/BKPLZ8bIKbAFYLdb4u8p2WiL94XNaSLEPPqYFPYL0F2EZmZmfVf6Rfk3L7Zk9Z4B diDA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=cKSCPDB+ZJlQ0/xbh0s71VG8EqQc1gl1B4gKjfQUU6o=; b=PjS2JIx0cOrOpBU0yJK4nyrJKKKHtAFMcIJZ4HDv7cYDfRX1HHswrdmE9ArHI3cXzg 88ADMMpZfqhYCyDqCqET0OVUD0Ah81dgmPbo5nRdw9ku/8eixhMC7GromTDemT5PWBvW Blz9okUtWDZtNk+1kNmJXkK6KUMt+eyk5HGKY9eRDP8RkFZAMb86M10er5BLGyV/UL5B m0lbaKiIguHmaCEyUw0drwzYrOqMDmegT2hzGgWm1KuoKy6CslgSYWsa2NJ4vtCcTK5W YZ6+By+aTSzCuCWpoicnFT9wOwHYgiH1mgeEXdA3eKDCg3rwKryi/Uyyp50Y3eZAqRoE ihGg== X-Gm-Message-State: AOAM533Suq//TTE1qmfsdc6WpYIYzterxR2qEADQs1xu2lObFJQfDEMk Q70IoJowOfQb0gVGfWnw6vdr/oNUMjky X-Google-Smtp-Source: ABdhPJypCjEbr+ONpoZ81chXzEG/lPkQQOU6NXnGyLKCd32mWqcH4DH0lybH4kS0IYwNIEjaceZUCQ== X-Received: by 2002:a37:6309:: with SMTP id x9mr26347362qkb.493.1604507230149; Wed, 04 Nov 2020 08:27:10 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.09 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:09 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 08/17] NFS: Simplify struct nfs_cache_array_entry Date: Wed, 4 Nov 2020 11:16:29 -0500 Message-Id: <20201104161638.300324-9-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-8-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> <20201104161638.300324-8-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust We don't need to store a hash, so replace struct qstr with a simple const char pointer and length. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 46 +++++++++++++++++++++++++--------------------- 1 file changed, 25 insertions(+), 21 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index b9001123ec84..be0e2891fecc 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -133,7 +133,8 @@ nfs_closedir(struct inode *inode, struct file *filp) struct nfs_cache_array_entry { u64 cookie; u64 ino; - struct qstr string; + const char *name; + unsigned int name_len; unsigned char d_type; }; @@ -192,7 +193,7 @@ void nfs_readdir_clear_array(struct page *page) array = kmap_atomic(page); for (i = 0; i < array->size; i++) - kfree(array->array[i].string.name); + kfree(array->array[i].name); nfs_readdir_array_init(array); kunmap_atomic(array); } @@ -213,20 +214,17 @@ static bool nfs_readdir_array_is_full(struct nfs_cache_array *array) * when called by nfs_readdir_add_to_array, the strings will be freed in * nfs_clear_readdir_array() */ -static -int nfs_readdir_make_qstr(struct qstr *string, const char *name, unsigned int len) +static const char *nfs_readdir_copy_name(const char *name, unsigned int len) { - string->len = len; - string->name = kmemdup_nul(name, len, GFP_KERNEL); - if (string->name == NULL) - return -ENOMEM; + const char *ret = kmemdup_nul(name, len, GFP_KERNEL); + /* * Avoid a kmemleak false positive. The pointer to the name is stored * in a page cache page which kmemleak does not scan. */ - kmemleak_not_leak(string->name); - string->hash = full_name_hash(NULL, name, len); - return 0; + if (ret != NULL) + kmemleak_not_leak(ret); + return ret; } /* @@ -249,27 +247,34 @@ static int nfs_readdir_array_can_expand(struct nfs_cache_array *array) static int nfs_readdir_add_to_array(struct nfs_entry *entry, struct page *page) { - struct nfs_cache_array *array = kmap(page); + struct nfs_cache_array *array; struct nfs_cache_array_entry *cache_entry; + const char *name; int ret; + name = nfs_readdir_copy_name(entry->name, entry->len); + if (!name) + return -ENOMEM; + + array = kmap_atomic(page); ret = nfs_readdir_array_can_expand(array); - if (ret) + if (ret) { + kfree(name); goto out; + } cache_entry = &array->array[array->size]; cache_entry->cookie = entry->prev_cookie; cache_entry->ino = entry->ino; cache_entry->d_type = entry->d_type; - ret = nfs_readdir_make_qstr(&cache_entry->string, entry->name, entry->len); - if (ret) - goto out; + cache_entry->name_len = entry->len; + cache_entry->name = name; array->last_cookie = entry->cookie; array->size++; if (entry->eof != 0) nfs_readdir_array_set_eof(array); out: - kunmap(page); + kunmap_atomic(array); return ret; } @@ -413,9 +418,8 @@ int nfs_readdir_search_for_cookie(struct nfs_cache_array *array, nfs_readdir_des if (printk_ratelimit()) { pr_notice("NFS: directory %pD2 contains a readdir loop." "Please contact your server vendor. " - "The file: %.*s has duplicate cookie %llu\n", - desc->file, array->array[i].string.len, - array->array[i].string.name, desc->dir_cookie); + "The file: %s has duplicate cookie %llu\n", + desc->file, array->array[i].name, desc->dir_cookie); } status = -ELOOP; goto out; @@ -888,7 +892,7 @@ int nfs_do_filldir(nfs_readdir_descriptor_t *desc) struct nfs_cache_array_entry *ent; ent = &array->array[i]; - if (!dir_emit(desc->ctx, ent->string.name, ent->string.len, + if (!dir_emit(desc->ctx, ent->name, ent->name_len, nfs_compat_user_ino64(ent->ino), ent->d_type)) { desc->eof = true; break; From patchwork Wed Nov 4 16:16:30 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881515 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 4475D14C0 for ; Wed, 4 Nov 2020 16:27:26 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 1E822206D9 for ; Wed, 4 Nov 2020 16:27:26 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="mF8JnYJf" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726344AbgKDQ1Z (ORCPT ); Wed, 4 Nov 2020 11:27:25 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36136 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1731201AbgKDQ1N (ORCPT ); Wed, 4 Nov 2020 11:27:13 -0500 Received: from mail-qk1-x742.google.com (mail-qk1-x742.google.com [IPv6:2607:f8b0:4864:20::742]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 9461AC0613D4 for ; Wed, 4 Nov 2020 08:27:12 -0800 (PST) Received: by mail-qk1-x742.google.com with SMTP id a65so17572482qkg.13 for ; Wed, 04 Nov 2020 08:27:12 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=PiwfpfNYPIszRF1iL4k5zXYxNelrn1vUwBxUeMpkK3U=; b=mF8JnYJf7FvrDO096NGPhi4uME5ZhMW6BkmWD8FV5dg/doBR4jTnofQwfD3NI0eALa 4W27KimIy7D5VlVZiX2Tx16QLR87TnPeQ29O3jnf+DBeMivtVAHz3819Mty4drLAM2z+ qimj/FLpg2NEqQ5l/XlDKb1D0TJK9+5wU9YIsN6pJDd3IYIQGqMoUlV2r1ZsLQoonR87 1jgimyj9Ty850UYkB9cuyuVeASiZ/atApRNm1rSeuQVTZQzxoh9hO37XBxDrtx2cppPU jgMgl0iC6imHbaAbMetNqbVzd4xxa8ZaVkoK2BJHrnAs52RMD3yTw7VPwe2c/JmJ3WWl 3fNg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=PiwfpfNYPIszRF1iL4k5zXYxNelrn1vUwBxUeMpkK3U=; b=tN1emf3m6/1+ewwx1DtUZ0K3cM7Psh190noBMR2+b90I8+pr1eWEgDWm7axCJN4UQC 5o2XK6EQ8nmhNbi60f+G5Bf3uNCtB0IUTFZta5Gc1aGr/sI5UVuIf30Z+X1qAIbn4sQE OKTho8bMjxWqh8cSmMBLg7KnbmlfTAsNl/aCLPg0ZOgOyHpzf3YTP6VpdFBUicbo2UfZ g20itV0NMV/oRXycaivbnjJUParG4yDtYJXpJXr5evfmFiqlSt3EHde+oRza6xku77RQ ocuWyv0vJuf4CaJ6cfho0K94dUlofBJoG+f4wdPxAjNBqmmITee76pmBdur2SYiVNuJx 6zcw== X-Gm-Message-State: AOAM531XZJfdr83e3qYAP/UukkUvQTFVfOCi3zGaHrLfJjdLWlTKQM2e 7+ye8xBGEkXwLxYfoP0+B+22Y9zwguNu X-Google-Smtp-Source: ABdhPJyh6f1Tg5SpXXWj8QRVmSkhX/U4TD8xW7aOHe+tpphoHW0ZxUgAOwBvQsEslwsne5xoTK4XPg== X-Received: by 2002:a37:474b:: with SMTP id u72mr27416683qka.333.1604507231443; Wed, 04 Nov 2020 08:27:11 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.10 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:10 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 09/17] NFS: Support larger readdir buffers Date: Wed, 4 Nov 2020 11:16:30 -0500 Message-Id: <20201104161638.300324-10-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-9-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> <20201104161638.300324-8-trond.myklebust@hammerspace.com> <20201104161638.300324-9-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust Support readdir buffers of up to 1MB in size so that we can read large directories using few RPC calls. Signed-off-by: Trond Myklebust --- fs/nfs/client.c | 4 ++-- fs/nfs/dir.c | 33 +++++++++++++++++++-------------- fs/nfs/internal.h | 6 ------ 3 files changed, 21 insertions(+), 22 deletions(-) diff --git a/fs/nfs/client.c b/fs/nfs/client.c index 4b8cc93913f7..f6454ba53d05 100644 --- a/fs/nfs/client.c +++ b/fs/nfs/client.c @@ -781,8 +781,8 @@ static void nfs_server_set_fsinfo(struct nfs_server *server, server->wtmult = nfs_block_bits(fsinfo->wtmult, NULL); server->dtsize = nfs_block_size(fsinfo->dtpref, NULL); - if (server->dtsize > PAGE_SIZE * NFS_MAX_READDIR_PAGES) - server->dtsize = PAGE_SIZE * NFS_MAX_READDIR_PAGES; + if (server->dtsize > NFS_MAX_FILE_IO_SIZE) + server->dtsize = NFS_MAX_FILE_IO_SIZE; if (server->dtsize > server->rsize) server->dtsize = server->rsize; diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index be0e2891fecc..438906dae083 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -727,44 +727,47 @@ static int nfs_readdir_page_filler(struct nfs_readdir_descriptor *desc, return status; } -static -void nfs_readdir_free_pages(struct page **pages, unsigned int npages) +static void nfs_readdir_free_pages(struct page **pages, size_t npages) { - unsigned int i; - for (i = 0; i < npages; i++) - put_page(pages[i]); + while (npages--) + put_page(pages[npages]); + kfree(pages); } /* * nfs_readdir_alloc_pages() will allocate pages that must be freed with a call * to nfs_readdir_free_pages() */ -static -int nfs_readdir_alloc_pages(struct page **pages, unsigned int npages) +static struct page **nfs_readdir_alloc_pages(size_t npages) { - unsigned int i; + struct page **pages; + size_t i; + pages = kmalloc_array(npages, sizeof(*pages), GFP_KERNEL); + if (!pages) + return NULL; for (i = 0; i < npages; i++) { struct page *page = alloc_page(GFP_KERNEL); if (page == NULL) goto out_freepages; pages[i] = page; } - return 0; + return pages; out_freepages: nfs_readdir_free_pages(pages, i); - return -ENOMEM; + return NULL; } static int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, struct inode *inode) { - struct page *pages[NFS_MAX_READDIR_PAGES]; + struct page **pages; struct nfs_entry entry; struct file *file = desc->file; + size_t array_size; + size_t dtsize = NFS_SERVER(inode)->dtsize; int status = -ENOMEM; - unsigned int array_size = ARRAY_SIZE(pages); entry.prev_cookie = 0; entry.cookie = nfs_readdir_page_last_cookie(page); @@ -781,9 +784,11 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, goto out; } - status = nfs_readdir_alloc_pages(pages, array_size); - if (status < 0) + array_size = (dtsize + PAGE_SIZE - 1) >> PAGE_SHIFT; + pages = nfs_readdir_alloc_pages(array_size); + if (!pages) goto out_release_label; + do { unsigned int pglen; status = nfs_readdir_xdr_filler(pages, desc, &entry, file, inode); diff --git a/fs/nfs/internal.h b/fs/nfs/internal.h index 6673a77884d9..b840d0a91c9d 100644 --- a/fs/nfs/internal.h +++ b/fs/nfs/internal.h @@ -56,12 +56,6 @@ static inline bool nfs_lookup_is_soft_revalidate(const struct dentry *dentry) #define NFS_UNSPEC_RETRANS (UINT_MAX) #define NFS_UNSPEC_TIMEO (UINT_MAX) -/* - * Maximum number of pages that readdir can use for creating - * a vmapped array of pages. - */ -#define NFS_MAX_READDIR_PAGES 8 - struct nfs_client_initdata { unsigned long init_flags; const char *hostname; /* Hostname of the server */ From patchwork Wed Nov 4 16:16:31 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881509 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id BFE67921 for ; Wed, 4 Nov 2020 16:27:22 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 91558206DB for ; Wed, 4 Nov 2020 16:27:22 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="lrw6iy7l" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731198AbgKDQ1O (ORCPT ); Wed, 4 Nov 2020 11:27:14 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36138 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1731206AbgKDQ1O (ORCPT ); Wed, 4 Nov 2020 11:27:14 -0500 Received: from mail-qt1-x844.google.com (mail-qt1-x844.google.com [IPv6:2607:f8b0:4864:20::844]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id A5F94C061A4A for ; Wed, 4 Nov 2020 08:27:13 -0800 (PST) Received: by mail-qt1-x844.google.com with SMTP id p12so5249360qtp.7 for ; Wed, 04 Nov 2020 08:27:13 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=w3qSV6/1/FQDA62kfZdJX3U8JfpYXaEx8nE11jTGprM=; b=lrw6iy7lAYZF1WvUHdIlI7ZoHLSalCsLRiQtd5tah2lg3GYkSnPqc8vjEGvMrD5f2C 0NpKlpYnOggy5WyZpHOsxRrUvktQn6wHH1LSg6nq0WNUD/MEMk4xv39w+7isEpdRG22k 0z1RFQt8/h3ETrJJcZ13iDMdBKXg9brPnz53GHWTvLnQybJYaG7cb6JJ7QHl1tRLNWht ozPfsdpAId05dpJ5UXcMxWcZItk8UknihfHUDXOHWYsDavzXVtKqpDXi96bzDEkWcQN+ 0zJjZ4jS86pp2vBr36ZwTaeJQlAzMR2iA2NtbQx/zSutDqfnzNgT1RpXWdsTRz5shvIx 0smw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=w3qSV6/1/FQDA62kfZdJX3U8JfpYXaEx8nE11jTGprM=; b=WFrDGJ9f3goqOYqnngJo/akPzXAWMsavjDcxZP2LpRBM7kOb0zMayVChmAd9SHxlFt t4A0/W5tRSvBESU+hTjijarn+OTVlTCiDnTD8xVIYduy8eQmLxaQqM8emKVBB/JIutjP Q024Yni6XQqZMbRPNS0cANQHYxZXjp0BmfHv6h9kZmTqdfCJZENI/LuoEHh/T4LYPws2 FyW5hUxo1kNWu+DZeBMUDa9ajjFK1g90nLf9FZxwOI+xyFok8HpCrZ3qWPljuBqM23j5 PaxN3MDWZd1gHs41wsVgEwpODolKG37tw2YdUQ66PiKQfidkSNGXqqFOn4mnwkpCyFzR Hp/w== X-Gm-Message-State: AOAM532DrA9oOkAF4RLYRIjgd8U3shkli7xa8FNaoN/hiwJmph2zEZ9X 92phokuqyaLhfpgsF5M3wKUdumZtWpks X-Google-Smtp-Source: ABdhPJx8QXX2BLWsW8iGDLQRY4kCgSMJiaUHCWuFm+lCRSkYmwrEHqlryDg7cG0xpl3XvmZMLjmgpg== X-Received: by 2002:ac8:590c:: with SMTP id 12mr12387889qty.28.1604507232532; Wed, 04 Nov 2020 08:27:12 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.11 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:11 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 10/17] NFS: More readdir cleanups Date: Wed, 4 Nov 2020 11:16:31 -0500 Message-Id: <20201104161638.300324-11-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-10-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> <20201104161638.300324-8-trond.myklebust@hammerspace.com> <20201104161638.300324-9-trond.myklebust@hammerspace.com> <20201104161638.300324-10-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust Remove the redundant caching of the credential in struct nfs_open_dir_context. Pass the buffer size as an argument to nfs_readdir_xdr_filler(). Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 25 +++++++++++-------------- include/linux/nfs_fs.h | 1 - 2 files changed, 11 insertions(+), 15 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 438906dae083..bc366bd8e8f3 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -68,7 +68,7 @@ const struct address_space_operations nfs_dir_aops = { .freepage = nfs_readdir_clear_array, }; -static struct nfs_open_dir_context *alloc_nfs_open_dir_context(struct inode *dir, const struct cred *cred) +static struct nfs_open_dir_context *alloc_nfs_open_dir_context(struct inode *dir) { struct nfs_inode *nfsi = NFS_I(dir); struct nfs_open_dir_context *ctx; @@ -78,7 +78,6 @@ static struct nfs_open_dir_context *alloc_nfs_open_dir_context(struct inode *dir ctx->attr_gencount = nfsi->attr_gencount; ctx->dir_cookie = 0; ctx->dup_cookie = 0; - ctx->cred = get_cred(cred); spin_lock(&dir->i_lock); if (list_empty(&nfsi->open_files) && (nfsi->cache_validity & NFS_INO_DATA_INVAL_DEFER)) @@ -96,7 +95,6 @@ static void put_nfs_open_dir_context(struct inode *dir, struct nfs_open_dir_cont spin_lock(&dir->i_lock); list_del(&ctx->list); spin_unlock(&dir->i_lock); - put_cred(ctx->cred); kfree(ctx); } @@ -113,7 +111,7 @@ nfs_opendir(struct inode *inode, struct file *filp) nfs_inc_stats(inode, NFSIOS_VFSOPEN); - ctx = alloc_nfs_open_dir_context(inode, current_cred()); + ctx = alloc_nfs_open_dir_context(inode); if (IS_ERR(ctx)) { res = PTR_ERR(ctx); goto out; @@ -468,12 +466,12 @@ int nfs_readdir_search_array(nfs_readdir_descriptor_t *desc) } /* Fill a page with xdr information before transferring to the cache page */ -static -int nfs_readdir_xdr_filler(struct page **pages, nfs_readdir_descriptor_t *desc, - struct nfs_entry *entry, struct file *file, struct inode *inode) +static int nfs_readdir_xdr_filler(struct nfs_readdir_descriptor *desc, + u64 cookie, struct page **pages, + size_t bufsize) { - struct nfs_open_dir_context *ctx = file->private_data; - const struct cred *cred = ctx->cred; + struct file *file = desc->file; + struct inode *inode = file_inode(file); unsigned long timestamp, gencount; int error; @@ -481,8 +479,8 @@ int nfs_readdir_xdr_filler(struct page **pages, nfs_readdir_descriptor_t *desc, timestamp = jiffies; gencount = nfs_inc_attr_generation_counter(); desc->dir_verifier = nfs_save_change_attribute(inode); - error = NFS_PROTO(inode)->readdir(file_dentry(file), cred, entry->cookie, pages, - NFS_SERVER(inode)->dtsize, desc->plus); + error = NFS_PROTO(inode)->readdir(file_dentry(file), file->f_cred, + cookie, pages, bufsize, desc->plus); if (error < 0) { /* We requested READDIRPLUS, but the server doesn't grok it */ if (error == -ENOTSUPP && desc->plus) { @@ -764,7 +762,6 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, { struct page **pages; struct nfs_entry entry; - struct file *file = desc->file; size_t array_size; size_t dtsize = NFS_SERVER(inode)->dtsize; int status = -ENOMEM; @@ -791,8 +788,8 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, do { unsigned int pglen; - status = nfs_readdir_xdr_filler(pages, desc, &entry, file, inode); - + status = nfs_readdir_xdr_filler(desc, entry.cookie, + pages, dtsize); if (status < 0) break; diff --git a/include/linux/nfs_fs.h b/include/linux/nfs_fs.h index a2c6455ea3fa..dd6b463dda80 100644 --- a/include/linux/nfs_fs.h +++ b/include/linux/nfs_fs.h @@ -88,7 +88,6 @@ struct nfs_open_context { struct nfs_open_dir_context { struct list_head list; - const struct cred *cred; unsigned long attr_gencount; __u64 dir_cookie; __u64 dup_cookie; From patchwork Wed Nov 4 16:16:32 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881497 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 8EBFA14B4 for ; Wed, 4 Nov 2020 16:27:19 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 65EFF206D9 for ; Wed, 4 Nov 2020 16:27:19 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="AQIoWqwx" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731232AbgKDQ1R (ORCPT ); Wed, 4 Nov 2020 11:27:17 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36144 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1731220AbgKDQ1P (ORCPT ); Wed, 4 Nov 2020 11:27:15 -0500 Received: from mail-qv1-xf43.google.com (mail-qv1-xf43.google.com [IPv6:2607:f8b0:4864:20::f43]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id C1E5DC0613D3 for ; Wed, 4 Nov 2020 08:27:14 -0800 (PST) Received: by mail-qv1-xf43.google.com with SMTP id i17so8100226qvp.11 for ; Wed, 04 Nov 2020 08:27:14 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=ODBqyBWEMtA4MaYYlZB5CrxKv2YKgiVoECc3FXd34GI=; b=AQIoWqwxydda1r/0fSLXicqjE9Cl17R6Cya7jUxQLtcuVtYYm8fSsL9H3SD/HvUqEe YsabFB9yLVDiOGJ/PT3f7/0TVMIli2jCHwUpkmb6jVKXs0iUjpmwEqfr4FaYsFbdmbUM +DNqsFVkQUXwNenLtOOOPpJWKUDVaDlSakTL7knKmb0tyEwdWq1Ozgi/8Et2sJKi8I2A E9NrmoCIv7fowSiX/D1nXPweKZpyOAlg5TN+r5UNbWofvs2jcnmObq81Q93c09Gac2YX 26YdiJSVyrP9Ku/KDrrEVVMJBbm3smGeP9a8nqWECgquqHQAsnv9wNaMaRavEpOgwWpd jlFQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=ODBqyBWEMtA4MaYYlZB5CrxKv2YKgiVoECc3FXd34GI=; b=m5Wa9o+DEOJ2J0hRkuUkSx+x4zGTLBMkvwx0FzbrwdNqOocMDn0A6gxhxD5rlSpxBe lKNaoE0JmBqoGxlwzOdVscIkCJtR3ISARIEMTuOd39vBUWuMNWjJdvBudz6JEbqq21RH gJFnVcD/D5Z62p9uwQr/V2liXRDqKjBEfaR4JvaSOpBPV5Jd4IXx46hTqP+0qssYKALc Q9e6I4ivZhTB++CSCOTc65QwzG24iIhQmJ9Lv/lSP9aJquMYrDsUTCdeNFrNwWcNvIhO YucdCSauCkAKcozaoFXPe9NxQF+gfckAWMFEguFQRWBFceO2yCtwb2j+fNHEOkiA4WHE maLA== X-Gm-Message-State: AOAM533LRxefFnwYTq8XwD0/nTNjQ3tgwmgxiyPg7y63mozIdAYVuM0s owg5duP2iMXKLgXjkSa55azbcgINciJu X-Google-Smtp-Source: ABdhPJz1AN9JyJVj+Ts+7exxv/3AUHsb8e4VNp63aqokh4fVjcKTHQ7WieRYtd4jtLc+hKwwbQFFCg== X-Received: by 2002:a0c:a5a2:: with SMTP id z31mr34682746qvz.15.1604507233602; Wed, 04 Nov 2020 08:27:13 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.12 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:12 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 11/17] NFS: nfs_do_filldir() does not return a value Date: Wed, 4 Nov 2020 11:16:32 -0500 Message-Id: <20201104161638.300324-12-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-11-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> <20201104161638.300324-8-trond.myklebust@hammerspace.com> <20201104161638.300324-9-trond.myklebust@hammerspace.com> <20201104161638.300324-10-trond.myklebust@hammerspace.com> <20201104161638.300324-11-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust Clean up nfs_do_filldir(). Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 21 +++++++-------------- 1 file changed, 7 insertions(+), 14 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index bc366bd8e8f3..48856cee10de 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -881,13 +881,11 @@ int readdir_search_pagecache(nfs_readdir_descriptor_t *desc) /* * Once we've found the start of the dirent within a page: fill 'er up... */ -static -int nfs_do_filldir(nfs_readdir_descriptor_t *desc) +static void nfs_do_filldir(struct nfs_readdir_descriptor *desc) { struct file *file = desc->file; - int i = 0; - int res = 0; - struct nfs_cache_array *array = NULL; + struct nfs_cache_array *array; + unsigned int i = 0; array = kmap(desc->page); for (i = desc->cache_entry_index; i < array->size; i++) { @@ -914,9 +912,8 @@ int nfs_do_filldir(nfs_readdir_descriptor_t *desc) desc->eof = true; kunmap(desc->page); - dfprintk(DIRCACHE, "NFS: nfs_do_filldir() filling ended @ cookie %Lu; returning = %d\n", - (unsigned long long)desc->dir_cookie, res); - return res; + dfprintk(DIRCACHE, "NFS: nfs_do_filldir() filling ended @ cookie %llu\n", + (unsigned long long)desc->dir_cookie); } /* @@ -957,7 +954,7 @@ int uncached_readdir(nfs_readdir_descriptor_t *desc) if (status < 0) goto out_release; - status = nfs_do_filldir(desc); + nfs_do_filldir(desc); out_release: nfs_readdir_clear_array(desc->page); @@ -1032,10 +1029,8 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) if (res < 0) break; - res = nfs_do_filldir(desc); + nfs_do_filldir(desc); nfs_readdir_page_unlock_and_put_cached(desc); - if (res < 0) - break; } while (!desc->eof); spin_lock(&file->f_lock); @@ -1046,8 +1041,6 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) spin_unlock(&file->f_lock); out: - if (res > 0) - res = 0; dfprintk(FILE, "NFS: readdir(%pD2) returns %d\n", file, res); return res; } From patchwork Wed Nov 4 16:16:33 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881499 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 5A3C7921 for ; Wed, 4 Nov 2020 16:27:20 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 372FC206DB for ; Wed, 4 Nov 2020 16:27:20 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="PrYCbf+f" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731224AbgKDQ1R (ORCPT ); Wed, 4 Nov 2020 11:27:17 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36152 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728999AbgKDQ1Q (ORCPT ); Wed, 4 Nov 2020 11:27:16 -0500 Received: from mail-qk1-x742.google.com (mail-qk1-x742.google.com [IPv6:2607:f8b0:4864:20::742]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id CBEA7C0613D3 for ; Wed, 4 Nov 2020 08:27:15 -0800 (PST) Received: by mail-qk1-x742.google.com with SMTP id x20so19839228qkn.1 for ; Wed, 04 Nov 2020 08:27:15 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=t7Ey1sfa1pwR5vNbG6pigwJU2WMDmtROpcMLzXcWqGE=; b=PrYCbf+fhQLGh2UTr8Rv1yRCaAWw1TF/IMrx1ilHv/4UA64DU5zgyeI5nfVauJoiph m6wMjQpM80bgvG5XYUEEeOk03CtkXLkXuS5HGzdLt3ZfUHpm5YUzZbZmUhWQBJuS3cMV HwYXQ7N3Xb2DpmFZ9RG+qQCT9NASbkNmFKCg8gMkPH7tEmPAEHjBninB7F4CrxOAxicW H7CBe51xfaYssYwgrRzZk0ejjp8CmMiEuzgV9Lsxx/0Kbnvp+tbS8JZXrlRqfrVhAqUK b/Jo/kkxwOVWp9AECjbCsH21Tvt4AvbhqGy/pPlCSxy+Q6kULevQxBpji4c7kRLeT8aF XDmA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=t7Ey1sfa1pwR5vNbG6pigwJU2WMDmtROpcMLzXcWqGE=; b=XWH6z3duZ5JXqjGqsL6+2ak7BCwyRPsQYZwy8vNvhp/y2vSrMFy4tj8Y52yLroTVD0 1mUmCB6FF3reKG+9ENeVrP7YtHgEFYSTOR1Rm/bAM7mDK7ONosgmPTACs90s+4+p7kP0 K64KCPMX+DJc6LhzSQ+glr28a3JlyucfXYhliAyi7Xr+fY7+RQxTsMSpIYwZp35d9KM+ BYvDG4BwwsWyB23MEh3c19JLmrqsH4H3CHZ94IARNiJyhxSxzWhGYbALs0N7TC8ty1O/ zyb5WNOhlsIDLaSM5J9uneTqhAwhSCRhLIaTU7+BnVA+A179gxXsH5g5LsGx1ynMsfGn +OtA== X-Gm-Message-State: AOAM530gwc0CDg4c940fAGK4tbXzF8/eCkQT51bYjpq5NacwLHkuemQ4 vV2YADsrbwZG1Hy3zAlLMbWwayPGv3Zg X-Google-Smtp-Source: ABdhPJzyn7XImTdpts21rpRFfctLbyYixB1CJWdKSmyd8LSDGvvMEv9mM2tYMcNiBx+0rK2Tdbfs1Q== X-Received: by 2002:a37:a68b:: with SMTP id p133mr24853911qke.272.1604507234714; Wed, 04 Nov 2020 08:27:14 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.13 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:13 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 12/17] NFS: Reduce readdir stack usage Date: Wed, 4 Nov 2020 11:16:33 -0500 Message-Id: <20201104161638.300324-13-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-12-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> <20201104161638.300324-8-trond.myklebust@hammerspace.com> <20201104161638.300324-9-trond.myklebust@hammerspace.com> <20201104161638.300324-10-trond.myklebust@hammerspace.com> <20201104161638.300324-11-trond.myklebust@hammerspace.com> <20201104161638.300324-12-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust The descriptor and the struct nfs_entry are both large structures, so don't allocate them from the stack. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 58 ++++++++++++++++++++++++++++++---------------------- 1 file changed, 33 insertions(+), 25 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 48856cee10de..c3af54640f6c 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -761,23 +761,24 @@ static int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, struct inode *inode) { struct page **pages; - struct nfs_entry entry; + struct nfs_entry *entry; size_t array_size; size_t dtsize = NFS_SERVER(inode)->dtsize; int status = -ENOMEM; - entry.prev_cookie = 0; - entry.cookie = nfs_readdir_page_last_cookie(page); - entry.eof = 0; - entry.fh = nfs_alloc_fhandle(); - entry.fattr = nfs_alloc_fattr(); - entry.server = NFS_SERVER(inode); - if (entry.fh == NULL || entry.fattr == NULL) + entry = kzalloc(sizeof(*entry), GFP_KERNEL); + if (!entry) + return -ENOMEM; + entry->cookie = nfs_readdir_page_last_cookie(page); + entry->fh = nfs_alloc_fhandle(); + entry->fattr = nfs_alloc_fattr(); + entry->server = NFS_SERVER(inode); + if (entry->fh == NULL || entry->fattr == NULL) goto out; - entry.label = nfs4_label_alloc(NFS_SERVER(inode), GFP_NOWAIT); - if (IS_ERR(entry.label)) { - status = PTR_ERR(entry.label); + entry->label = nfs4_label_alloc(NFS_SERVER(inode), GFP_NOWAIT); + if (IS_ERR(entry->label)) { + status = PTR_ERR(entry->label); goto out; } @@ -788,7 +789,7 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, do { unsigned int pglen; - status = nfs_readdir_xdr_filler(desc, entry.cookie, + status = nfs_readdir_xdr_filler(desc, entry->cookie, pages, dtsize); if (status < 0) break; @@ -799,15 +800,16 @@ int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, break; } - status = nfs_readdir_page_filler(desc, &entry, pages, page, pglen); + status = nfs_readdir_page_filler(desc, entry, pages, page, pglen); } while (!status && nfs_readdir_page_needs_filling(page)); nfs_readdir_free_pages(pages, array_size); out_release_label: - nfs4_label_free(entry.label); + nfs4_label_free(entry->label); out: - nfs_free_fattr(entry.fattr); - nfs_free_fhandle(entry.fh); + nfs_free_fattr(entry->fattr); + nfs_free_fhandle(entry->fh); + kfree(entry); return status; } @@ -974,13 +976,8 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) struct dentry *dentry = file_dentry(file); struct inode *inode = d_inode(dentry); struct nfs_open_dir_context *dir_ctx = file->private_data; - nfs_readdir_descriptor_t my_desc = { - .file = file, - .ctx = ctx, - .plus = nfs_use_readdirplus(inode, ctx), - }, - *desc = &my_desc; - int res = 0; + struct nfs_readdir_descriptor *desc; + int res; dfprintk(FILE, "NFS: readdir(%pD2) starting at cookie %llu\n", file, (long long)ctx->pos); @@ -992,10 +989,19 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) * to either find the entry with the appropriate number or * revalidate the cookie. */ - if (ctx->pos == 0 || nfs_attribute_cache_expired(inode)) + if (ctx->pos == 0 || nfs_attribute_cache_expired(inode)) { res = nfs_revalidate_mapping(inode, file->f_mapping); - if (res < 0) + if (res < 0) + goto out; + } + + res = -ENOMEM; + desc = kzalloc(sizeof(*desc), GFP_KERNEL); + if (!desc) goto out; + desc->file = file; + desc->ctx = ctx; + desc->plus = nfs_use_readdirplus(inode, ctx); spin_lock(&file->f_lock); desc->dir_cookie = dir_ctx->dir_cookie; @@ -1040,6 +1046,8 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) dir_ctx->attr_gencount = desc->attr_gencount; spin_unlock(&file->f_lock); + kfree(desc); + out: dfprintk(FILE, "NFS: readdir(%pD2) returns %d\n", file, res); return res; From patchwork Wed Nov 4 16:16:34 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881505 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id B70D414C0 for ; Wed, 4 Nov 2020 16:27:21 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 91B892072E for ; Wed, 4 Nov 2020 16:27:21 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="Ckzl4S2c" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731221AbgKDQ1T (ORCPT ); Wed, 4 Nov 2020 11:27:19 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36156 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1728999AbgKDQ1R (ORCPT ); Wed, 4 Nov 2020 11:27:17 -0500 Received: from mail-qk1-x742.google.com (mail-qk1-x742.google.com [IPv6:2607:f8b0:4864:20::742]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id E47F7C0613D3 for ; Wed, 4 Nov 2020 08:27:16 -0800 (PST) Received: by mail-qk1-x742.google.com with SMTP id i21so19073529qka.12 for ; Wed, 04 Nov 2020 08:27:16 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=cZM9YC5VCcFCPCuH5Bz4/PhkiBSQ+y7wr39iOdBSmjo=; b=Ckzl4S2c/jN/UGwqkpsuaUKKdXj48WVKEMVbaKqCMr4Ajm624BVrt5h2g9qy0U8TzL Q3uxSE0TV81SBuFFdnmIk41w0wht0Ckl41WZ1QzBsfaVqVH59i0eU3brZ3TD9z43PU6o kN8NwnLY+mffbCo5rzTdK62UCBxRmGl88yCd1zp05b2OpftQpfMYvpay0U7+WxYOwHWJ ZglG19v5bEliR3uRj1tEvEbQg0lJMLghZWL91wCFEAvN0Ndz/OIgra+YJchpHj/5jhoh rLMEn9F50HzYhjEzOxrkGpzNA4n5JZUaV3IZBTtTC0SWTVtO0SaRrsr8S7bqoPrxgo8i XmTA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=cZM9YC5VCcFCPCuH5Bz4/PhkiBSQ+y7wr39iOdBSmjo=; b=W1OrgfQeXWPERd/KIi92PiPT1Vw09juoJGiFPvPBh9JD9Lf3IfdKnXoazRDTz9itF/ Q7ixT6LXcChK4N2POxNmuYvhZY7NK9rgnSUr/NlLMKi9YeYtSwUD9h8xxTjYgnN+d0mo 3ef04waPppD2SkUSIHrOJ19cRh6OHm12L8PxoNJ4cdMd+KFWlCYtFKovFHHiQtNdYiIK X+0v3VY00hGbFyr2TZ8jZJCgihZalhpsV5LyjAf5JY05/xbi16hve2lOpbKnPGpFlnSC pG9Txq7GeL6wO2RsLH5V4Yi55JQ4AVvYbwRodIwuZdlOa7DtYjxp6NKd01oIMt8Lz7z/ 79Bw== X-Gm-Message-State: AOAM5323GHq48jlCUlBn+v8l6Zu9u6+9HYiOYmPAtqJmOjTb20q5czKm 02fT2yggkBosnAHgBmljdVyRM/JqxVjr X-Google-Smtp-Source: ABdhPJyVE8/9mGRTKWT89bzSZ7kZqgkGTYiJQSnQlgSguTRsmW4CqSpz9WeWmRHkXJpS1CH9YeJWLA== X-Received: by 2002:a37:76c7:: with SMTP id r190mr25676564qkc.416.1604507235852; Wed, 04 Nov 2020 08:27:15 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.14 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:15 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 13/17] NFS: Cleanup to remove nfs_readdir_descriptor_t typedef Date: Wed, 4 Nov 2020 11:16:34 -0500 Message-Id: <20201104161638.300324-14-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-13-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> <20201104161638.300324-8-trond.myklebust@hammerspace.com> <20201104161638.300324-9-trond.myklebust@hammerspace.com> <20201104161638.300324-10-trond.myklebust@hammerspace.com> <20201104161638.300324-11-trond.myklebust@hammerspace.com> <20201104161638.300324-12-trond.myklebust@hammerspace.com> <20201104161638.300324-13-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 30 +++++++++++++----------------- 1 file changed, 13 insertions(+), 17 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index c3af54640f6c..b226f6f3ae96 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -144,7 +144,7 @@ struct nfs_cache_array { struct nfs_cache_array_entry array[]; }; -typedef struct nfs_readdir_descriptor { +struct nfs_readdir_descriptor { struct file *file; struct page *page; struct dir_context *ctx; @@ -163,7 +163,7 @@ typedef struct nfs_readdir_descriptor { signed char duped; bool plus; bool eof; -} nfs_readdir_descriptor_t; +}; static void nfs_readdir_array_init(struct nfs_cache_array *array) { @@ -362,8 +362,8 @@ bool nfs_readdir_use_cookie(const struct file *filp) return true; } -static -int nfs_readdir_search_for_pos(struct nfs_cache_array *array, nfs_readdir_descriptor_t *desc) +static int nfs_readdir_search_for_pos(struct nfs_cache_array *array, + struct nfs_readdir_descriptor *desc) { loff_t diff = desc->ctx->pos - desc->current_index; unsigned int index; @@ -394,8 +394,8 @@ nfs_readdir_inode_mapping_valid(struct nfs_inode *nfsi) return !test_bit(NFS_INO_INVALIDATING, &nfsi->flags); } -static -int nfs_readdir_search_for_cookie(struct nfs_cache_array *array, nfs_readdir_descriptor_t *desc) +static int nfs_readdir_search_for_cookie(struct nfs_cache_array *array, + struct nfs_readdir_descriptor *desc) { int i; loff_t new_pos; @@ -443,8 +443,7 @@ int nfs_readdir_search_for_cookie(struct nfs_cache_array *array, nfs_readdir_des return status; } -static -int nfs_readdir_search_array(nfs_readdir_descriptor_t *desc) +static int nfs_readdir_search_array(struct nfs_readdir_descriptor *desc) { struct nfs_cache_array *array; int status; @@ -497,7 +496,7 @@ static int nfs_readdir_xdr_filler(struct nfs_readdir_descriptor *desc, return error; } -static int xdr_decode(nfs_readdir_descriptor_t *desc, +static int xdr_decode(struct nfs_readdir_descriptor *desc, struct nfs_entry *entry, struct xdr_stream *xdr) { struct inode *inode = file_inode(desc->file); @@ -757,8 +756,8 @@ static struct page **nfs_readdir_alloc_pages(size_t npages) return NULL; } -static -int nfs_readdir_xdr_to_array(nfs_readdir_descriptor_t *desc, struct page *page, struct inode *inode) +static int nfs_readdir_xdr_to_array(struct nfs_readdir_descriptor *desc, + struct page *page, struct inode *inode) { struct page **pages; struct nfs_entry *entry; @@ -838,8 +837,7 @@ nfs_readdir_page_get_cached(struct nfs_readdir_descriptor *desc) * Returns 0 if desc->dir_cookie was found on page desc->page_index * and locks the page to prevent removal from the page cache. */ -static -int find_and_lock_cache_page(nfs_readdir_descriptor_t *desc) +static int find_and_lock_cache_page(struct nfs_readdir_descriptor *desc) { struct inode *inode = file_inode(desc->file); struct nfs_inode *nfsi = NFS_I(inode); @@ -864,8 +862,7 @@ int find_and_lock_cache_page(nfs_readdir_descriptor_t *desc) } /* Search for desc->dir_cookie from the beginning of the page cache */ -static inline -int readdir_search_pagecache(nfs_readdir_descriptor_t *desc) +static int readdir_search_pagecache(struct nfs_readdir_descriptor *desc) { int res; @@ -930,8 +927,7 @@ static void nfs_do_filldir(struct nfs_readdir_descriptor *desc) * we should already have a complete representation of the * directory in the page cache by the time we get here. */ -static inline -int uncached_readdir(nfs_readdir_descriptor_t *desc) +static int uncached_readdir(struct nfs_readdir_descriptor *desc) { struct page *page = NULL; int status; From patchwork Wed Nov 4 16:16:35 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881503 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 13E1614B4 for ; Wed, 4 Nov 2020 16:27:21 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id CE5CC206DB for ; Wed, 4 Nov 2020 16:27:20 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="goC2go9e" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728999AbgKDQ1U (ORCPT ); Wed, 4 Nov 2020 11:27:20 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36162 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726344AbgKDQ1S (ORCPT ); Wed, 4 Nov 2020 11:27:18 -0500 Received: from mail-qt1-x841.google.com (mail-qt1-x841.google.com [IPv6:2607:f8b0:4864:20::841]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 0DD8AC0613D3 for ; Wed, 4 Nov 2020 08:27:18 -0800 (PST) Received: by mail-qt1-x841.google.com with SMTP id h12so12609584qtu.1 for ; Wed, 04 Nov 2020 08:27:18 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=uitkgNsrQ+w9e0WKoHTLsIeCU2ez8dbftYaDmCFKgG4=; b=goC2go9e2xQQwnPog8gICjfX1ws2yIDu/gcGxcTwkAhr4qp2EtadZ8wqGGsmoDgVuU QI4cTGE+xhH9N+rRNdZKfGHz3K3lFEfPEOUaVNcEPBGUu/yz6W5nuN/0uU9/D2LYvhCU fS21E+UfLYCIGoOovDLrDGZxyWQPqM+TsansWsVroUKLdZqfdpeAFopN+JNkMneScN3a qn32W1O8sOr0C3pLlvoN/mMH86SdIoE4M0Obus69Nf8IFwNpjbOr0t0kG3HvogSlt+T5 kLdQkgZ2FCILOiSFha16y3lCzy31RG2N0sT8BpokbjfWbcYPQnuz7UBkVXJTuZ7xCQwf 2m4Q== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=uitkgNsrQ+w9e0WKoHTLsIeCU2ez8dbftYaDmCFKgG4=; b=DZkDVNCDo932snwY/wI9+28h3yz+UKLRmTdvLughiI4/pqJrztpQidbtnzeKaHyXuh bAhaMAQMuFteSYHDMOiVBD08bD/edOExe7kd/Nq1xcLW7CgEz/ui/cQjrDvA2v9qpX2E qhrgDV6DIJTqjuC9SFSdtJO/EIs0egHG6W10umutu/YV30GqrIEl+9Z7n3pf1TmJFuo/ znSvO81R71C++JlEwRreI8w3Cth26/+OClaoiMakEaE5k3foqB549x4PsmpyELWRF/vv 0aBuTPKi/z7+W6b+IKH0N/wM77Ux+3/mDqSsnG7pnc3SWkwNiz+TJaUfU/QGXUZWMAAM Qqbg== X-Gm-Message-State: AOAM533kMjqghhIqPFWr+qpr88C4iSmWJqNgoojG2TDCz+adEyngW+OT 6g8DOe6qJBZ2gdUx/f4RP3wXpRQC4m1s X-Google-Smtp-Source: ABdhPJzURfWCT7XGWZYCpWQJj9tMTKpOt8YD0/E9PWC2Enaqdw0Hf6B8uyI/RMgzGTIfOuNtbo7B1Q== X-Received: by 2002:ac8:7391:: with SMTP id t17mr19866451qtp.289.1604507236822; Wed, 04 Nov 2020 08:27:16 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.15 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:16 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 14/17] NFS: Allow the NFS generic code to pass in a verifier to readdir Date: Wed, 4 Nov 2020 11:16:35 -0500 Message-Id: <20201104161638.300324-15-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-14-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> <20201104161638.300324-8-trond.myklebust@hammerspace.com> <20201104161638.300324-9-trond.myklebust@hammerspace.com> <20201104161638.300324-10-trond.myklebust@hammerspace.com> <20201104161638.300324-11-trond.myklebust@hammerspace.com> <20201104161638.300324-12-trond.myklebust@hammerspace.com> <20201104161638.300324-13-trond.myklebust@hammerspace.com> <20201104161638.300324-14-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust If we're ever going to allow support for servers that use the readdir verifier, then that use needs to be managed by the middle layers as those need to be able to reject cookies from other verifiers. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 23 ++++++++++++++++++----- fs/nfs/nfs3proc.c | 35 +++++++++++++++++------------------ fs/nfs/nfs4proc.c | 38 ++++++++++++++++++-------------------- fs/nfs/proc.c | 18 +++++++++--------- include/linux/nfs_xdr.h | 17 +++++++++++++++-- 5 files changed, 77 insertions(+), 54 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index b226f6f3ae96..3ee0668a9719 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -469,8 +469,20 @@ static int nfs_readdir_xdr_filler(struct nfs_readdir_descriptor *desc, u64 cookie, struct page **pages, size_t bufsize) { - struct file *file = desc->file; - struct inode *inode = file_inode(file); + struct inode *inode = file_inode(desc->file); + __be32 verf_res[2]; + struct nfs_readdir_arg arg = { + .dentry = file_dentry(desc->file), + .cred = desc->file->f_cred, + .verf = NFS_I(inode)->cookieverf, + .cookie = cookie, + .pages = pages, + .page_len = bufsize, + .plus = desc->plus, + }; + struct nfs_readdir_res res = { + .verf = verf_res, + }; unsigned long timestamp, gencount; int error; @@ -478,20 +490,21 @@ static int nfs_readdir_xdr_filler(struct nfs_readdir_descriptor *desc, timestamp = jiffies; gencount = nfs_inc_attr_generation_counter(); desc->dir_verifier = nfs_save_change_attribute(inode); - error = NFS_PROTO(inode)->readdir(file_dentry(file), file->f_cred, - cookie, pages, bufsize, desc->plus); + error = NFS_PROTO(inode)->readdir(&arg, &res); if (error < 0) { /* We requested READDIRPLUS, but the server doesn't grok it */ if (error == -ENOTSUPP && desc->plus) { NFS_SERVER(inode)->caps &= ~NFS_CAP_READDIRPLUS; clear_bit(NFS_INO_ADVISE_RDPLUS, &NFS_I(inode)->flags); - desc->plus = false; + desc->plus = arg.plus = false; goto again; } goto error; } desc->timestamp = timestamp; desc->gencount = gencount; + memcpy(NFS_I(inode)->cookieverf, res.verf, + sizeof(NFS_I(inode)->cookieverf)); error: return error; } diff --git a/fs/nfs/nfs3proc.c b/fs/nfs/nfs3proc.c index 6b66b73a50eb..5c4e23abc345 100644 --- a/fs/nfs/nfs3proc.c +++ b/fs/nfs/nfs3proc.c @@ -662,37 +662,36 @@ nfs3_proc_rmdir(struct inode *dir, const struct qstr *name) * Also note that this implementation handles both plain readdir and * readdirplus. */ -static int -nfs3_proc_readdir(struct dentry *dentry, const struct cred *cred, - u64 cookie, struct page **pages, unsigned int count, bool plus) +static int nfs3_proc_readdir(struct nfs_readdir_arg *nr_arg, + struct nfs_readdir_res *nr_res) { - struct inode *dir = d_inode(dentry); - __be32 *verf = NFS_I(dir)->cookieverf; + struct inode *dir = d_inode(nr_arg->dentry); struct nfs3_readdirargs arg = { .fh = NFS_FH(dir), - .cookie = cookie, - .verf = {verf[0], verf[1]}, - .plus = plus, - .count = count, - .pages = pages + .cookie = nr_arg->cookie, + .plus = nr_arg->plus, + .count = nr_arg->page_len, + .pages = nr_arg->pages }; struct nfs3_readdirres res = { - .verf = verf, - .plus = plus + .verf = nr_res->verf, + .plus = nr_arg->plus, }; struct rpc_message msg = { .rpc_proc = &nfs3_procedures[NFS3PROC_READDIR], .rpc_argp = &arg, .rpc_resp = &res, - .rpc_cred = cred, + .rpc_cred = nr_arg->cred, }; int status = -ENOMEM; - if (plus) + if (nr_arg->plus) msg.rpc_proc = &nfs3_procedures[NFS3PROC_READDIRPLUS]; + if (arg.cookie) + memcpy(arg.verf, nr_arg->verf, sizeof(arg.verf)); - dprintk("NFS call readdir%s %d\n", - plus? "plus" : "", (unsigned int) cookie); + dprintk("NFS call readdir%s %llu\n", nr_arg->plus ? "plus" : "", + (unsigned long long)nr_arg->cookie); res.dir_attr = nfs_alloc_fattr(); if (res.dir_attr == NULL) @@ -705,8 +704,8 @@ nfs3_proc_readdir(struct dentry *dentry, const struct cred *cred, nfs_free_fattr(res.dir_attr); out: - dprintk("NFS reply readdir%s: %d\n", - plus? "plus" : "", status); + dprintk("NFS reply readdir%s: %d\n", nr_arg->plus ? "plus" : "", + status); return status; } diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index a5b9356bee6a..8e82f988a11f 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c @@ -4961,35 +4961,34 @@ static int nfs4_proc_mkdir(struct inode *dir, struct dentry *dentry, return err; } -static int _nfs4_proc_readdir(struct dentry *dentry, const struct cred *cred, - u64 cookie, struct page **pages, unsigned int count, bool plus) +static int _nfs4_proc_readdir(struct nfs_readdir_arg *nr_arg, + struct nfs_readdir_res *nr_res) { - struct inode *dir = d_inode(dentry); + struct inode *dir = d_inode(nr_arg->dentry); struct nfs4_readdir_arg args = { .fh = NFS_FH(dir), - .pages = pages, + .pages = nr_arg->pages, .pgbase = 0, - .count = count, - .bitmask = NFS_SERVER(d_inode(dentry))->attr_bitmask, - .plus = plus, + .count = nr_arg->page_len, + .bitmask = NFS_SERVER(d_inode(nr_arg->dentry))->attr_bitmask, + .plus = nr_arg->plus, }; struct nfs4_readdir_res res; struct rpc_message msg = { .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_READDIR], .rpc_argp = &args, .rpc_resp = &res, - .rpc_cred = cred, + .rpc_cred = nr_arg->cred, }; int status; - dprintk("%s: dentry = %pd2, cookie = %Lu\n", __func__, - dentry, - (unsigned long long)cookie); - nfs4_setup_readdir(cookie, NFS_I(dir)->cookieverf, dentry, &args); + dprintk("%s: dentry = %pd2, cookie = %llu\n", __func__, + nr_arg->dentry, (unsigned long long)nr_arg->cookie); + nfs4_setup_readdir(nr_arg->cookie, nr_arg->verf, nr_arg->dentry, &args); res.pgbase = args.pgbase; status = nfs4_call_sync(NFS_SERVER(dir)->client, NFS_SERVER(dir), &msg, &args.seq_args, &res.seq_res, 0); if (status >= 0) { - memcpy(NFS_I(dir)->cookieverf, res.verifier.data, NFS4_VERIFIER_SIZE); + memcpy(nr_res->verf, res.verifier.data, NFS4_VERIFIER_SIZE); status += args.pgbase; } @@ -4999,19 +4998,18 @@ static int _nfs4_proc_readdir(struct dentry *dentry, const struct cred *cred, return status; } -static int nfs4_proc_readdir(struct dentry *dentry, const struct cred *cred, - u64 cookie, struct page **pages, unsigned int count, bool plus) +static int nfs4_proc_readdir(struct nfs_readdir_arg *arg, + struct nfs_readdir_res *res) { struct nfs4_exception exception = { .interruptible = true, }; int err; do { - err = _nfs4_proc_readdir(dentry, cred, cookie, - pages, count, plus); - trace_nfs4_readdir(d_inode(dentry), err); - err = nfs4_handle_exception(NFS_SERVER(d_inode(dentry)), err, - &exception); + err = _nfs4_proc_readdir(arg, res); + trace_nfs4_readdir(d_inode(arg->dentry), err); + err = nfs4_handle_exception(NFS_SERVER(d_inode(arg->dentry)), + err, &exception); } while (exception.retry); return err; } diff --git a/fs/nfs/proc.c b/fs/nfs/proc.c index 15c865cc837f..73ab7c59d3a7 100644 --- a/fs/nfs/proc.c +++ b/fs/nfs/proc.c @@ -499,26 +499,26 @@ nfs_proc_rmdir(struct inode *dir, const struct qstr *name) * sure it is syntactically correct; the entries itself are decoded * from nfs_readdir by calling the decode_entry function directly. */ -static int -nfs_proc_readdir(struct dentry *dentry, const struct cred *cred, - u64 cookie, struct page **pages, unsigned int count, bool plus) +static int nfs_proc_readdir(struct nfs_readdir_arg *nr_arg, + struct nfs_readdir_res *nr_res) { - struct inode *dir = d_inode(dentry); + struct inode *dir = d_inode(nr_arg->dentry); struct nfs_readdirargs arg = { .fh = NFS_FH(dir), - .cookie = cookie, - .count = count, - .pages = pages, + .cookie = nr_arg->cookie, + .count = nr_arg->page_len, + .pages = nr_arg->pages, }; struct rpc_message msg = { .rpc_proc = &nfs_procedures[NFSPROC_READDIR], .rpc_argp = &arg, - .rpc_cred = cred, + .rpc_cred = nr_arg->cred, }; int status; - dprintk("NFS call readdir %d\n", (unsigned int)cookie); + dprintk("NFS call readdir %llu\n", (unsigned long long)nr_arg->cookie); status = rpc_call_sync(NFS_CLIENT(dir), &msg, 0); + nr_res->verf[0] = nr_res->verf[1] = 0; nfs_invalidate_atime(dir); diff --git a/include/linux/nfs_xdr.h b/include/linux/nfs_xdr.h index d63cb862d58e..3327239fa2f9 100644 --- a/include/linux/nfs_xdr.h +++ b/include/linux/nfs_xdr.h @@ -750,6 +750,20 @@ struct nfs_entry { struct nfs_server * server; }; +struct nfs_readdir_arg { + struct dentry *dentry; + const struct cred *cred; + __be32 *verf; + u64 cookie; + struct page **pages; + unsigned int page_len; + bool plus; +}; + +struct nfs_readdir_res { + __be32 *verf; +}; + /* * The following types are for NFSv2 only. */ @@ -1744,8 +1758,7 @@ struct nfs_rpc_ops { unsigned int, struct iattr *); int (*mkdir) (struct inode *, struct dentry *, struct iattr *); int (*rmdir) (struct inode *, const struct qstr *); - int (*readdir) (struct dentry *, const struct cred *, - u64, struct page **, unsigned int, bool); + int (*readdir) (struct nfs_readdir_arg *, struct nfs_readdir_res *); int (*mknod) (struct inode *, struct dentry *, struct iattr *, dev_t); int (*statfs) (struct nfs_server *, struct nfs_fh *, From patchwork Wed Nov 4 16:16:36 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881507 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 78BCA14B4 for ; Wed, 4 Nov 2020 16:27:22 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 53C5B206D9 for ; Wed, 4 Nov 2020 16:27:22 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="c5LFuR0x" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731230AbgKDQ1V (ORCPT ); Wed, 4 Nov 2020 11:27:21 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36166 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1731220AbgKDQ1T (ORCPT ); Wed, 4 Nov 2020 11:27:19 -0500 Received: from mail-qt1-x844.google.com (mail-qt1-x844.google.com [IPv6:2607:f8b0:4864:20::844]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 2DC1CC0613D4 for ; Wed, 4 Nov 2020 08:27:19 -0800 (PST) Received: by mail-qt1-x844.google.com with SMTP id t5so4018109qtp.2 for ; Wed, 04 Nov 2020 08:27:19 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=XfoodEipPydo9i+BM5Q0PHWBV4Ukm2TC8rEaUOKmKGU=; b=c5LFuR0xu7tnPGhwUhonmGCH48vJeklIv2F+DzJ2Xd/wJU4fO7TCuITsYrd8zEfZYS jHFjpcsABRxSyRLkAKGz1FNDCnGmXbQqhv18obkyfKlTcLheBJFq/JeCdkYqsoD/rfyu l4inuU+7UYk1bhqaHxNfToFLfXs3htkn7YRcUrU1HeF9T55HZ+zW9aw7crmMd8ZU8n5p weAcOyrDLGpi/s0YHcuR4Yzj+cYkliPaXoLb6xGA3XNc3zW5clMiH4xgxMMpFoYwLO7E YEatgcRk7rtlzsq0MELwmOEY25m6EVbyjLZr6SsulU4X4lcWMZjKgWVWu2Y2f/CiZYey +1ng== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=XfoodEipPydo9i+BM5Q0PHWBV4Ukm2TC8rEaUOKmKGU=; b=cRDJJQBoTuwgRLvlW3SNcZ0i4ugn5xjSxhs8y/OBibvmpcW49n/Oi8JZTrq8hBfErp yVN+CT0r0La+soxlTo0JTUkheq+PCHPtycwPyZRnfNWcyGJ6sHrONHtxeLKGL6yhjb8I WFaghaIeHp4RorFOBHbPZarinSNyDgOoHmElIVKG48ccEkMzr1Y2RS6d28i9lBajcnFS MajaPRUKTYg7r2NBrciESUzmAEh1NXIXvZ56ZTxkGszPeXoOLpng7vWbQYnpG0ddLsrD iL3P3iKlxaNNTO5ivGm5mggtNGhf/1yxmqRQ9rWicgrbE++xe5ersCtZodYILFplPgJb /x+w== X-Gm-Message-State: AOAM531hHyyRZu2jM+oAiBTWEGQiGTfg9hK7BQosvyLRL7d3vOwK8t1a PrRNCEOBYSkDMfGG2UsljfOPp1RGl76D X-Google-Smtp-Source: ABdhPJziy6+iYGK07xGAqDo7lQ5ZoETPEKwIoOHhYGAnpE9v8rqpv33yuJDNzg/QkU4eokjTu7NYyw== X-Received: by 2002:ac8:5942:: with SMTP id 2mr12264676qtz.183.1604507238095; Wed, 04 Nov 2020 08:27:18 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.16 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:17 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 15/17] NFS: Handle NFS4ERR_NOT_SAME and NFSERR_BADCOOKIE from readdir calls Date: Wed, 4 Nov 2020 11:16:36 -0500 Message-Id: <20201104161638.300324-16-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-15-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> <20201104161638.300324-8-trond.myklebust@hammerspace.com> <20201104161638.300324-9-trond.myklebust@hammerspace.com> <20201104161638.300324-10-trond.myklebust@hammerspace.com> <20201104161638.300324-11-trond.myklebust@hammerspace.com> <20201104161638.300324-12-trond.myklebust@hammerspace.com> <20201104161638.300324-13-trond.myklebust@hammerspace.com> <20201104161638.300324-14-trond.myklebust@hammerspace.com> <20201104161638.300324-15-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust If the server returns NFS4ERR_NOT_SAME or tells us that the cookie is bad in response to a READDIR call, then we should empty the page cache so that we can fill it from scratch again. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 24 ++++++++++++++++-------- fs/nfs/nfs4proc.c | 2 ++ 2 files changed, 18 insertions(+), 8 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 3ee0668a9719..3b44bef3a1b4 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -861,15 +861,21 @@ static int find_and_lock_cache_page(struct nfs_readdir_descriptor *desc) return -ENOMEM; if (nfs_readdir_page_needs_filling(desc->page)) { res = nfs_readdir_xdr_to_array(desc, desc->page, inode); - if (res < 0) - goto error; + if (res < 0) { + nfs_readdir_page_unlock_and_put_cached(desc); + if (res == -EBADCOOKIE || res == -ENOTSYNC) { + invalidate_inode_pages2(desc->file->f_mapping); + desc->page_index = 0; + return -EAGAIN; + } + return res; + } } res = nfs_readdir_search_array(desc); if (res == 0) { nfsi->page_index = desc->page_index; return 0; } -error: nfs_readdir_page_unlock_and_put_cached(desc); return res; } @@ -879,12 +885,12 @@ static int readdir_search_pagecache(struct nfs_readdir_descriptor *desc) { int res; - if (desc->page_index == 0) { - desc->current_index = 0; - desc->prev_index = 0; - desc->last_cookie = 0; - } do { + if (desc->page_index == 0) { + desc->current_index = 0; + desc->prev_index = 0; + desc->last_cookie = 0; + } res = find_and_lock_cache_page(desc); } while (res == -EAGAIN); return res; @@ -1030,6 +1036,8 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) res = uncached_readdir(desc); if (res == 0) continue; + if (res == -EBADCOOKIE || res == -ENOTSYNC) + res = 0; } break; } diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index 8e82f988a11f..3f1fdb06ba56 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c @@ -184,6 +184,8 @@ static int nfs4_map_errors(int err) return -EPROTONOSUPPORT; case -NFS4ERR_FILE_OPEN: return -EBUSY; + case -NFS4ERR_NOT_SAME: + return -ENOTSYNC; default: dprintk("%s could not handle NFSv4 error %d\n", __func__, -err); From patchwork Wed Nov 4 16:16:37 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881511 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 7F74714C0 for ; Wed, 4 Nov 2020 16:27:23 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 5A77F206D9 for ; Wed, 4 Nov 2020 16:27:23 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="R9rvG/lS" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1731220AbgKDQ1W (ORCPT ); Wed, 4 Nov 2020 11:27:22 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36172 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726344AbgKDQ1U (ORCPT ); Wed, 4 Nov 2020 11:27:20 -0500 Received: from mail-qt1-x841.google.com (mail-qt1-x841.google.com [IPv6:2607:f8b0:4864:20::841]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 46B9CC0613D3 for ; Wed, 4 Nov 2020 08:27:20 -0800 (PST) Received: by mail-qt1-x841.google.com with SMTP id g17so4101542qts.5 for ; Wed, 04 Nov 2020 08:27:20 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=8EbaX/h/3RCq01aTlbpXpFc+qXn4adW1WPgCbxfQhE8=; b=R9rvG/lS3IOKvgKuKmO5sWnHY/n/9bvPgxLbKRnqp2ROAXpav1qVX9707iZXgZOz4p p6hd3Zrjf/J8/jZXlWvKvsx+ISoLc3TKSDr5TAz05KkRzMel6zgUdCj/JL32ih7wQeHN w92IELNQ8l30MU859IwggHXlyxfNnDMQ225iq+i1cCw/Kpbhe0Zz8LnhFYL7uK+tMowb OfFMDgklGb4gmMXwZ4/9zl8iHdmaalfINVpbnAdoLiT58lpIwyKp2L21/ty/DGboHmBC G1RrUS6H2C7zt49Qc3QxwD62YMQsN7v3tcVGl2xNBKIW79mz5StbR9u+aD0LGU4NPhiO 0PCA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=8EbaX/h/3RCq01aTlbpXpFc+qXn4adW1WPgCbxfQhE8=; b=W78Z/RIFqhu5Szu+I+88usiz5ZUeHfWm4XUavxoZpqx+7omvAo1MAccbKH9t8X2GEm fpxBkMGvYXPxrHjWaxEUW9ESnZOkoHIZkQqyjKtjUOxKLAb8ml0s9pYDb6ZNYT+MzjXT gh8yiXYdzBwdm4+kEFsumwXVnO84SvmBh7TgJXvlq5WKIaE/AcPAMO3Ps0nrJkxKwiPp e2FYcR/DfCZybDDpE9m3/8APg3oEX06Wr4hlmUSngiRreZYJtJTLFtYgCyoEvxDsIfR/ e+nwe8USdnIko/uTUSDJQ3eGFa+J0BgO/gZ68nt2FT6QBJPprv54aLaDCoJBGz0PVEt/ Jp4A== X-Gm-Message-State: AOAM532fjVZUdJ+IUX8I+Uo/IppTqgAj/ClD+G3h5rYrfni5qGe8c0Py nMLXhH7hmXIjdmqtq/X5W6EZnGGOLOIw X-Google-Smtp-Source: ABdhPJwEGXzqiQHJ8x1eh0o9rP/z+Qq355grZlLW2ZHySyaKHThpDHGoqKXde2+FW7NMcRWTY7KmSg== X-Received: by 2002:aed:2d82:: with SMTP id i2mr10517509qtd.10.1604507239088; Wed, 04 Nov 2020 08:27:19 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.18 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:18 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 16/17] NFS: Improve handling of directory verifiers Date: Wed, 4 Nov 2020 11:16:37 -0500 Message-Id: <20201104161638.300324-17-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-16-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> <20201104161638.300324-8-trond.myklebust@hammerspace.com> <20201104161638.300324-9-trond.myklebust@hammerspace.com> <20201104161638.300324-10-trond.myklebust@hammerspace.com> <20201104161638.300324-11-trond.myklebust@hammerspace.com> <20201104161638.300324-12-trond.myklebust@hammerspace.com> <20201104161638.300324-13-trond.myklebust@hammerspace.com> <20201104161638.300324-14-trond.myklebust@hammerspace.com> <20201104161638.300324-15-trond.myklebust@hammerspace.com> <20201104161638.300324-16-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust If the server insists on using the readdir verifiers in order to allow cookies to expire, then we should ensure that we cache the verifier with the cookie, so that we can return an error if the application tries to use the expired cookie. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 35 +++++++++++++++++++++++------------ fs/nfs/inode.c | 7 ------- include/linux/nfs_fs.h | 8 +++++++- 3 files changed, 30 insertions(+), 20 deletions(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 3b44bef3a1b4..454377228167 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -155,6 +155,7 @@ struct nfs_readdir_descriptor { loff_t current_index; loff_t prev_index; + __be32 verf[NFS_DIR_VERIFIER_SIZE]; unsigned long dir_verifier; unsigned long timestamp; unsigned long gencount; @@ -466,15 +467,15 @@ static int nfs_readdir_search_array(struct nfs_readdir_descriptor *desc) /* Fill a page with xdr information before transferring to the cache page */ static int nfs_readdir_xdr_filler(struct nfs_readdir_descriptor *desc, - u64 cookie, struct page **pages, - size_t bufsize) + __be32 *verf, u64 cookie, + struct page **pages, size_t bufsize, + __be32 *verf_res) { struct inode *inode = file_inode(desc->file); - __be32 verf_res[2]; struct nfs_readdir_arg arg = { .dentry = file_dentry(desc->file), .cred = desc->file->f_cred, - .verf = NFS_I(inode)->cookieverf, + .verf = verf, .cookie = cookie, .pages = pages, .page_len = bufsize, @@ -503,8 +504,6 @@ static int nfs_readdir_xdr_filler(struct nfs_readdir_descriptor *desc, } desc->timestamp = timestamp; desc->gencount = gencount; - memcpy(NFS_I(inode)->cookieverf, res.verf, - sizeof(NFS_I(inode)->cookieverf)); error: return error; } @@ -770,11 +769,13 @@ static struct page **nfs_readdir_alloc_pages(size_t npages) } static int nfs_readdir_xdr_to_array(struct nfs_readdir_descriptor *desc, - struct page *page, struct inode *inode) + struct page *page, __be32 *verf_arg, + __be32 *verf_res) { struct page **pages; struct nfs_entry *entry; size_t array_size; + struct inode *inode = file_inode(desc->file); size_t dtsize = NFS_SERVER(inode)->dtsize; int status = -ENOMEM; @@ -801,8 +802,9 @@ static int nfs_readdir_xdr_to_array(struct nfs_readdir_descriptor *desc, do { unsigned int pglen; - status = nfs_readdir_xdr_filler(desc, entry->cookie, - pages, dtsize); + status = nfs_readdir_xdr_filler(desc, verf_arg, entry->cookie, + pages, dtsize, + verf_res); if (status < 0) break; @@ -854,13 +856,15 @@ static int find_and_lock_cache_page(struct nfs_readdir_descriptor *desc) { struct inode *inode = file_inode(desc->file); struct nfs_inode *nfsi = NFS_I(inode); + __be32 verf[NFS_DIR_VERIFIER_SIZE]; int res; desc->page = nfs_readdir_page_get_cached(desc); if (!desc->page) return -ENOMEM; if (nfs_readdir_page_needs_filling(desc->page)) { - res = nfs_readdir_xdr_to_array(desc, desc->page, inode); + res = nfs_readdir_xdr_to_array(desc, desc->page, + nfsi->cookieverf, verf); if (res < 0) { nfs_readdir_page_unlock_and_put_cached(desc); if (res == -EBADCOOKIE || res == -ENOTSYNC) { @@ -870,6 +874,7 @@ static int find_and_lock_cache_page(struct nfs_readdir_descriptor *desc) } return res; } + memcpy(nfsi->cookieverf, verf, sizeof(nfsi->cookieverf)); } res = nfs_readdir_search_array(desc); if (res == 0) { @@ -902,6 +907,7 @@ static int readdir_search_pagecache(struct nfs_readdir_descriptor *desc) static void nfs_do_filldir(struct nfs_readdir_descriptor *desc) { struct file *file = desc->file; + struct nfs_inode *nfsi = NFS_I(file_inode(file)); struct nfs_cache_array *array; unsigned int i = 0; @@ -915,6 +921,7 @@ static void nfs_do_filldir(struct nfs_readdir_descriptor *desc) desc->eof = true; break; } + memcpy(desc->verf, nfsi->cookieverf, sizeof(desc->verf)); if (i < (array->size-1)) desc->dir_cookie = array->array[i+1].cookie; else @@ -949,8 +956,8 @@ static void nfs_do_filldir(struct nfs_readdir_descriptor *desc) static int uncached_readdir(struct nfs_readdir_descriptor *desc) { struct page *page = NULL; + __be32 verf[NFS_DIR_VERIFIER_SIZE]; int status; - struct inode *inode = file_inode(desc->file); dfprintk(DIRCACHE, "NFS: uncached_readdir() searching for cookie %Lu\n", (unsigned long long)desc->dir_cookie); @@ -967,7 +974,7 @@ static int uncached_readdir(struct nfs_readdir_descriptor *desc) desc->duped = 0; nfs_readdir_page_init_array(page, desc->dir_cookie); - status = nfs_readdir_xdr_to_array(desc, page, inode); + status = nfs_readdir_xdr_to_array(desc, page, desc->verf, verf); if (status < 0) goto out_release; @@ -1023,6 +1030,7 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) desc->dup_cookie = dir_ctx->dup_cookie; desc->duped = dir_ctx->duped; desc->attr_gencount = dir_ctx->attr_gencount; + memcpy(desc->verf, dir_ctx->verf, sizeof(desc->verf)); spin_unlock(&file->f_lock); do { @@ -1061,6 +1069,7 @@ static int nfs_readdir(struct file *file, struct dir_context *ctx) dir_ctx->dup_cookie = desc->dup_cookie; dir_ctx->duped = desc->duped; dir_ctx->attr_gencount = desc->attr_gencount; + memcpy(dir_ctx->verf, desc->verf, sizeof(dir_ctx->verf)); spin_unlock(&file->f_lock); kfree(desc); @@ -1101,6 +1110,8 @@ static loff_t nfs_llseek_dir(struct file *filp, loff_t offset, int whence) dir_ctx->dir_cookie = offset; else dir_ctx->dir_cookie = 0; + if (offset == 0) + memset(dir_ctx->verf, 0, sizeof(dir_ctx->verf)); dir_ctx->duped = 0; } spin_unlock(&filp->f_lock); diff --git a/fs/nfs/inode.c b/fs/nfs/inode.c index aa6493905bbe..9b765a900b28 100644 --- a/fs/nfs/inode.c +++ b/fs/nfs/inode.c @@ -229,7 +229,6 @@ static void nfs_zap_caches_locked(struct inode *inode) nfsi->attrtimeo = NFS_MINATTRTIMEO(inode); nfsi->attrtimeo_timestamp = jiffies; - memset(NFS_I(inode)->cookieverf, 0, sizeof(NFS_I(inode)->cookieverf)); if (S_ISREG(mode) || S_ISDIR(mode) || S_ISLNK(mode)) { nfs_set_cache_invalid(inode, NFS_INO_INVALID_ATTR | NFS_INO_INVALID_DATA @@ -1237,7 +1236,6 @@ EXPORT_SYMBOL_GPL(nfs_revalidate_inode); static int nfs_invalidate_mapping(struct inode *inode, struct address_space *mapping) { - struct nfs_inode *nfsi = NFS_I(inode); int ret; if (mapping->nrpages != 0) { @@ -1250,11 +1248,6 @@ static int nfs_invalidate_mapping(struct inode *inode, struct address_space *map if (ret < 0) return ret; } - if (S_ISDIR(inode->i_mode)) { - spin_lock(&inode->i_lock); - memset(nfsi->cookieverf, 0, sizeof(nfsi->cookieverf)); - spin_unlock(&inode->i_lock); - } nfs_inc_stats(inode, NFSIOS_DATAINVALIDATE); nfs_fscache_wait_on_invalidate(inode); diff --git a/include/linux/nfs_fs.h b/include/linux/nfs_fs.h index dd6b463dda80..681ed98e4ba8 100644 --- a/include/linux/nfs_fs.h +++ b/include/linux/nfs_fs.h @@ -45,6 +45,11 @@ */ #define NFS_RPC_SWAPFLAGS (RPC_TASK_SWAPPER|RPC_TASK_ROOTCREDS) +/* + * Size of the NFS directory verifier + */ +#define NFS_DIR_VERIFIER_SIZE 2 + /* * NFSv3/v4 Access mode cache entry */ @@ -89,6 +94,7 @@ struct nfs_open_context { struct nfs_open_dir_context { struct list_head list; unsigned long attr_gencount; + __be32 verf[NFS_DIR_VERIFIER_SIZE]; __u64 dir_cookie; __u64 dup_cookie; signed char duped; @@ -156,7 +162,7 @@ struct nfs_inode { * This is the cookie verifier used for NFSv3 readdir * operations */ - __be32 cookieverf[2]; + __be32 cookieverf[NFS_DIR_VERIFIER_SIZE]; atomic_long_t nrequests; struct nfs_mds_commit_info commit_info; From patchwork Wed Nov 4 16:16:38 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 11881513 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id A47F014B4 for ; Wed, 4 Nov 2020 16:27:25 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 7F7A0206D9 for ; Wed, 4 Nov 2020 16:27:25 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="U9X8cxRg" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1730886AbgKDQ1Y (ORCPT ); Wed, 4 Nov 2020 11:27:24 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36176 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726344AbgKDQ1X (ORCPT ); Wed, 4 Nov 2020 11:27:23 -0500 Received: from mail-qv1-xf42.google.com (mail-qv1-xf42.google.com [IPv6:2607:f8b0:4864:20::f42]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 5F534C0613D3 for ; Wed, 4 Nov 2020 08:27:21 -0800 (PST) Received: by mail-qv1-xf42.google.com with SMTP id dj6so6183814qvb.3 for ; Wed, 04 Nov 2020 08:27:21 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=7PN4Vw59i214EUwCV4qZJILmXyvuZ2XbdjIb2vLc7fE=; b=U9X8cxRg9GbuExgMS7t2NBY/tlMPvf9/sjkDhBjgNWWh4xOlfQgAy6/c0lCATcyJDf 6XvbvHz/eSbmSiOu80K1NpcoHMdcqOwRuOR/9pBtTCZYf28FUlP9QAwqknznzp0SRNzu LxGsStOzX1m7ksJ3f1yANcya84/VRboEbopGN2X+KFpNeTI/eT/S0ze2ZFLdvkjOHpmq Euh6mIAy4/ielDVhJjYGUNdEOX13fzns0zpWv1dGQI8XBZOX4J/UsjfBLNXFRX3z44dP T5CET19lT4xc5SYqlq1QWldemIC/1BrAup+nixUfGq74w466aHNzC7To6lL4PfQXMoj8 GTZQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=7PN4Vw59i214EUwCV4qZJILmXyvuZ2XbdjIb2vLc7fE=; b=Rxp1uWiiJOopIg1Mkuap2Yw8oqbfysVnENw2XUyZAVKgVN9/4IlzSbpBFzow2RGHf8 nGzOf8/qQaixPJN0JM443OfMwDJx/0CFHOZxY+G1GbJP5y6jhMGl8ZHWu+AhdYJ8dSqT bDmjy9igMMiUKAHLIz3S5xLc5CicAB64cAykAgn9zq0IoU+NpWIX5UpFcxtcsTSsxLAn lSWaK8qdv1vd0SVoHl6XMjTdNfsyLS3lZWgRdeLgOj9rc4gXqd0aV/dQDL5k1e83d1Kq ts1SiK3oWBbR4DLwd4/6CpOgi/FnTb4oqYGyD7vMrSEwYjfY0h4KknKyxZ6vCeJ+LZAE lulQ== X-Gm-Message-State: AOAM532FGc4Z3W3gZCEh78XE89XF1S3m3UgjWC5ULHiWYTuy9czaQjnt 8TwFJnDwh2iGLOqRD03w1L64grR4YfFc X-Google-Smtp-Source: ABdhPJyv39HNcY+vbLpKPEPg1YC/R5WHpv3mpgfmYOC/4QJ6HfetsMOTlJ1s1ZeXf8Cutj3v5ijPrQ== X-Received: by 2002:a05:6214:18e8:: with SMTP id ep8mr18339651qvb.61.1604507240229; Wed, 04 Nov 2020 08:27:20 -0800 (PST) Received: from localhost.localdomain (c-68-36-133-222.hsd1.mi.comcast.net. [68.36.133.222]) by smtp.gmail.com with ESMTPSA id g78sm2896924qke.88.2020.11.04.08.27.19 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 04 Nov 2020 08:27:19 -0800 (PST) From: trondmy@gmail.com X-Google-Original-From: trond.myklebust@hammerspace.com To: linux-nfs@vger.kernel.org Subject: [PATCH v3 17/17] NFS: Optimisations for monotonically increasing readdir cookies Date: Wed, 4 Nov 2020 11:16:38 -0500 Message-Id: <20201104161638.300324-18-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.28.0 In-Reply-To: <20201104161638.300324-17-trond.myklebust@hammerspace.com> References: <20201104161638.300324-1-trond.myklebust@hammerspace.com> <20201104161638.300324-2-trond.myklebust@hammerspace.com> <20201104161638.300324-3-trond.myklebust@hammerspace.com> <20201104161638.300324-4-trond.myklebust@hammerspace.com> <20201104161638.300324-5-trond.myklebust@hammerspace.com> <20201104161638.300324-6-trond.myklebust@hammerspace.com> <20201104161638.300324-7-trond.myklebust@hammerspace.com> <20201104161638.300324-8-trond.myklebust@hammerspace.com> <20201104161638.300324-9-trond.myklebust@hammerspace.com> <20201104161638.300324-10-trond.myklebust@hammerspace.com> <20201104161638.300324-11-trond.myklebust@hammerspace.com> <20201104161638.300324-12-trond.myklebust@hammerspace.com> <20201104161638.300324-13-trond.myklebust@hammerspace.com> <20201104161638.300324-14-trond.myklebust@hammerspace.com> <20201104161638.300324-15-trond.myklebust@hammerspace.com> <20201104161638.300324-16-trond.myklebust@hammerspace.com> <20201104161638.300324-17-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org From: Trond Myklebust If the server is handing out monotonically increasing readdir cookie values, then we can optimise away searches through pages that contain cookies that lie outside our search range. Signed-off-by: Trond Myklebust --- fs/nfs/dir.c | 23 ++++++++++++++++++++++- 1 file changed, 22 insertions(+), 1 deletion(-) diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index 454377228167..b6c3501e8f61 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -140,7 +140,8 @@ struct nfs_cache_array { u64 last_cookie; unsigned int size; unsigned char page_full : 1, - page_is_eof : 1; + page_is_eof : 1, + cookies_are_ordered : 1; struct nfs_cache_array_entry array[]; }; @@ -178,6 +179,7 @@ static void nfs_readdir_page_init_array(struct page *page, u64 last_cookie) array = kmap_atomic(page); nfs_readdir_array_init(array); array->last_cookie = last_cookie; + array->cookies_are_ordered = 1; kunmap_atomic(array); } @@ -269,6 +271,8 @@ int nfs_readdir_add_to_array(struct nfs_entry *entry, struct page *page) cache_entry->name_len = entry->len; cache_entry->name = name; array->last_cookie = entry->cookie; + if (array->last_cookie <= cache_entry->cookie) + array->cookies_are_ordered = 0; array->size++; if (entry->eof != 0) nfs_readdir_array_set_eof(array); @@ -395,6 +399,19 @@ nfs_readdir_inode_mapping_valid(struct nfs_inode *nfsi) return !test_bit(NFS_INO_INVALIDATING, &nfsi->flags); } +static bool nfs_readdir_array_cookie_in_range(struct nfs_cache_array *array, + u64 cookie) +{ + if (!array->cookies_are_ordered) + return true; + /* Optimisation for monotonically increasing cookies */ + if (cookie >= array->last_cookie) + return false; + if (array->size && cookie < array->array[0].cookie) + return false; + return true; +} + static int nfs_readdir_search_for_cookie(struct nfs_cache_array *array, struct nfs_readdir_descriptor *desc) { @@ -402,6 +419,9 @@ static int nfs_readdir_search_for_cookie(struct nfs_cache_array *array, loff_t new_pos; int status = -EAGAIN; + if (!nfs_readdir_array_cookie_in_range(array, desc->dir_cookie)) + goto check_eof; + for (i = 0; i < array->size; i++) { if (array->array[i].cookie == desc->dir_cookie) { struct nfs_inode *nfsi = NFS_I(file_inode(desc->file)); @@ -435,6 +455,7 @@ static int nfs_readdir_search_for_cookie(struct nfs_cache_array *array, return 0; } } +check_eof: if (array->page_is_eof) { status = -EBADCOOKIE; if (desc->dir_cookie == array->last_cookie)