From patchwork Thu Aug 30 15:15:49 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Amir Goldstein X-Patchwork-Id: 10582059 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 5D73E14BD for ; Thu, 30 Aug 2018 15:16:04 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 4ABF92C064 for ; Thu, 30 Aug 2018 15:16:04 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 3F3402C06F; Thu, 30 Aug 2018 15:16:04 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 217312C064 for ; Thu, 30 Aug 2018 15:16:03 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727149AbeH3TSk (ORCPT ); Thu, 30 Aug 2018 15:18:40 -0400 Received: from mail-wm0-f68.google.com ([74.125.82.68]:34461 "EHLO mail-wm0-f68.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726732AbeH3TSk (ORCPT ); Thu, 30 Aug 2018 15:18:40 -0400 Received: by mail-wm0-f68.google.com with SMTP id j25-v6so1164381wmc.1 for ; Thu, 30 Aug 2018 08:16:00 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=00HbgocxK/qyfr7xPEVUscrPISA9QSuViBhJJ8XlgVE=; b=dTvS7cBy2EK1VXfUIzgfk/Xf04FwGxRWbNNyD6YaQx3eHLuJhLtn9dPcw6K3h37Lkx aQFzDnsGa9CPD9Yqp+CD3kS5DpLZj3YRPjJHtDJySsd0RnKyPyduwPWEH3pKZsvpPsPu r61bsgMy6JTsFbYVP4HkT8OVZ8l9KN/8vGhUTpzGWZdM9T0Y6+Q+UV2xy/R0ti55TC0f VSyonWHtYPDw7HpCu08HHACBciM46LXsNH1AVAlUCKNoH+rWinaPmrN9gLFhYl8MBBiP tj0WAurt1IyoF242zyVikqxXMuDmrDCGWTKr4qS0ApY8jDjCZGsbrm+VlRRlqA7Yq/Ev s5/g== 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=00HbgocxK/qyfr7xPEVUscrPISA9QSuViBhJJ8XlgVE=; b=Sofmwyr+8R5WCx2K9xIUeRNMpFmPSQqU8JZogytjPo2wU8y8jzxpGHAHY/K7cffRHn q9lnTkuE4fokzPaBeQ3p973O0DWRs4h6vi0nArE+4VqQsU7vyOvZe4JRdnOlllJ2QaeD xboOOzaxCEBo4gaRQcQvGoPWhPRoSytAwVOG9oFBEPbn3pq+hyttLwh8S9nc2EtH5Gbx qGmQSAhf9133uCpPImOo8BH3O78GZcxGBR/WOQhdzkqqOT7terEqpHxvdXh0ZXnT3qh7 Ldx7Se+80nzviD+QPwnjzO32J0DT3MwKPNSEwBvUFiiobYiARIv5wdNSCTE8ujniSpzF 3wWg== X-Gm-Message-State: APzg51B5wFBBmU6GhTcJdG2usVCaLsRMr5nX0g03v650zSRjEMvDVjLG 6xKLXJXaYm5XMjI2eJ+qB/bmuuvE X-Google-Smtp-Source: ANB0VdYZESlGzUaaSoxJAUHY891gWzgK5eX3+sF99wYixTHtJLAT/ShJHINy1+iDPtJ5uwdA6Je7Zw== X-Received: by 2002:a1c:8145:: with SMTP id c66-v6mr2205974wmd.139.1535642160030; Thu, 30 Aug 2018 08:16:00 -0700 (PDT) Received: from localhost.localdomain (bzq-166-168-31-246.red.bezeqint.net. [31.168.166.246]) by smtp.gmail.com with ESMTPSA id 124-v6sm3186823wmk.20.2018.08.30.08.15.58 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Thu, 30 Aug 2018 08:15:59 -0700 (PDT) From: Amir Goldstein To: Jan Kara Cc: Marko Rauhamaa , linux-fsdevel@vger.kernel.org Subject: [PATCH v3 1/3] fsnotify: add super block object type Date: Thu, 30 Aug 2018 18:15:49 +0300 Message-Id: <20180830151551.27422-2-amir73il@gmail.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20180830151551.27422-1-amir73il@gmail.com> References: <20180830151551.27422-1-amir73il@gmail.com> Sender: linux-fsdevel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-fsdevel@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Add the infrastructure to attach a mark to a super_block struct and detach all attached marks when super block is destroyed. This is going to be used by fanotify backend to setup super block marks. Signed-off-by: Amir Goldstein --- fs/notify/fdinfo.c | 5 +++++ fs/notify/fsnotify.c | 8 +++++++- fs/notify/fsnotify.h | 11 +++++++++++ fs/notify/mark.c | 4 ++++ fs/super.c | 2 +- include/linux/fs.h | 5 +++++ include/linux/fsnotify_backend.h | 17 ++++++++++++++--- 7 files changed, 47 insertions(+), 5 deletions(-) diff --git a/fs/notify/fdinfo.c b/fs/notify/fdinfo.c index 86fcf5814279..25385e336ac7 100644 --- a/fs/notify/fdinfo.c +++ b/fs/notify/fdinfo.c @@ -131,6 +131,11 @@ static void fanotify_fdinfo(struct seq_file *m, struct fsnotify_mark *mark) seq_printf(m, "fanotify mnt_id:%x mflags:%x mask:%x ignored_mask:%x\n", mnt->mnt_id, mflags, mark->mask, mark->ignored_mask); + } else if (mark->connector->type == FSNOTIFY_OBJ_TYPE_SB) { + struct super_block *sb = fsnotify_conn_sb(mark->connector); + + seq_printf(m, "fanotify sdev:%x mflags:%x mask:%x ignored_mask:%x\n", + sb->s_dev, mflags, mark->mask, mark->ignored_mask); } } diff --git a/fs/notify/fsnotify.c b/fs/notify/fsnotify.c index f174397b63a0..775e731d3016 100644 --- a/fs/notify/fsnotify.c +++ b/fs/notify/fsnotify.c @@ -48,7 +48,7 @@ void __fsnotify_vfsmount_delete(struct vfsmount *mnt) * Called during unmount with no locks held, so needs to be safe against * concurrent modifiers. We temporarily drop sb->s_inode_list_lock and CAN block. */ -void fsnotify_unmount_inodes(struct super_block *sb) +static void fsnotify_unmount_inodes(struct super_block *sb) { struct inode *inode, *iput_inode = NULL; @@ -98,6 +98,12 @@ void fsnotify_unmount_inodes(struct super_block *sb) iput(iput_inode); } +void fsnotify_sb_delete(struct super_block *sb) +{ + fsnotify_unmount_inodes(sb); + fsnotify_clear_marks_by_sb(sb); +} + /* * Given an inode, first check if we care what happens to our children. Inotify * and dnotify both tell their parents about events. If we care about any event diff --git a/fs/notify/fsnotify.h b/fs/notify/fsnotify.h index 7902653dd577..5a00121fb219 100644 --- a/fs/notify/fsnotify.h +++ b/fs/notify/fsnotify.h @@ -21,6 +21,12 @@ static inline struct mount *fsnotify_conn_mount( return container_of(conn->obj, struct mount, mnt_fsnotify_marks); } +static inline struct super_block *fsnotify_conn_sb( + struct fsnotify_mark_connector *conn) +{ + return container_of(conn->obj, struct super_block, s_fsnotify_marks); +} + /* destroy all events sitting in this groups notification queue */ extern void fsnotify_flush_notify(struct fsnotify_group *group); @@ -43,6 +49,11 @@ static inline void fsnotify_clear_marks_by_mount(struct vfsmount *mnt) { fsnotify_destroy_marks(&real_mount(mnt)->mnt_fsnotify_marks); } +/* run the list of all marks associated with sb and destroy them */ +static inline void fsnotify_clear_marks_by_sb(struct super_block *sb) +{ + fsnotify_destroy_marks(&sb->s_fsnotify_marks); +} /* Wait until all marks queued for destruction are destroyed */ extern void fsnotify_wait_marks_destroyed(void); diff --git a/fs/notify/mark.c b/fs/notify/mark.c index 59cdb27826de..b5172ccb2e60 100644 --- a/fs/notify/mark.c +++ b/fs/notify/mark.c @@ -115,6 +115,8 @@ static __u32 *fsnotify_conn_mask_p(struct fsnotify_mark_connector *conn) return &fsnotify_conn_inode(conn)->i_fsnotify_mask; else if (conn->type == FSNOTIFY_OBJ_TYPE_VFSMOUNT) return &fsnotify_conn_mount(conn)->mnt_fsnotify_mask; + else if (conn->type == FSNOTIFY_OBJ_TYPE_SB) + return &fsnotify_conn_sb(conn)->s_fsnotify_mask; return NULL; } @@ -192,6 +194,8 @@ static struct inode *fsnotify_detach_connector_from_object( inode->i_fsnotify_mask = 0; } else if (conn->type == FSNOTIFY_OBJ_TYPE_VFSMOUNT) { fsnotify_conn_mount(conn)->mnt_fsnotify_mask = 0; + } else if (conn->type == FSNOTIFY_OBJ_TYPE_SB) { + fsnotify_conn_sb(conn)->s_fsnotify_mask = 0; } rcu_assign_pointer(*(conn->obj), NULL); diff --git a/fs/super.c b/fs/super.c index f3a8c008e164..ca53a08497ed 100644 --- a/fs/super.c +++ b/fs/super.c @@ -442,7 +442,7 @@ void generic_shutdown_super(struct super_block *sb) sync_filesystem(sb); sb->s_flags &= ~SB_ACTIVE; - fsnotify_unmount_inodes(sb); + fsnotify_sb_delete(sb); cgroup_writeback_umount(); evict_inodes(sb); diff --git a/include/linux/fs.h b/include/linux/fs.h index 6c0b4a1c22ff..4f0a11d0d296 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -1464,6 +1464,11 @@ struct super_block { spinlock_t s_inode_wblist_lock; struct list_head s_inodes_wb; /* writeback inodes */ + +#ifdef CONFIG_FSNOTIFY + __u32 s_fsnotify_mask; + struct fsnotify_mark_connector __rcu *s_fsnotify_marks; +#endif } __randomize_layout; /* Helper functions so that in most cases filesystems will diff --git a/include/linux/fsnotify_backend.h b/include/linux/fsnotify_backend.h index b8f4182f42f1..81b88fc9df31 100644 --- a/include/linux/fsnotify_backend.h +++ b/include/linux/fsnotify_backend.h @@ -206,12 +206,14 @@ struct fsnotify_group { enum fsnotify_obj_type { FSNOTIFY_OBJ_TYPE_INODE, FSNOTIFY_OBJ_TYPE_VFSMOUNT, + FSNOTIFY_OBJ_TYPE_SB, FSNOTIFY_OBJ_TYPE_COUNT, FSNOTIFY_OBJ_TYPE_DETACHED = FSNOTIFY_OBJ_TYPE_COUNT }; #define FSNOTIFY_OBJ_TYPE_INODE_FL (1U << FSNOTIFY_OBJ_TYPE_INODE) #define FSNOTIFY_OBJ_TYPE_VFSMOUNT_FL (1U << FSNOTIFY_OBJ_TYPE_VFSMOUNT) +#define FSNOTIFY_OBJ_TYPE_SB_FL (1U << FSNOTIFY_OBJ_TYPE_SB) #define FSNOTIFY_OBJ_ALL_TYPES_MASK ((1U << FSNOTIFY_OBJ_TYPE_COUNT) - 1) static inline bool fsnotify_valid_obj_type(unsigned int type) @@ -255,6 +257,7 @@ static inline struct fsnotify_mark *fsnotify_iter_##name##_mark( \ FSNOTIFY_ITER_FUNCS(inode, INODE) FSNOTIFY_ITER_FUNCS(vfsmount, VFSMOUNT) +FSNOTIFY_ITER_FUNCS(sb, SB) #define fsnotify_foreach_obj_type(type) \ for (type = 0; type < FSNOTIFY_OBJ_TYPE_COUNT; type++) @@ -267,8 +270,8 @@ struct fsnotify_mark_connector; typedef struct fsnotify_mark_connector __rcu *fsnotify_connp_t; /* - * Inode / vfsmount point to this structure which tracks all marks attached to - * the inode / vfsmount. The reference to inode / vfsmount is held by this + * Inode/vfsmount/sb point to this structure which tracks all marks attached to + * the inode/vfsmount/sb. The reference to inode/vfsmount/sb is held by this * structure. We destroy this structure when there are no more marks attached * to it. The structure is protected by fsnotify_mark_srcu. */ @@ -335,6 +338,7 @@ extern int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int dat extern int __fsnotify_parent(const struct path *path, struct dentry *dentry, __u32 mask); extern void __fsnotify_inode_delete(struct inode *inode); extern void __fsnotify_vfsmount_delete(struct vfsmount *mnt); +extern void fsnotify_sb_delete(struct super_block *sb); extern u32 fsnotify_get_cookie(void); static inline int fsnotify_inode_watches_children(struct inode *inode) @@ -455,9 +459,13 @@ static inline void fsnotify_clear_inode_marks_by_group(struct fsnotify_group *gr { fsnotify_clear_marks_by_group(group, FSNOTIFY_OBJ_TYPE_INODE_FL); } +/* run all the marks in a group, and clear all of the sn marks */ +static inline void fsnotify_clear_sb_marks_by_group(struct fsnotify_group *group) +{ + fsnotify_clear_marks_by_group(group, FSNOTIFY_OBJ_TYPE_SB_FL); +} extern void fsnotify_get_mark(struct fsnotify_mark *mark); extern void fsnotify_put_mark(struct fsnotify_mark *mark); -extern void fsnotify_unmount_inodes(struct super_block *sb); extern void fsnotify_finish_user_wait(struct fsnotify_iter_info *iter_info); extern bool fsnotify_prepare_user_wait(struct fsnotify_iter_info *iter_info); @@ -484,6 +492,9 @@ static inline void __fsnotify_inode_delete(struct inode *inode) static inline void __fsnotify_vfsmount_delete(struct vfsmount *mnt) {} +static inline void fsnotify_sb_delete(struct super_block *sb) +{} + static inline void fsnotify_update_flags(struct dentry *dentry) {} From patchwork Thu Aug 30 15:15:50 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Amir Goldstein X-Patchwork-Id: 10582061 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 8BEAB175A for ; Thu, 30 Aug 2018 15:16:04 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 7BC0D2C064 for ; Thu, 30 Aug 2018 15:16:04 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 6FD9F2C06C; Thu, 30 Aug 2018 15:16:04 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 0D1E82C065 for ; Thu, 30 Aug 2018 15:16:04 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727200AbeH3TSl (ORCPT ); Thu, 30 Aug 2018 15:18:41 -0400 Received: from mail-wm0-f65.google.com ([74.125.82.65]:52160 "EHLO mail-wm0-f65.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726690AbeH3TSl (ORCPT ); Thu, 30 Aug 2018 15:18:41 -0400 Received: by mail-wm0-f65.google.com with SMTP id y2-v6so2390652wma.1 for ; Thu, 30 Aug 2018 08:16:01 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=UFR4Gr5JBOnfj0hmDbjl7YEGyHdsFtUiiff4c4kZI74=; b=AGZxveutzvfZOHg1oHHXSR/t0k3xr9GITeTKqXwEoo8+OMT6+BYTrMPRelb5S49qFG ej6grpPQj4uqRN0A9UOlF7gAJYv7bZenfanDJtfLU8F6myuwtcMC9D9Ejm3QLMQWsxAt WDIGrWFT9tDsaNoq5/A5nTi5nv1Tp3BRQZjp9ymHlpX7IlEirz7G5SNdgy6wrLBWsEa7 G+1ZrLJbyKGVBqZxvaHeJKEkbqj07f6+xGLywWtyOjn7Cb7sk/0XyDW0p3UQ5GDUo3bU LKqgj3EiUTgyUoUt2xLuiD4bTvt3KVVUcCM4rKsWiTrA4PJC70rxL1A0Pr31aBeGYXR3 bbKQ== 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=UFR4Gr5JBOnfj0hmDbjl7YEGyHdsFtUiiff4c4kZI74=; b=Rgo6IdiXz50IUYovbjxSAKX5w7S3DC2biYk9cHhw1gbIgKlVwlfY0ph3KoUc2WIPf9 G4cktyTeu5I7lpOOHKJaUE4R3ZZk/wkWdVVDnDf2bR6anNlpmgN8/teqReahgW19jbuM PhgFkv/guIC8G6jido3r2I7EgeL6lpycrJwW0Qo20z7ghVApRzPSno5pDiK3Wqrk+lPK pUqG6+0DCF+yr5UkjOXZfrMBtvBvFYdZH4HPlkhc4LUroJ/eGOpKLUoBFrQ71wcS2ZwN nQa4BcrcHxkxx879JM4WNeedSJ+ADDOYZd0prDmFpPnhcrUcWS4vFebqLXPHeP11cRHf RBBA== X-Gm-Message-State: APzg51BquE5pEX5l6GDLJp4DEOyuWfTncq76m7ocT11BOGLefKwOUQrT 5TsVMrEIGCdS36aN8TAByCw= X-Google-Smtp-Source: ANB0VdZelmqopqGMz3dr0DEORK04bzKJnp00zfjOWWHfwrVSWa0myQPhkRw/xGxuOXS+oL5ImZPhLw== X-Received: by 2002:a1c:6a06:: with SMTP id f6-v6mr2042481wmc.159.1535642161193; Thu, 30 Aug 2018 08:16:01 -0700 (PDT) Received: from localhost.localdomain (bzq-166-168-31-246.red.bezeqint.net. [31.168.166.246]) by smtp.gmail.com with ESMTPSA id 124-v6sm3186823wmk.20.2018.08.30.08.16.00 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Thu, 30 Aug 2018 08:16:00 -0700 (PDT) From: Amir Goldstein To: Jan Kara Cc: Marko Rauhamaa , linux-fsdevel@vger.kernel.org Subject: [PATCH v3 2/3] fsnotify: send path type events to group with super block marks Date: Thu, 30 Aug 2018 18:15:50 +0300 Message-Id: <20180830151551.27422-3-amir73il@gmail.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20180830151551.27422-1-amir73il@gmail.com> References: <20180830151551.27422-1-amir73il@gmail.com> Sender: linux-fsdevel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-fsdevel@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Send events to group if super block mark mask matches the event and unless the same group has an ignore mask on the vfsmount or the inode on which the event occurred. Soon, fanotify backend is going to support super block marks and fanotify backend only supports path type events. Signed-off-by: Amir Goldstein --- fs/notify/fsnotify.c | 27 +++++++++++++++++---------- 1 file changed, 17 insertions(+), 10 deletions(-) diff --git a/fs/notify/fsnotify.c b/fs/notify/fsnotify.c index 775e731d3016..89a71242b786 100644 --- a/fs/notify/fsnotify.c +++ b/fs/notify/fsnotify.c @@ -325,15 +325,18 @@ int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is, const unsigned char *file_name, u32 cookie) { struct fsnotify_iter_info iter_info = {}; - struct mount *mnt; + struct super_block *sb = NULL; + struct mount *mnt = NULL; + __u32 mnt_or_sb_mask = 0; int ret = 0; /* global tests shouldn't care about events on child only the specific event */ __u32 test_mask = (mask & ~FS_EVENT_ON_CHILD); - if (data_is == FSNOTIFY_EVENT_PATH) + if (data_is == FSNOTIFY_EVENT_PATH) { mnt = real_mount(((const struct path *)data)->mnt); - else - mnt = NULL; + sb = mnt->mnt.mnt_sb; + mnt_or_sb_mask = mnt->mnt_fsnotify_mask | sb->s_fsnotify_mask; + } /* * Optimization: srcu_read_lock() has a memory barrier which can @@ -343,16 +346,16 @@ int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is, * need SRCU to keep them "alive". */ if (!to_tell->i_fsnotify_marks && - (!mnt || !mnt->mnt_fsnotify_marks)) + (!mnt || (!mnt->mnt_fsnotify_marks && !sb->s_fsnotify_marks))) return 0; /* * if this is a modify event we may need to clear the ignored masks - * otherwise return if neither the inode nor the vfsmount care about + * otherwise return if neither the inode nor the vfsmount/sb care about * this type of event. */ if (!(mask & FS_MODIFY) && !(test_mask & to_tell->i_fsnotify_mask) && - !(mnt && test_mask & mnt->mnt_fsnotify_mask)) + !(mnt && (test_mask & mnt_or_sb_mask))) return 0; iter_info.srcu_idx = srcu_read_lock(&fsnotify_mark_srcu); @@ -364,16 +367,20 @@ int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is, } if (mnt && ((mask & FS_MODIFY) || - (test_mask & mnt->mnt_fsnotify_mask))) { + (test_mask & mnt_or_sb_mask))) { iter_info.marks[FSNOTIFY_OBJ_TYPE_INODE] = fsnotify_first_mark(&to_tell->i_fsnotify_marks); iter_info.marks[FSNOTIFY_OBJ_TYPE_VFSMOUNT] = fsnotify_first_mark(&mnt->mnt_fsnotify_marks); + if ((mask & FS_MODIFY) || + (test_mask & sb->s_fsnotify_mask)) + iter_info.marks[FSNOTIFY_OBJ_TYPE_SB] = + fsnotify_first_mark(&sb->s_fsnotify_marks); } /* - * We need to merge inode & vfsmount mark lists so that inode mark - * ignore masks are properly reflected for mount mark notifications. + * We need to merge inode/vfsmount/sb mark lists so that e.g. inode mark + * ignore masks are properly reflected for mount/sb mark notifications. * That's why this traversal is so complicated... */ while (fsnotify_iter_select_report_types(&iter_info)) { From patchwork Thu Aug 30 15:15:51 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Amir Goldstein X-Patchwork-Id: 10582063 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 68C9F175A for ; Thu, 30 Aug 2018 15:16:06 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 592C92C064 for ; Thu, 30 Aug 2018 15:16:06 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 4D1E82C06C; Thu, 30 Aug 2018 15:16:06 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id C77A82C064 for ; Thu, 30 Aug 2018 15:16:05 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727185AbeH3TSn (ORCPT ); Thu, 30 Aug 2018 15:18:43 -0400 Received: from mail-wm0-f67.google.com ([74.125.82.67]:55623 "EHLO mail-wm0-f67.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726732AbeH3TSn (ORCPT ); Thu, 30 Aug 2018 15:18:43 -0400 Received: by mail-wm0-f67.google.com with SMTP id f21-v6so2381746wmc.5; Thu, 30 Aug 2018 08:16:03 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=GqtFM+7ZLopLnQudodaC37cW5EBN2nLiq07hOIPRl3c=; b=vOuO3w3WYc3yoko3SLj35YikYuS6BzLine/D5dSg3UtM6abWfpgeRaLNScYOkCDwBp ayR33fSlPoZVzMWYwZl8N4GdHMLZXTdvojVYnF1zwVuT88THMlx6smZp1kZP3YedDmOR T8CnxNIxpsulhXwmB5HJaHVcCZdZTk+ye0t7o/GP9q0LMDHJZHT+qMe8D4++8ZEgkNO+ +Kr1x9+9qm7uZBnrQtz08tKIIvMazLbAhLX4Vsl/XUOtkDYQzkb26GfIA2yImLTdMjAk 3XIxIA7IsgUAjdp9GO0e/U/J31yi3CqEGy0mbACR4lXh7ysjaX5ufLIHdgDP0pOMgolL nFNg== 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=GqtFM+7ZLopLnQudodaC37cW5EBN2nLiq07hOIPRl3c=; b=as/YU1AcXV1iOqxqmvZJ/a3yY2EdjwHQWVHJNz0dr46uC7ub1Y2CxYEQEfuF7aasHB KZ6pv4oLHBvmy5tgxN5XgO7Diy1WVqAQpIHTfmheCpsq/6ced1irv4fOkhifnljTr/mT Qw49AXmTzqiChLlaBPSRLSUzxirVaTd2vTIVC6hyjwj26hT2P5bwIx2xbwdHcTM7Gy42 y+K6ZzgFz5HLT0k0bqisRkKKsUdsFms9gRi55g/wq+SYe7ReYGHbX5xNPXcwYSCr9rjv fVKTnB6sy5F9p12nIPi08bsKYdM76nsVw0/l0CchQ7e2pq9JrmNd3lZvny/dQVdUTut8 II4A== X-Gm-Message-State: APzg51BD5CBQ7qk/jkCT4Eb9bDbmM8tUPiqfLiaPE3pyOsYtyVk/xCch Va3BoTEK+ALaTZmQdCbYU/C/4I32 X-Google-Smtp-Source: ANB0Vda9m+9GVGxAQxXhOIdCpK7K/dnu69yXG4VrlCwSpxgGtYgGr0W3fddxYWWeYnWeiXwq8qwJxw== X-Received: by 2002:a1c:9692:: with SMTP id y140-v6mr2081520wmd.82.1535642162471; Thu, 30 Aug 2018 08:16:02 -0700 (PDT) Received: from localhost.localdomain (bzq-166-168-31-246.red.bezeqint.net. [31.168.166.246]) by smtp.gmail.com with ESMTPSA id 124-v6sm3186823wmk.20.2018.08.30.08.16.01 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Thu, 30 Aug 2018 08:16:01 -0700 (PDT) From: Amir Goldstein To: Jan Kara Cc: Marko Rauhamaa , linux-fsdevel@vger.kernel.org, linux-api@vger.kernel.org Subject: [PATCH v3 3/3] fanotify: add API to attach/detach super block mark Date: Thu, 30 Aug 2018 18:15:51 +0300 Message-Id: <20180830151551.27422-4-amir73il@gmail.com> X-Mailer: git-send-email 2.17.1 In-Reply-To: <20180830151551.27422-1-amir73il@gmail.com> References: <20180830151551.27422-1-amir73il@gmail.com> Sender: linux-fsdevel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-fsdevel@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Add another mark type flag FAN_MARK_FILESYSTEM for add/remove/flush of super block mark type. A super block watch gets all events on the filesystem, regardless of the mount from which the mark was added, unless an ignore mask exists on either the inode or the mount where the event was generated. Only one of FAN_MARK_MOUNT and FAN_MARK_FILESYSTEM mark type flags may be provided to fanotify_mark() or no mark type flag for inode mark. Cc: Signed-off-by: Amir Goldstein --- fs/notify/fanotify/fanotify_user.c | 37 ++++++++++++++++++++++++++++++++----- include/uapi/linux/fanotify.h | 7 ++++++- 2 files changed, 38 insertions(+), 6 deletions(-) diff --git a/fs/notify/fanotify/fanotify_user.c b/fs/notify/fanotify/fanotify_user.c index 69054886915b..dff64c7e75fd 100644 --- a/fs/notify/fanotify/fanotify_user.c +++ b/fs/notify/fanotify/fanotify_user.c @@ -563,6 +563,13 @@ static int fanotify_remove_vfsmount_mark(struct fsnotify_group *group, mask, flags); } +static int fanotify_remove_sb_mark(struct fsnotify_group *group, + struct super_block *sb, __u32 mask, + unsigned int flags) +{ + return fanotify_remove_mark(group, &sb->s_fsnotify_marks, mask, flags); +} + static int fanotify_remove_inode_mark(struct fsnotify_group *group, struct inode *inode, __u32 mask, unsigned int flags) @@ -658,6 +665,14 @@ static int fanotify_add_vfsmount_mark(struct fsnotify_group *group, FSNOTIFY_OBJ_TYPE_VFSMOUNT, mask, flags); } +static int fanotify_add_sb_mark(struct fsnotify_group *group, + struct super_block *sb, __u32 mask, + unsigned int flags) +{ + return fanotify_add_mark(group, &sb->s_fsnotify_marks, + FSNOTIFY_OBJ_TYPE_SB, mask, flags); +} + static int fanotify_add_inode_mark(struct fsnotify_group *group, struct inode *inode, __u32 mask, unsigned int flags) @@ -806,6 +821,7 @@ static int do_fanotify_mark(int fanotify_fd, unsigned int flags, __u64 mask, struct fd f; struct path path; u32 valid_mask = FAN_ALL_EVENTS | FAN_EVENT_ON_CHILD; + unsigned int mark_type = flags & FAN_ALL_MARK_TYPE_FLAGS; int ret; pr_debug("%s: fanotify_fd=%d flags=%x dfd=%d pathname=%p mask=%llx\n", @@ -817,6 +833,11 @@ static int do_fanotify_mark(int fanotify_fd, unsigned int flags, __u64 mask, if (flags & ~FAN_ALL_MARK_FLAGS) return -EINVAL; + + /* mixed mark type flags are invalid */ + if (mark_type && !is_power_of_2(mark_type)) + return -EINVAL; + switch (flags & (FAN_MARK_ADD | FAN_MARK_REMOVE | FAN_MARK_FLUSH)) { case FAN_MARK_ADD: /* fallthrough */ case FAN_MARK_REMOVE: @@ -824,7 +845,7 @@ static int do_fanotify_mark(int fanotify_fd, unsigned int flags, __u64 mask, return -EINVAL; break; case FAN_MARK_FLUSH: - if (flags & ~(FAN_MARK_MOUNT | FAN_MARK_FLUSH)) + if (flags & ~(FAN_ALL_MARK_TYPE_FLAGS | FAN_MARK_FLUSH)) return -EINVAL; break; default: @@ -863,8 +884,10 @@ static int do_fanotify_mark(int fanotify_fd, unsigned int flags, __u64 mask, if (flags & FAN_MARK_FLUSH) { ret = 0; - if (flags & FAN_MARK_MOUNT) + if (mark_type == FAN_MARK_MOUNT) fsnotify_clear_vfsmount_marks_by_group(group); + else if (mark_type == FAN_MARK_FILESYSTEM) + fsnotify_clear_sb_marks_by_group(group); else fsnotify_clear_inode_marks_by_group(group); goto fput_and_out; @@ -875,7 +898,7 @@ static int do_fanotify_mark(int fanotify_fd, unsigned int flags, __u64 mask, goto fput_and_out; /* inode held in place by reference to path; group by fget on fd */ - if (!(flags & FAN_MARK_MOUNT)) + if (mark_type == FAN_MARK_INODE) inode = path.dentry->d_inode; else mnt = path.mnt; @@ -883,14 +906,18 @@ static int do_fanotify_mark(int fanotify_fd, unsigned int flags, __u64 mask, /* create/update an inode mark */ switch (flags & (FAN_MARK_ADD | FAN_MARK_REMOVE)) { case FAN_MARK_ADD: - if (flags & FAN_MARK_MOUNT) + if (mark_type == FAN_MARK_MOUNT) ret = fanotify_add_vfsmount_mark(group, mnt, mask, flags); + else if (mark_type == FAN_MARK_FILESYSTEM) + ret = fanotify_add_sb_mark(group, mnt->mnt_sb, mask, flags); else ret = fanotify_add_inode_mark(group, inode, mask, flags); break; case FAN_MARK_REMOVE: - if (flags & FAN_MARK_MOUNT) + if (mark_type == FAN_MARK_MOUNT) ret = fanotify_remove_vfsmount_mark(group, mnt, mask, flags); + else if (mark_type == FAN_MARK_FILESYSTEM) + ret = fanotify_remove_sb_mark(group, mnt->mnt_sb, mask, flags); else ret = fanotify_remove_inode_mark(group, inode, mask, flags); break; diff --git a/include/uapi/linux/fanotify.h b/include/uapi/linux/fanotify.h index 74247917de04..7345b9a57f66 100644 --- a/include/uapi/linux/fanotify.h +++ b/include/uapi/linux/fanotify.h @@ -43,6 +43,7 @@ FAN_UNLIMITED_MARKS) /* flags used for fanotify_modify_mark() */ +#define FAN_MARK_INODE 0x00000000 #define FAN_MARK_ADD 0x00000001 #define FAN_MARK_REMOVE 0x00000002 #define FAN_MARK_DONT_FOLLOW 0x00000004 @@ -51,6 +52,7 @@ #define FAN_MARK_IGNORED_MASK 0x00000020 #define FAN_MARK_IGNORED_SURV_MODIFY 0x00000040 #define FAN_MARK_FLUSH 0x00000080 +#define FAN_MARK_FILESYSTEM 0x00000100 #define FAN_ALL_MARK_FLAGS (FAN_MARK_ADD |\ FAN_MARK_REMOVE |\ @@ -59,7 +61,10 @@ FAN_MARK_MOUNT |\ FAN_MARK_IGNORED_MASK |\ FAN_MARK_IGNORED_SURV_MODIFY |\ - FAN_MARK_FLUSH) + FAN_MARK_FLUSH|\ + FAN_MARK_FILESYSTEM) + +#define FAN_ALL_MARK_TYPE_FLAGS (FAN_MARK_MOUNT | FAN_MARK_FILESYSTEM) /* * All of the events - we build the list by hand so that we can add flags in