From patchwork Wed Aug 8 17:25:52 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Dave Jiang X-Patchwork-Id: 955201 Return-Path: X-Original-To: patchwork-incoming@ozlabs.org Delivered-To: patchwork-incoming@ozlabs.org Authentication-Results: ozlabs.org; spf=none (mailfrom) smtp.mailfrom=vger.kernel.org (client-ip=209.132.180.67; helo=vger.kernel.org; envelope-from=linux-ext4-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=intel.com Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 41lyw65lyJz9s3Z for ; Thu, 9 Aug 2018 03:25:58 +1000 (AEST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728189AbeHHTqf (ORCPT ); Wed, 8 Aug 2018 15:46:35 -0400 Received: from mga03.intel.com ([134.134.136.65]:48128 "EHLO mga03.intel.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727337AbeHHTqf (ORCPT ); Wed, 8 Aug 2018 15:46:35 -0400 X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from orsmga001.jf.intel.com ([10.7.209.18]) by orsmga103.jf.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 08 Aug 2018 10:25:55 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.53,458,1531810800"; d="scan'208";a="80026779" Received: from djiang5-desk3.ch.intel.com ([143.182.136.93]) by orsmga001.jf.intel.com with ESMTP; 08 Aug 2018 10:25:52 -0700 Subject: [PATCH v2 1/2] ext4: Close race between direct IO and ext4_break_layouts() From: Dave Jiang To: tytso@mit.edu, darrick.wong@oracle.com, jack@suse.cz, zwisler@kernel.org Cc: linux-nvdimm@lists.01.org, david@fromorbit.com, linux-xfs@vger.kernel.org, linux-fsdevel@vger.kernel.org, lczerner@redhat.com, linux-ext4@vger.kernel.org, hch@lst.de Date: Wed, 08 Aug 2018 10:25:52 -0700 Message-ID: <153374910694.40645.17166196534680658204.stgit@djiang5-desk3.ch.intel.com> User-Agent: StGit/unknown-version MIME-Version: 1.0 Sender: linux-ext4-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-ext4@vger.kernel.org From: Ross Zwisler If the refcount of a page is lowered between the time that it is returned by dax_busy_page() and when the refcount is again checked in ext4_break_layouts() => ___wait_var_event(), the waiting function ext4_wait_dax_page() will never be called. This means that ext4_break_layouts() will still have 'retry' set to false, so we'll stop looping and never check the refcount of other pages in this inode. Instead, always continue looping as long as dax_layout_busy_page() gives us a page which it found with an elevated refcount. Signed-off-by: Ross Zwisler Reviewed-by: Jan Kara --- v2: - remove verbiage in comment header (Jan) fs/ext4/inode.c | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c index 8f6ad7667974..d2663a1e3ec2 100644 --- a/fs/ext4/inode.c +++ b/fs/ext4/inode.c @@ -4191,9 +4191,8 @@ int ext4_update_disksize_before_punch(struct inode *inode, loff_t offset, return 0; } -static void ext4_wait_dax_page(struct ext4_inode_info *ei, bool *did_unlock) +static void ext4_wait_dax_page(struct ext4_inode_info *ei) { - *did_unlock = true; up_write(&ei->i_mmap_sem); schedule(); down_write(&ei->i_mmap_sem); @@ -4203,14 +4202,12 @@ int ext4_break_layouts(struct inode *inode) { struct ext4_inode_info *ei = EXT4_I(inode); struct page *page; - bool retry; int error; if (WARN_ON_ONCE(!rwsem_is_locked(&ei->i_mmap_sem))) return -EINVAL; do { - retry = false; page = dax_layout_busy_page(inode->i_mapping); if (!page) return 0; @@ -4218,8 +4215,8 @@ int ext4_break_layouts(struct inode *inode) error = ___wait_var_event(&page->_refcount, atomic_read(&page->_refcount) == 1, TASK_INTERRUPTIBLE, 0, 0, - ext4_wait_dax_page(ei, &retry)); - } while (error == 0 && retry); + ext4_wait_dax_page(ei)); + } while (error == 0); return error; } From patchwork Wed Aug 8 17:26:36 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Dave Jiang X-Patchwork-Id: 955202 Return-Path: X-Original-To: patchwork-incoming@ozlabs.org Delivered-To: patchwork-incoming@ozlabs.org Authentication-Results: ozlabs.org; spf=none (mailfrom) smtp.mailfrom=vger.kernel.org (client-ip=209.132.180.67; helo=vger.kernel.org; envelope-from=linux-ext4-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=intel.com Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 41lyxB2sXzz9s3Z for ; Thu, 9 Aug 2018 03:26:54 +1000 (AEST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1728024AbeHHTrc (ORCPT ); Wed, 8 Aug 2018 15:47:32 -0400 Received: from mga09.intel.com ([134.134.136.24]:64457 "EHLO mga09.intel.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727337AbeHHTrc (ORCPT ); Wed, 8 Aug 2018 15:47:32 -0400 X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from fmsmga003.fm.intel.com ([10.253.24.29]) by orsmga102.jf.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 08 Aug 2018 10:26:52 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.53,458,1531810800"; d="scan'208";a="71232865" Received: from djiang5-desk3.ch.intel.com ([143.182.136.93]) by FMSMGA003.fm.intel.com with ESMTP; 08 Aug 2018 10:26:36 -0700 Subject: [PATCH v2 2/2] [PATCH] xfs: Close race between direct IO and xfs_break_layouts() From: Dave Jiang To: tytso@mit.edu, darrick.wong@oracle.com, jack@suse.cz, zwisler@kernel.org Cc: linux-nvdimm@lists.01.org, david@fromorbit.com, linux-xfs@vger.kernel.org, linux-fsdevel@vger.kernel.org, lczerner@redhat.com, linux-ext4@vger.kernel.org, hch@lst.de Date: Wed, 08 Aug 2018 10:26:36 -0700 Message-ID: <153374915981.40645.3350205963852459041.stgit@djiang5-desk3.ch.intel.com> In-Reply-To: <153374910694.40645.17166196534680658204.stgit@djiang5-desk3.ch.intel.com> References: <153374910694.40645.17166196534680658204.stgit@djiang5-desk3.ch.intel.com> User-Agent: StGit/unknown-version MIME-Version: 1.0 Sender: linux-ext4-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-ext4@vger.kernel.org This patch is the duplicate of ross's fix for ext4 for xfs. If the refcount of a page is lowered between the time that it is returned by dax_busy_page() and when the refcount is again checked in xfs_break_layouts() => ___wait_var_event(), the waiting function xfs_wait_dax_page() will never be called. This means that xfs_break_layouts() will still have 'retry' set to false, so we'll stop looping and never check the refcount of other pages in this inode. Instead, always continue looping as long as dax_layout_busy_page() gives us a page which it found with an elevated refcount. Signed-off-by: Dave Jiang Reviewed-by: Jan Kara --- v2: - Rename parameter from did_unlock to retry (Jan) fs/xfs/xfs_file.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/fs/xfs/xfs_file.c b/fs/xfs/xfs_file.c index a3e7767a5715..cd6f0d8c4922 100644 --- a/fs/xfs/xfs_file.c +++ b/fs/xfs/xfs_file.c @@ -721,12 +721,10 @@ xfs_file_write_iter( static void xfs_wait_dax_page( - struct inode *inode, - bool *did_unlock) + struct inode *inode) { struct xfs_inode *ip = XFS_I(inode); - *did_unlock = true; xfs_iunlock(ip, XFS_MMAPLOCK_EXCL); schedule(); xfs_ilock(ip, XFS_MMAPLOCK_EXCL); @@ -736,7 +734,7 @@ static int xfs_break_dax_layouts( struct inode *inode, uint iolock, - bool *did_unlock) + bool *retry) { struct page *page; @@ -746,9 +744,10 @@ xfs_break_dax_layouts( if (!page) return 0; + *retry = true; return ___wait_var_event(&page->_refcount, atomic_read(&page->_refcount) == 1, TASK_INTERRUPTIBLE, - 0, 0, xfs_wait_dax_page(inode, did_unlock)); + 0, 0, xfs_wait_dax_page(inode)); } int