From patchwork Wed Nov 25 18:37:24 2015 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Dan Williams X-Patchwork-Id: 7702151 Return-Path: X-Original-To: patchwork-linux-nvdimm@patchwork.kernel.org Delivered-To: patchwork-parsemail@patchwork1.web.kernel.org Received: from mail.kernel.org (mail.kernel.org [198.145.29.136]) by patchwork1.web.kernel.org (Postfix) with ESMTP id AC7109F1BE for ; Wed, 25 Nov 2015 18:37:55 +0000 (UTC) Received: from mail.kernel.org (localhost [127.0.0.1]) by mail.kernel.org (Postfix) with ESMTP id CC66C20877 for ; Wed, 25 Nov 2015 18:37:54 +0000 (UTC) Received: from ml01.01.org (ml01.01.org [198.145.21.10]) (using TLSv1.2 with cipher DHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.kernel.org (Postfix) with ESMTPS id D5DD120867 for ; Wed, 25 Nov 2015 18:37:53 +0000 (UTC) Received: from ml01.vlan14.01.org (localhost [IPv6:::1]) by ml01.01.org (Postfix) with ESMTP id CAEA21A2029; Wed, 25 Nov 2015 10:37:53 -0800 (PST) X-Original-To: linux-nvdimm@lists.01.org Delivered-To: linux-nvdimm@lists.01.org Received: from mga01.intel.com (mga01.intel.com [192.55.52.88]) by ml01.01.org (Postfix) with ESMTP id 407901A202E for ; Wed, 25 Nov 2015 10:37:52 -0800 (PST) Received: from fmsmga003.fm.intel.com ([10.253.24.29]) by fmsmga101.fm.intel.com with ESMTP; 25 Nov 2015 10:37:52 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.20,343,1444719600"; d="scan'208";a="607067682" Received: from dwillia2-desk3.jf.intel.com (HELO dwillia2-desk3.amr.corp.intel.com) ([10.54.39.39]) by FMSMGA003.fm.intel.com with ESMTP; 25 Nov 2015 10:37:51 -0800 Subject: [PATCH v2 5/7] fs: notify superblocks of backing-device death From: Dan Williams To: linux-nvdimm@lists.01.org Date: Wed, 25 Nov 2015 10:37:24 -0800 Message-ID: <20151125183724.12508.73971.stgit@dwillia2-desk3.amr.corp.intel.com> In-Reply-To: <20151125183656.12508.52212.stgit@dwillia2-desk3.amr.corp.intel.com> References: <20151125183656.12508.52212.stgit@dwillia2-desk3.amr.corp.intel.com> User-Agent: StGit/0.17.1-9-g687f MIME-Version: 1.0 Cc: Jens Axboe , linux-fsdevel@vger.kernel.org, Dave Chinner , linux-block@vger.kernel.org, Jan Kara X-BeenThere: linux-nvdimm@lists.01.org X-Mailman-Version: 2.1.17 Precedence: list List-Id: "Linux-nvdimm developer list." List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: linux-nvdimm-bounces@lists.01.org Sender: "Linux-nvdimm" X-Spam-Status: No, score=-3.2 required=5.0 tests=BAYES_00, RCVD_IN_DNSWL_LOW, RP_MATCHES_RCVD, UNPARSEABLE_RELAY autolearn=unavailable version=3.3.1 X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on mail.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Set SB_I_BDIDEAD when a block device is no longer available to service requests. This will be used in several places where an fs should give up early because the block device is gone. Letting the fs continue on as if the block device is still present can lead to long latencies waiting for an fs to detect the loss of its backing device, trigger crashes, or generate misleasing warnings. Cc: Jan Kara Cc: Jens Axboe Suggested-by: Dave Chinner Signed-off-by: Dan Williams --- block/genhd.c | 2 ++ fs/block_dev.c | 17 +++++++++++++++++ include/linux/fs.h | 2 ++ 3 files changed, 21 insertions(+) diff --git a/block/genhd.c b/block/genhd.c index e5cafa51567c..8a743cb81fb4 100644 --- a/block/genhd.c +++ b/block/genhd.c @@ -648,10 +648,12 @@ void del_gendisk(struct gendisk *disk) while ((part = disk_part_iter_next(&piter))) { invalidate_partition(disk, part->partno); delete_partition(disk, part->partno); + kill_bdev_super(disk, part->partno); } disk_part_iter_exit(&piter); invalidate_partition(disk, 0); + kill_bdev_super(disk, 0); set_capacity(disk, 0); disk->flags &= ~GENHD_FL_UP; diff --git a/fs/block_dev.c b/fs/block_dev.c index 1dd416bf72f7..d0233d643d33 100644 --- a/fs/block_dev.c +++ b/fs/block_dev.c @@ -1795,6 +1795,23 @@ int __invalidate_device(struct block_device *bdev, bool kill_dirty) } EXPORT_SYMBOL(__invalidate_device); +void kill_bdev_super(struct gendisk *disk, int partno) +{ + struct block_device *bdev = bdget_disk(disk, partno); + struct super_block *sb; + + if (!bdev) + return; + sb = get_super(bdev); + if (!sb) + goto out; + + sb->s_iflags |= SB_I_BDI_DEAD; + drop_super(sb); + out: + bdput(bdev); +} + void iterate_bdevs(void (*func)(struct block_device *, void *), void *arg) { struct inode *inode, *old_inode = NULL; diff --git a/include/linux/fs.h b/include/linux/fs.h index 3aa514254161..76925e322e87 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -1254,6 +1254,7 @@ struct mm_struct; /* sb->s_iflags */ #define SB_I_CGROUPWB 0x00000001 /* cgroup-aware writeback enabled */ #define SB_I_NOEXEC 0x00000002 /* Ignore executables on this fs */ +#define SB_I_BDI_DEAD 0x00000004 /* Give up, backing device is dead */ /* Possible states of 'frozen' field */ enum { @@ -2390,6 +2391,7 @@ extern int revalidate_disk(struct gendisk *); extern int check_disk_change(struct block_device *); extern int __invalidate_device(struct block_device *, bool); extern int invalidate_partition(struct gendisk *, int); +extern void kill_bdev_super(struct gendisk *, int); #endif unsigned long invalidate_mapping_pages(struct address_space *mapping, pgoff_t start, pgoff_t end);