aboutsummaryrefslogtreecommitdiffstats
path: root/fs/xfs
diff options
context:
space:
mode:
authorDave Chinner <dchinner@redhat.com>2012-11-12 06:54:02 -0500
committerBen Myers <bpm@sgi.com>2012-11-15 22:34:05 -0500
commiteab4e63368b4cfa597dbdac66d1a7a836a693b7d (patch)
tree37d6756a3fd9e43ecf65d1b4a3950ecd34ad653f /fs/xfs
parentc3f8fc73ac97b76a12692088ef9cace9af8422c0 (diff)
xfs: uncached buffer reads need to return an error
With verification being done as an IO completion callback, different errors can be returned from a read. Uncached reads only return a buffer or NULL on failure, which means the verification error cannot be returned to the caller. Split the error handling for these reads into two - a failure to get a buffer will still return NULL, but a read error will return a referenced buffer with b_error set rather than NULL. The caller is responsible for checking the error state of the buffer returned. Signed-off-by: Dave Chinner <dchinner@redhat.com> Reviewed-by: Christoph Hellwig <hch@lst.de> Reviewed-by: Phil White <pwhite@sgi.com> Signed-off-by: Ben Myers <bpm@sgi.com>
Diffstat (limited to 'fs/xfs')
-rw-r--r--fs/xfs/xfs_buf.c9
-rw-r--r--fs/xfs/xfs_fsops.c5
-rw-r--r--fs/xfs/xfs_mount.c6
-rw-r--r--fs/xfs/xfs_rtalloc.c9
4 files changed, 21 insertions, 8 deletions
diff --git a/fs/xfs/xfs_buf.c b/fs/xfs/xfs_buf.c
index 0298dd684798..fbc965fc075a 100644
--- a/fs/xfs/xfs_buf.c
+++ b/fs/xfs/xfs_buf.c
@@ -715,8 +715,7 @@ xfs_buf_read_uncached(
715 int flags, 715 int flags,
716 xfs_buf_iodone_t verify) 716 xfs_buf_iodone_t verify)
717{ 717{
718 xfs_buf_t *bp; 718 struct xfs_buf *bp;
719 int error;
720 719
721 bp = xfs_buf_get_uncached(target, numblks, flags); 720 bp = xfs_buf_get_uncached(target, numblks, flags);
722 if (!bp) 721 if (!bp)
@@ -730,11 +729,7 @@ xfs_buf_read_uncached(
730 bp->b_iodone = verify; 729 bp->b_iodone = verify;
731 730
732 xfsbdstrat(target->bt_mount, bp); 731 xfsbdstrat(target->bt_mount, bp);
733 error = xfs_buf_iowait(bp); 732 xfs_buf_iowait(bp);
734 if (error) {
735 xfs_buf_relse(bp);
736 return NULL;
737 }
738 return bp; 733 return bp;
739} 734}
740 735
diff --git a/fs/xfs/xfs_fsops.c b/fs/xfs/xfs_fsops.c
index 5440768ec41c..f35f8d7731f0 100644
--- a/fs/xfs/xfs_fsops.c
+++ b/fs/xfs/xfs_fsops.c
@@ -171,6 +171,11 @@ xfs_growfs_data_private(
171 XFS_FSS_TO_BB(mp, 1), 0, NULL); 171 XFS_FSS_TO_BB(mp, 1), 0, NULL);
172 if (!bp) 172 if (!bp)
173 return EIO; 173 return EIO;
174 if (bp->b_error) {
175 int error = bp->b_error;
176 xfs_buf_relse(bp);
177 return error;
178 }
174 xfs_buf_relse(bp); 179 xfs_buf_relse(bp);
175 180
176 new = nb; /* use new as a temporary here */ 181 new = nb; /* use new as a temporary here */
diff --git a/fs/xfs/xfs_mount.c b/fs/xfs/xfs_mount.c
index d5402b0eb6a3..df6d0b2aade1 100644
--- a/fs/xfs/xfs_mount.c
+++ b/fs/xfs/xfs_mount.c
@@ -658,6 +658,12 @@ reread:
658 xfs_warn(mp, "SB buffer read failed"); 658 xfs_warn(mp, "SB buffer read failed");
659 return EIO; 659 return EIO;
660 } 660 }
661 if (bp->b_error) {
662 error = bp->b_error;
663 if (loud)
664 xfs_warn(mp, "SB validate failed");
665 goto release_buf;
666 }
661 667
662 /* 668 /*
663 * Initialize the mount structure from the superblock. 669 * Initialize the mount structure from the superblock.
diff --git a/fs/xfs/xfs_rtalloc.c b/fs/xfs/xfs_rtalloc.c
index b271ed939d7b..98dc670d3ee0 100644
--- a/fs/xfs/xfs_rtalloc.c
+++ b/fs/xfs/xfs_rtalloc.c
@@ -1876,6 +1876,11 @@ xfs_growfs_rt(
1876 XFS_FSB_TO_BB(mp, 1), 0, NULL); 1876 XFS_FSB_TO_BB(mp, 1), 0, NULL);
1877 if (!bp) 1877 if (!bp)
1878 return EIO; 1878 return EIO;
1879 if (bp->b_error) {
1880 error = bp->b_error;
1881 xfs_buf_relse(bp);
1882 return error;
1883 }
1879 xfs_buf_relse(bp); 1884 xfs_buf_relse(bp);
1880 1885
1881 /* 1886 /*
@@ -2221,8 +2226,10 @@ xfs_rtmount_init(
2221 bp = xfs_buf_read_uncached(mp->m_rtdev_targp, 2226 bp = xfs_buf_read_uncached(mp->m_rtdev_targp,
2222 d - XFS_FSB_TO_BB(mp, 1), 2227 d - XFS_FSB_TO_BB(mp, 1),
2223 XFS_FSB_TO_BB(mp, 1), 0, NULL); 2228 XFS_FSB_TO_BB(mp, 1), 0, NULL);
2224 if (!bp) { 2229 if (!bp || bp->b_error) {
2225 xfs_warn(mp, "realtime device size check failed"); 2230 xfs_warn(mp, "realtime device size check failed");
2231 if (bp)
2232 xfs_buf_relse(bp);
2226 return EIO; 2233 return EIO;
2227 } 2234 }
2228 xfs_buf_relse(bp); 2235 xfs_buf_relse(bp);