Received: by 10.192.165.148 with SMTP id m20csp2831353imm; Mon, 7 May 2018 01:50:13 -0700 (PDT) X-Google-Smtp-Source: AB8JxZq+gGLyuZt5+n9IYc8u8NHicRhftpnMh0jA8rj+DZuxNr0wCqScHAU9HsQdSa7hpxBE/TtA X-Received: by 10.98.189.24 with SMTP id a24mr35069923pff.30.1525683013852; Mon, 07 May 2018 01:50:13 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1525683013; cv=none; d=google.com; s=arc-20160816; b=p+Z5iCFcgvgDxQjpIbJ/VpjjT/7HcC0kWtlQnN3Khe8108F72uZ6SIT7zepbjFQNsz OFlbZwXWhzyBI3P56JwaOH22mIIrY9v0TVYrkiTd2AickmQJPq2MM8q1QnhzzjNYm/7h saa9F9kJKLKjePwsJn+MegOufTMkr+ZZesUxorKF9UuoxQoBJbWsU+FIC8fZKl91ZsZX gdF9JbUket2Foc9nw0LwD+EgLiNELN7tjoPhgzGn+veSMevU+JXLttEDGPOluszye05g ouJwjnyg/lqZzVxrLi9/0ya6uDnDkozw9LIkmVQ/JePz2jh5sBb3DCGSgHcmbI33zom4 zVAg== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:references:in-reply-to:message-id:date :subject:cc:to:from:arc-authentication-results; bh=t28YRwRGnAz5rkhSJhkqIpUFGu5tpsnKgArUU8nlD2g=; b=HdwZfCCeLe+/OIQ/fGyMugfsmwnmFuc0/aJrRc86kZpX0Gy9e2nlhAr8FnJbQNNKUV d7ysW8brWhlQDPRn4ugCPUWU6pPBN6/XTxd71AW1W9TSP7EFhVbMRLj7LuESChcc99Q/ K2x6cT4VXbO8E3/xtFRYZSQauR4Hnh1tzxK2rut9UoZU5Is2tNTUjJAHfpcewsMgptWp sT7BefGRvIepz34yxppHl3S7d4BEZIs9ebWHY//a2BIWyaInBlUrHz1r5uTGC+0TJ04a KJvZS01DfPnPDo1x9GcxQNlK1+jSQCKVsX39xBS/CwOy7gD92wslmA6XY30lL6cx5l3u Zb2w== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=redhat.com Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id 70-v6si21529446ple.372.2018.05.07.01.49.59; Mon, 07 May 2018 01:50:13 -0700 (PDT) Received-SPF: pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) client-ip=209.132.180.67; Authentication-Results: mx.google.com; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=redhat.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1752627AbeEGItg (ORCPT + 99 others); Mon, 7 May 2018 04:49:36 -0400 Received: from mail-wm0-f66.google.com ([74.125.82.66]:38536 "EHLO mail-wm0-f66.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751940AbeEGIiQ (ORCPT ); Mon, 7 May 2018 04:38:16 -0400 Received: by mail-wm0-f66.google.com with SMTP id m198-v6so13049800wmg.3 for ; Mon, 07 May 2018 01:38:15 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=t28YRwRGnAz5rkhSJhkqIpUFGu5tpsnKgArUU8nlD2g=; b=A7fkSXWhOTXK1syzGWHGT6vQEKFMSsQIjPTcBafNzyUDJPHxp1erl+DYSXHLJFGobo NTcuqkCPPo+DCBiO/r0FkKlwbouY0+99iKujoFqWG+h3WwHFfoTBBtRDwGfX4NjrXOR+ kA4AJ3Hrje5jEKrNNCmCk5uIl5yLv/yiIgKB6+sW9+NMAVn01lOubhdgQFS4idtX0HDU sHe3j+VfWDYfILy9oM2SA7iKEuGo5eUVzHTwFywb9Qjhnc3Y43WCGWvwh09VwjYbt+M8 6icAtfymMWCvQly95UstTJF6TLvPY1Jd1r4Z0JUYU3xrvI8RKAfNG0wKg0ehICIwKTD1 1k0g== X-Gm-Message-State: ALQs6tDBLPJU4SN2va4Xzk0gEAMr1bIVGwnhGM88Eawsr80LpyP9zlxy izVNzg2DeDNkd3WoTBvF5KBd7Q== X-Received: by 2002:a1c:170f:: with SMTP id 15-v6mr179705wmx.90.1525682294855; Mon, 07 May 2018 01:38:14 -0700 (PDT) Received: from veci.piliscsaba.redhat.com (C2B0E321.catv.pool.telekom.hu. [194.176.227.33]) by smtp.gmail.com with ESMTPSA id h8-v6sm5908050wmc.16.2018.05.07.01.38.13 (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Mon, 07 May 2018 01:38:14 -0700 (PDT) From: Miklos Szeredi To: linux-unionfs@vger.kernel.org Cc: linux-fsdevel@vger.kernel.org, linux-kernel@vger.kernel.org, Al Viro Subject: [PATCH v2 02/35] vfs: optionally don't account file in nr_files Date: Mon, 7 May 2018 10:37:34 +0200 Message-Id: <20180507083807.28792-3-mszeredi@redhat.com> X-Mailer: git-send-email 2.14.3 In-Reply-To: <20180507083807.28792-1-mszeredi@redhat.com> References: <20180507083807.28792-1-mszeredi@redhat.com> Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Stacking file operations in overlay will store an extra open file for each overlay file opened. The overhead is just that of "struct file" which is about 256bytes, because overlay already pins an extra dentry and inode when the file is open, which add up to a much larger overhead. For fear of breaking working setups, don't start accounting the extra file. The implementation adds a bool argument to path_open() to control whether the returned file is to be accounted or not. If the file is not accounted, f_mode will contain FMODE_NOACCOUNT, so that when freeing the file the count is not decremented. Signed-off-by: Miklos Szeredi --- fs/file_table.c | 13 +++++++++---- fs/internal.h | 7 ++++++- fs/open.c | 10 +++++----- include/linux/fs.h | 5 ++++- 4 files changed, 24 insertions(+), 11 deletions(-) diff --git a/fs/file_table.c b/fs/file_table.c index 7ec0b3e5f05d..60376bfa04cf 100644 --- a/fs/file_table.c +++ b/fs/file_table.c @@ -51,7 +51,8 @@ static void file_free_rcu(struct rcu_head *head) static inline void file_free(struct file *f) { - percpu_counter_dec(&nr_files); + if (!(f->f_mode & FMODE_NOACCOUNT)) + percpu_counter_dec(&nr_files); call_rcu(&f->f_u.fu_rcuhead, file_free_rcu); } @@ -100,7 +101,7 @@ int proc_nr_files(struct ctl_table *table, int write, * done, you will imbalance int the mount's writer count * and a warning at __fput() time. */ -struct file *get_empty_filp(void) +struct file *__get_empty_filp(bool account) { const struct cred *cred = current_cred(); static long old_max; @@ -110,7 +111,8 @@ struct file *get_empty_filp(void) /* * Privileged users can go above max_files */ - if (get_nr_files() >= files_stat.max_files && !capable(CAP_SYS_ADMIN)) { + if (account && + get_nr_files() >= files_stat.max_files && !capable(CAP_SYS_ADMIN)) { /* * percpu_counters are inaccurate. Do an expensive check before * we go and fail. @@ -123,7 +125,10 @@ struct file *get_empty_filp(void) if (unlikely(!f)) return ERR_PTR(-ENOMEM); - percpu_counter_inc(&nr_files); + if (account) + percpu_counter_inc(&nr_files); + else + f->f_mode = FMODE_NOACCOUNT; f->f_cred = get_cred(cred); error = security_file_alloc(f); if (unlikely(error)) { diff --git a/fs/internal.h b/fs/internal.h index e08972db0303..b82725ba3054 100644 --- a/fs/internal.h +++ b/fs/internal.h @@ -93,7 +93,12 @@ extern void chroot_fs_refs(const struct path *, const struct path *); /* * file_table.c */ -extern struct file *get_empty_filp(void); +extern struct file *__get_empty_filp(bool account); + +static inline struct file *get_empty_filp(void) +{ + return __get_empty_filp(true); +} /* * super.c diff --git a/fs/open.c b/fs/open.c index d0bf7f061a1a..6e52fd6fea7c 100644 --- a/fs/open.c +++ b/fs/open.c @@ -732,8 +732,8 @@ static int do_dentry_open(struct file *f, static const struct file_operations empty_fops = {}; int error; - f->f_mode = OPEN_FMODE(f->f_flags) | FMODE_LSEEK | - FMODE_PREAD | FMODE_PWRITE; + f->f_mode = (f->f_mode & FMODE_NOACCOUNT) | OPEN_FMODE(f->f_flags) | + FMODE_LSEEK | FMODE_PREAD | FMODE_PWRITE; path_get(&f->f_path); f->f_inode = inode; @@ -743,7 +743,7 @@ static int do_dentry_open(struct file *f, f->f_wb_err = filemap_sample_wb_err(f->f_mapping); if (unlikely(f->f_flags & O_PATH)) { - f->f_mode = FMODE_PATH; + f->f_mode = (f->f_mode & FMODE_NOACCOUNT) | FMODE_PATH; f->f_op = &empty_fops; goto done; } @@ -917,12 +917,12 @@ int vfs_open(const struct path *path, struct file *file, * Return: A pointer to a struct file or an IS_ERR pointer. Cannot return NULL. */ struct file *path_open(const struct path *path, int flags, struct inode *inode, - const struct cred *cred) + const struct cred *cred, bool account) { struct file *file; int retval; - file = get_empty_filp(); + file = __get_empty_filp(account); if (IS_ERR(file)) return file; diff --git a/include/linux/fs.h b/include/linux/fs.h index d97a661342c8..af49b55ff439 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -153,6 +153,9 @@ typedef int (dio_iodone_t)(struct kiocb *iocb, loff_t offset, /* File is capable of returning -EAGAIN if I/O will block */ #define FMODE_NOWAIT ((__force fmode_t)0x8000000) +/* File does not contribute to nr_files count */ +#define FMODE_NOACCOUNT ((__force fmode_t)0x10000000) + /* * Flag for rw_copy_check_uvector and compat_rw_copy_check_uvector * that indicates that they should check the contents of the iovec are @@ -2402,7 +2405,7 @@ extern struct file *file_open_root(struct dentry *, struct vfsmount *, const char *, int, umode_t); extern struct file * dentry_open(const struct path *, int, const struct cred *); extern struct file *path_open(const struct path *, int, struct inode *, - const struct cred *); + const struct cred *, bool); extern int filp_close(struct file *, fl_owner_t id); extern struct filename *getname_flags(const char __user *, int, int *); -- 2.14.3