libxfs: make xfs_buf_delwri_submit actually do something
xfs_buf_delwri_queue doesn't report errors, which means that if the
buffer write fails we have no way of knowing that something bad
happened. In the kernel we queue and then submit buffers, and the
submit call communicates errors to callers. Do the same here since
we're going to start using the AG header initialization functions, which
use delwri_{queue,submit} heavily.
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
Reviewed-by: Christoph Hellwig <hch@lst.de>
diff --git a/libxfs/libxfs_io.h b/libxfs/libxfs_io.h
index 16000ac..d93dd37 100644
--- a/libxfs/libxfs_io.h
+++ b/libxfs/libxfs_io.h
@@ -71,6 +71,7 @@
struct xfs_buf_map *b_maps;
struct xfs_buf_map __b_map;
int b_nmaps;
+ struct list_head b_list;
#ifdef XFS_BUF_TRACING
struct list_head b_lock_list;
const char *b_func;
@@ -245,11 +246,14 @@
return bp;
}
+/* Push a single buffer on a delwri queue. */
static inline void
xfs_buf_delwri_queue(struct xfs_buf *bp, struct list_head *buffer_list)
{
bp->b_node.cn_count++;
- libxfs_writebuf(bp, 0);
+ list_add_tail(&bp->b_list, buffer_list);
}
+int xfs_buf_delwri_submit(struct list_head *buffer_list);
+
#endif /* __LIBXFS_IO_H__ */
diff --git a/libxfs/libxfs_priv.h b/libxfs/libxfs_priv.h
index ed2d665..57b5864 100644
--- a/libxfs/libxfs_priv.h
+++ b/libxfs/libxfs_priv.h
@@ -382,7 +382,6 @@
#define xfs_buf_relse(bp) libxfs_putbuf(bp)
#define xfs_buf_get(devp,blkno,len) (libxfs_getbuf((devp), (blkno), (len)))
#define xfs_bwrite(bp) libxfs_writebuf((bp), 0)
-#define xfs_buf_delwri_submit(bl) (0)
#define xfs_buf_oneshot(bp) ((void) 0)
#define XBRW_READ LIBXFS_BREAD
diff --git a/libxfs/rdwr.c b/libxfs/rdwr.c
index d38eab4..3ba2c4b 100644
--- a/libxfs/rdwr.c
+++ b/libxfs/rdwr.c
@@ -1473,3 +1473,28 @@
libxfs_idestroy(ip);
kmem_zone_free(xfs_inode_zone, ip);
}
+
+/*
+ * Write out a buffer list synchronously.
+ *
+ * This will take the @buffer_list, write all buffers out and wait for I/O
+ * completion on all of the buffers. @buffer_list is consumed by the function,
+ * so callers must have some other way of tracking buffers if they require such
+ * functionality.
+ */
+int
+xfs_buf_delwri_submit(
+ struct list_head *buffer_list)
+{
+ struct xfs_buf *bp, *n;
+ int error = 0, error2;
+
+ list_for_each_entry_safe(bp, n, buffer_list, b_list) {
+ list_del_init(&bp->b_list);
+ error2 = libxfs_writebuf(bp, 0);
+ if (!error)
+ error = error2;
+ }
+
+ return error;
+}