From patchwork Sat Apr 6 10:05:52 2013 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Marco Stornelli X-Patchwork-Id: 234324 Return-Path: X-Original-To: patchwork-incoming@ozlabs.org Delivered-To: patchwork-incoming@ozlabs.org Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id DA1922C0119 for ; Sat, 6 Apr 2013 21:13:24 +1100 (EST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S932735Ab3DFKNH (ORCPT ); Sat, 6 Apr 2013 06:13:07 -0400 Received: from mail-ea0-f182.google.com ([209.85.215.182]:41226 "EHLO mail-ea0-f182.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1757419Ab3DFKNF (ORCPT ); Sat, 6 Apr 2013 06:13:05 -0400 Received: by mail-ea0-f182.google.com with SMTP id q15so1669537ead.13 for ; Sat, 06 Apr 2013 03:13:02 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:message-id:date:from:user-agent:mime-version:to:cc :subject:content-type:content-transfer-encoding; bh=0hdPJ8gc4nW3ADqif1DEQlZ9OEFt/yFE355Zyzv3uXM=; b=WYtgwoY77/hZsfBPSi8knwNTM4ELPdKNWXbEpvh8zyt7BWOyx5ebGO1v0ODhl4l9aR h8mm7l94tm+88Occgn4xxpkFbnJcH958K/iLhL2+EUw968zPD/iRfz5fP5Eg7z57gdPU sakP28MQCNVpjAoxPt0p0bFHUJhZ8MD/WzoG6rjrmlzSHcTGBxxnvS9+RMjmQwHXY3dZ YPNqVcfggCj/gE+diEdDzfm5zf5mBc9bi1kBxioQK6hUcfjMWiXsMUURMUJzRaaqT1ag bttSHuI9R4pvMHJ3z2/hM2tQXjogDZICB3Ku9yFbLGbevwRzPkOuL/8vS4snH/c6zeNc T+cg== X-Received: by 10.14.175.71 with SMTP id y47mr28079615eel.18.1365243182757; Sat, 06 Apr 2013 03:13:02 -0700 (PDT) Received: from [80.183.108.112] (host112-108-dynamic.183-80-r.retail.telecomitalia.it. [80.183.108.112]) by mx.google.com with ESMTPS id m46sm20061220eeo.16.2013.04.06.03.12.56 (version=TLSv1 cipher=ECDHE-RSA-RC4-SHA bits=128/128); Sat, 06 Apr 2013 03:13:02 -0700 (PDT) Message-ID: <515FF380.5020406@gmail.com> Date: Sat, 06 Apr 2013 12:05:52 +0200 From: Marco Stornelli User-Agent: Mozilla/5.0 (X11; Linux i686; rv:17.0) Gecko/20130329 Thunderbird/17.0.5 MIME-Version: 1.0 To: linux-fsdevel@vger.kernel.org CC: Chris Mason , Alexander Viro , Theodore Ts'o , Andreas Dilger , Jaegeuk Kim , Steven Whitehouse , KONISHI Ryusuke , Mark Fasheh , Joel Becker , Matthew Wilcox , Marco Stornelli , Mike Snitzer , Alasdair G Kergon , linux-btrfs@vger.kernel.org, linux-kernel@vger.kernel.org, linux-ext4@vger.kernel.org, linux-f2fs-devel@lists.sourceforge.net, cluster-devel@redhat.com, linux-nilfs@vger.kernel.org, ocfs2-devel@oss.oracle.com, linux-mm@kvack.org, Jan Kara Subject: [PATCH 3/4] fsfreeze: manage kill signal when sb_start_pagefault is called Sender: linux-ext4-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-ext4@vger.kernel.org In every place where sb_start_pagefault was called now we must manage the error code and return VM_FAULT_RETRY. Signed-off-by: Marco Stornelli --- fs/btrfs/inode.c | 4 +++- fs/buffer.c | 4 +++- fs/ext4/inode.c | 4 +++- fs/f2fs/file.c | 4 +++- fs/gfs2/file.c | 4 +++- fs/nilfs2/file.c | 4 +++- fs/ocfs2/mmap.c | 4 +++- include/linux/fs.h | 6 ++++-- mm/filemap.c | 7 +++++-- 9 files changed, 30 insertions(+), 11 deletions(-) diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c index 09c58a3..a6166f4 100644 --- a/fs/btrfs/inode.c +++ b/fs/btrfs/inode.c @@ -7559,7 +7559,9 @@ int btrfs_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf) u64 page_start; u64 page_end; - sb_start_pagefault(inode->i_sb); + ret = sb_start_pagefault(inode->i_sb); + if (ret) + return VM_FAULT_RETRY; ret = btrfs_delalloc_reserve_space(inode, PAGE_CACHE_SIZE); if (!ret) { ret = file_update_time(vma->vm_file); diff --git a/fs/buffer.c b/fs/buffer.c index b4dcb34..6d3d2cc 100644 --- a/fs/buffer.c +++ b/fs/buffer.c @@ -2383,7 +2383,9 @@ int block_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf, int ret; struct super_block *sb = file_inode(vma->vm_file)->i_sb; - sb_start_pagefault(sb); + ret = sb_start_pagefault(sb); + if (ret) + return VM_FAULT_RETRY; /* * Update file times before taking page lock. We may end up failing the diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c index b3a5213..efc47f6 100644 --- a/fs/ext4/inode.c +++ b/fs/ext4/inode.c @@ -5023,7 +5023,9 @@ int ext4_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf) get_block_t *get_block; int retries = 0; - sb_start_pagefault(inode->i_sb); + ret = sb_start_pagefault(inode->i_sb); + if (ret) + return VM_FAULT_RETRY; file_update_time(vma->vm_file); /* Delalloc case is easy... */ if (test_opt(inode->i_sb, DELALLOC) && diff --git a/fs/f2fs/file.c b/fs/f2fs/file.c index 958a46d..cce4147 100644 --- a/fs/f2fs/file.c +++ b/fs/f2fs/file.c @@ -37,7 +37,9 @@ static int f2fs_vm_page_mkwrite(struct vm_area_struct *vma, f2fs_balance_fs(sbi); - sb_start_pagefault(inode->i_sb); + err = sb_start_pagefault(inode->i_sb); + if (err) + return VM_FAULT_RETRY; mutex_lock_op(sbi, DATA_NEW); diff --git a/fs/gfs2/file.c b/fs/gfs2/file.c index d79c2da..071e777 100644 --- a/fs/gfs2/file.c +++ b/fs/gfs2/file.c @@ -396,7 +396,9 @@ static int gfs2_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf) loff_t size; int ret; - sb_start_pagefault(inode->i_sb); + ret = sb_start_pagefault(inode->i_sb); + if (ret) + return VM_FAULT_RETRY; /* Update file times before taking page lock */ file_update_time(vma->vm_file); diff --git a/fs/nilfs2/file.c b/fs/nilfs2/file.c index 08fdb77..1c7678a 100644 --- a/fs/nilfs2/file.c +++ b/fs/nilfs2/file.c @@ -74,7 +74,9 @@ static int nilfs_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf) if (unlikely(nilfs_near_disk_full(inode->i_sb->s_fs_info))) return VM_FAULT_SIGBUS; /* -ENOSPC */ - sb_start_pagefault(inode->i_sb); + ret = sb_start_pagefault(inode->i_sb); + if (ret) + return VM_FAULT_RETRY; lock_page(page); if (page->mapping != inode->i_mapping || page_offset(page) >= i_size_read(inode) || !PageUptodate(page)) { diff --git a/fs/ocfs2/mmap.c b/fs/ocfs2/mmap.c index 10d66c7..f0973ae 100644 --- a/fs/ocfs2/mmap.c +++ b/fs/ocfs2/mmap.c @@ -136,7 +136,9 @@ static int ocfs2_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf) sigset_t oldset; int ret; - sb_start_pagefault(inode->i_sb); + ret = sb_start_pagefault(inode->i_sb); + if (ret) + return VM_FAULT_RETRY; ocfs2_block_signals(&oldset); /* diff --git a/include/linux/fs.h b/include/linux/fs.h index 03921d6..550574e 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -1407,6 +1407,8 @@ static inline int sb_start_write_trylock(struct super_block *sb) * sb_start_pagefault - get write access to a superblock from a page fault * @sb: the super we write to * + * It returns zero when no error occured, the error code otherwise. + * * When a process starts handling write page fault, it should embed the * operation into sb_start_pagefault() - sb_end_pagefault() pair to get * exclusion against file system freezing. This is needed since the page fault @@ -1422,9 +1424,9 @@ static inline int sb_start_write_trylock(struct super_block *sb) * mmap_sem * -> sb_start_pagefault */ -static inline void sb_start_pagefault(struct super_block *sb) +static inline int sb_start_pagefault(struct super_block *sb) { - __sb_start_write_wait(sb, SB_FREEZE_PAGEFAULT, false); + __sb_start_write_wait(sb, SB_FREEZE_PAGEFAULT, true); } /* diff --git a/mm/filemap.c b/mm/filemap.c index b238671..acf8d97 100644 --- a/mm/filemap.c +++ b/mm/filemap.c @@ -1712,9 +1712,11 @@ int filemap_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf) { struct page *page = vmf->page; struct inode *inode = file_inode(vma->vm_file); - int ret = VM_FAULT_LOCKED; + int ret = 0; - sb_start_pagefault(inode->i_sb); + ret = sb_start_pagefault(inode->i_sb); + if (ret) + return VM_FAULT_RETRY; file_update_time(vma->vm_file); lock_page(page); if (page->mapping != inode->i_mapping) { @@ -1727,6 +1729,7 @@ int filemap_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf) * progress, we are guaranteed that writeback during freezing will * see the dirty page and writeprotect it again. */ + ret = VM_FAULT_LOCKED; set_page_dirty(page); wait_for_stable_page(page); out: