[RHEL7,COMMIT] ms/mm: set both AS_EIO/AS_ENOSPC and errseq_t in mapping_set_error

Submitted by Konstantin Khorenko on June 9, 2018, 10:29 a.m.

Details

Message ID 201806091029.w59ATaeE024400@finist_ce7.work
State New
Series "ms/mm: set both AS_EIO/AS_ENOSPC and errseq_t in mapping_set_error"
Headers show

Commit Message

Konstantin Khorenko June 9, 2018, 10:29 a.m.
The commit is pushed to "branch-rh7-3.10.0-862.vz7.48.x-ovz" and will appear at https://src.openvz.org/scm/ovz/vzkernel.git
after rh7-3.10.0-862.el7
------>
commit db397f3f6b79658e756bc3280cc2d16e2dbb6252
Author: Vasily Averin <vvs@virtuozzo.com>
Date:   Sat Jun 9 13:29:36 2018 +0300

    ms/mm: set both AS_EIO/AS_ENOSPC and errseq_t in mapping_set_error
    
    mainline commit 8ed1e46 ("mm: set both AS_EIO/AS_ENOSPC and errseq_t in mapping_set_error")
    
    When a writeback error occurs, we want later callers to be able to pick
    up that fact when they go to wait on that writeback to complete.
    Traditionally, we've used AS_EIO/AS_ENOSPC flags to track that, but
    that's problematic since only one "checker" will be informed when an
    error occurs.
    
    In later patches, we're going to want to convert many of these callers
    to check for errors since a well-defined point in time. For now, ensure
    that we can handle both sorts of checks by both setting errors in both
    places when there is a writeback failure.
    
    Signed-off-by: Jeff Layton <jlayton@redhat.com>
    Signed-off-by: Vasily Averin <vvs@virtuozzo.com>
---
 include/linux/pagemap.h | 31 +++++++++++++++++++++++++------
 1 file changed, 25 insertions(+), 6 deletions(-)

Patch hide | download patch | download mbox

diff --git a/include/linux/pagemap.h b/include/linux/pagemap.h
index d0d8c6bd7b31..3d4ad45c0e42 100644
--- a/include/linux/pagemap.h
+++ b/include/linux/pagemap.h
@@ -29,14 +29,33 @@  enum mapping_flags {
 	AS_NO_WRITEBACK_TAGS = __GFP_BITS_SHIFT + 5,
 };
 
+/**
+ * mapping_set_error - record a writeback error in the address_space
+ * @mapping - the mapping in which an error should be set
+ * @error - the error to set in the mapping
+ *
+ * When writeback fails in some way, we must record that error so that
+ * userspace can be informed when fsync and the like are called.  We endeavor
+ * to report errors on any file that was open at the time of the error.  Some
+ * internal callers also need to know when writeback errors have occurred.
+ *
+ * When a writeback error occurs, most filesystems will want to call
+ * mapping_set_error to record the error in the mapping so that it can be
+ * reported when the application calls fsync(2).
+ */
 static inline void mapping_set_error(struct address_space *mapping, int error)
 {
-	if (unlikely(error)) {
-		if (error == -ENOSPC)
-			set_bit(AS_ENOSPC, &mapping->flags);
-		else
-			set_bit(AS_EIO, &mapping->flags);
-	}
+	if (likely(!error))
+		return;
+
+	/* Record in wb_err for checkers using errseq_t based tracking */
+	filemap_set_wb_err(mapping, error);
+
+	/* Record it in flags for now, for legacy callers */
+	if (error == -ENOSPC)
+		set_bit(AS_ENOSPC, &mapping->flags);
+	else
+		set_bit(AS_EIO, &mapping->flags);
 }
 
 static inline void mapping_set_unevictable(struct address_space *mapping)