From: Dave Chinner <dchinner@xxxxxxxxxx> Verifiers need to be used everywhere to enable calculation of CRCs during writeback of modified metadata. Add then to the libxfs buffer interfaces conver the internal use of devices to be buftarg aware. Verifiers also require that the buffer has a back pointer to the struct xfs_mount. To make this source level comaptible between kernel and userspace, convert userspace to pass struct xfs_buftargs around rather than a "device". Signed-off-by: Dave Chinner <dchinner@xxxxxxxxxx> --- copy/xfs_copy.c | 4 +- db/sb.c | 8 +- include/libxfs.h | 96 ++++++++++++++---------- include/libxlog.h | 2 +- include/xfs_dir2.h | 7 ++ libxfs/init.c | 84 ++++++++++++++++++--- libxfs/logitem.c | 4 +- libxfs/rdwr.c | 195 ++++++++++++++++++++++++++++++++---------------- libxfs/trans.c | 16 ++-- libxfs/xfs.h | 11 +-- libxfs/xfs_dir2_priv.h | 8 -- logprint/logprint.c | 4 +- mkfs/proto.c | 4 +- mkfs/xfs_mkfs.c | 56 ++++++++------ repair/attr_repair.c | 10 +-- repair/dino_chunks.c | 8 +- repair/dinode.c | 10 ++- repair/dir2.c | 15 ++-- repair/phase2.c | 7 +- repair/phase3.c | 2 +- repair/phase6.c | 13 ++-- repair/prefetch.c | 4 +- repair/rt.c | 4 +- repair/scan.c | 15 ++-- repair/xfs_repair.c | 6 +- 25 files changed, 381 insertions(+), 212 deletions(-) diff --git a/copy/xfs_copy.c b/copy/xfs_copy.c index 7f65de3..39517da 100644 --- a/copy/xfs_copy.c +++ b/copy/xfs_copy.c @@ -674,8 +674,10 @@ main(int argc, char **argv) /* prepare the mount structure */ - sbp = libxfs_readbuf(xargs.ddev, XFS_SB_DADDR, 1, 0); memset(&mbuf, 0, sizeof(xfs_mount_t)); + libxfs_buftarg_init(&mbuf, xargs.ddev, xargs.logdev, xargs.rtdev); + sbp = libxfs_readbuf(mbuf.m_ddev_targp, XFS_SB_DADDR, 1, 0, + &xfs_sb_buf_ops); sb = &mbuf.m_sb; libxfs_sb_from_disk(sb, XFS_BUF_TO_SBP(sbp)); diff --git a/db/sb.c b/db/sb.c index 4da1f6a..54ca7dd 100644 --- a/db/sb.c +++ b/db/sb.c @@ -231,15 +231,14 @@ sb_logcheck(void) } memset(&log, 0, sizeof(log)); - if (!x.logdev) - x.logdev = x.ddev; + libxfs_buftarg_init(mp, x.ddev, x.logdev, x.rtdev); x.logBBsize = XFS_FSB_TO_BB(mp, mp->m_sb.sb_logblocks); x.logBBstart = XFS_FSB_TO_DADDR(mp, mp->m_sb.sb_logstart); x.lbsize = BBSIZE; if (xfs_sb_version_hassector(&mp->m_sb)) x.lbsize <<= (mp->m_sb.sb_logsectlog - BBSHIFT); - log.l_dev = (mp->m_sb.sb_logstart == 0) ? x.logdev : x.ddev; + log.l_dev = mp->m_logdev_targp; log.l_logsize = BBTOB(log.l_logBBsize); log.l_logBBsize = x.logBBsize; log.l_logBBstart = x.logBBstart; @@ -271,8 +270,7 @@ sb_logzero(uuid_t *uuidp) dbprintf(_("Clearing log and setting UUID\n")); - if (libxfs_log_clear( - (mp->m_sb.sb_logstart == 0) ? x.logdev : x.ddev, + if (libxfs_log_clear(mp->m_logdev_targp, XFS_FSB_TO_DADDR(mp, mp->m_sb.sb_logstart), (xfs_extlen_t)XFS_FSB_TO_BB(mp, mp->m_sb.sb_logblocks), uuidp, diff --git a/include/libxfs.h b/include/libxfs.h index 972d850..d5131c1 100644 --- a/include/libxfs.h +++ b/include/libxfs.h @@ -116,12 +116,25 @@ typedef struct { #define LIBXFS_EXCLUSIVELY 0x0010 /* disallow other accesses (O_EXCL) */ #define LIBXFS_DIRECT 0x0020 /* can use direct I/O, not buffered */ +/* + * IO verifier callbacks need the xfs_mount pointer, so we have to behave + * somewhat like the kernel now for userspace IO in terms of having buftarg + * based devices... + */ +struct xfs_buftarg { + struct xfs_mount *bt_mount; + dev_t dev; +}; + +extern void libxfs_buftarg_init(struct xfs_mount *mp, dev_t ddev, + dev_t logdev, dev_t rtdev); + extern char *progname; extern int libxfs_init (libxfs_init_t *); extern void libxfs_destroy (void); extern int libxfs_device_to_fd (dev_t); extern dev_t libxfs_device_open (char *, int, int, int); -extern void libxfs_device_zero (dev_t, xfs_daddr_t, uint); +extern void libxfs_device_zero(struct xfs_buftarg *, xfs_daddr_t, uint); extern void libxfs_device_close (dev_t); extern int libxfs_device_alignment (void); extern void libxfs_report(FILE *); @@ -130,11 +143,12 @@ extern void platform_findsizes(char *path, int fd, long long *sz, int *bsz); /* check or write log footer: specify device, log size in blocks & uuid */ typedef xfs_caddr_t (libxfs_get_block_t)(xfs_caddr_t, int, void *); -extern int libxfs_log_clear (dev_t, xfs_daddr_t, uint, uuid_t *, - int, int, int); +extern int libxfs_log_clear (struct xfs_buftarg *, xfs_daddr_t, uint, + uuid_t *, int, int, int); extern int libxfs_log_header (xfs_caddr_t, uuid_t *, int, int, int, libxfs_get_block_t *, void *); + /* * Define a user-level mount structure with all we need * in order to make use of the numerous XFS_* macros. @@ -151,9 +165,12 @@ typedef struct xfs_mount { struct xfs_inode *m_rbmip; /* pointer to bitmap inode */ struct xfs_inode *m_rsumip; /* pointer to summary inode */ struct xfs_inode *m_rootip; /* pointer to root directory */ - dev_t m_dev; - dev_t m_logdev; - dev_t m_rtdev; + struct xfs_buftarg *m_ddev_targp; + struct xfs_buftarg *m_logdev_targp; + struct xfs_buftarg *m_rtdev_targp; +#define m_dev m_ddev_targp +#define m_logdev m_logdev_targp +#define m_rtdev m_rtdev_targp __uint8_t m_dircook_elog; /* log d-cookie entry bits */ __uint8_t m_blkbit_log; /* blocklog + NBBY */ __uint8_t m_blkbb_log; /* blocklog - BBSHIFT */ @@ -218,11 +235,6 @@ extern void libxfs_rtmount_destroy (xfs_mount_t *); /* * Simple I/O interface */ -typedef struct xfs_buftarg { - struct xfs_mount *bt_mount; - dev_t dev; -} xfs_buftarg_t; - #define XB_PAGES 2 struct xfs_buf_map { @@ -244,7 +256,8 @@ typedef struct xfs_buf { xfs_daddr_t b_bn; unsigned b_bcount; unsigned int b_length; - dev_t b_dev; + struct xfs_buftarg *b_target; +#define b_dev b_target->dev pthread_mutex_t b_lock; pthread_t b_holder; unsigned int b_recur; @@ -254,7 +267,6 @@ typedef struct xfs_buf { void *b_addr; int b_error; const struct xfs_buf_ops *b_ops; - struct xfs_buftarg *b_target; struct xfs_perag *b_pag; struct xfs_buf_map *b_map; int b_nmaps; @@ -315,12 +327,12 @@ extern struct cache_operations libxfs_bcache_operations; #ifdef XFS_BUF_TRACING -#define libxfs_readbuf(dev, daddr, len, flags) \ +#define libxfs_readbuf(dev, daddr, len, flags, ops) \ libxfs_trace_readbuf(__FUNCTION__, __FILE__, __LINE__, \ - (dev), (daddr), (len), (flags)) -#define libxfs_readbuf_map(dev, map, nmaps, flags) \ + (dev), (daddr), (len), (flags), (ops)) +#define libxfs_readbuf_map(dev, map, nmaps, flags, ops) \ libxfs_trace_readbuf_map(__FUNCTION__, __FILE__, __LINE__, \ - (dev), (map), (nmaps), (flags)) + (dev), (map), (nmaps), (flags), (ops)) #define libxfs_writebuf(buf, flags) \ libxfs_trace_writebuf(__FUNCTION__, __FILE__, __LINE__, \ (buf), (flags)) @@ -337,28 +349,34 @@ extern struct cache_operations libxfs_bcache_operations; libxfs_trace_putbuf(__FUNCTION__, __FILE__, __LINE__, (buf)) extern xfs_buf_t *libxfs_trace_readbuf(const char *, const char *, int, - dev_t, xfs_daddr_t, int, int); + struct xfs_buftarg *, xfs_daddr_t, int, int, + const struct xfs_buf_ops *); extern xfs_buf_t *libxfs_trace_readbuf_map(const char *, const char *, int, - dev_t, struct xfs_buf_map *, int, int); + struct xfs_buftarg *, struct xfs_buf_map *, int, int, + const struct xfs_buf_ops *); extern int libxfs_trace_writebuf(const char *, const char *, int, xfs_buf_t *, int); extern xfs_buf_t *libxfs_trace_getbuf(const char *, const char *, int, - dev_t, xfs_daddr_t, int); + struct xfs_buftarg *, xfs_daddr_t, int); extern xfs_buf_t *libxfs_trace_getbuf_map(const char *, const char *, int, - dev_t, struct xfs_buf_map *, int); + struct xfs_buftarg *, struct xfs_buf_map *, int); extern xfs_buf_t *libxfs_trace_getbuf_flags(const char *, const char *, int, - dev_t, xfs_daddr_t, int, unsigned int); + struct xfs_buftarg *, xfs_daddr_t, int, unsigned int); extern void libxfs_trace_putbuf (const char *, const char *, int, xfs_buf_t *); #else -extern xfs_buf_t *libxfs_readbuf(dev_t, xfs_daddr_t, int, int); -extern xfs_buf_t *libxfs_readbuf_map(dev_t, struct xfs_buf_map *, int, int); +extern xfs_buf_t *libxfs_readbuf(struct xfs_buftarg *, xfs_daddr_t, int, int, + const struct xfs_buf_ops *); +extern xfs_buf_t *libxfs_readbuf_map(struct xfs_buftarg *, struct xfs_buf_map *, + int, int, const struct xfs_buf_ops *); extern int libxfs_writebuf(xfs_buf_t *, int); -extern xfs_buf_t *libxfs_getbuf(dev_t, xfs_daddr_t, int); -extern xfs_buf_t *libxfs_getbuf_map(dev_t, struct xfs_buf_map *, int); -extern xfs_buf_t *libxfs_getbuf_flags(dev_t, xfs_daddr_t, int, unsigned int); +extern xfs_buf_t *libxfs_getbuf(struct xfs_buftarg *, xfs_daddr_t, int); +extern xfs_buf_t *libxfs_getbuf_map(struct xfs_buftarg *, + struct xfs_buf_map *, int); +extern xfs_buf_t *libxfs_getbuf_flags(struct xfs_buftarg *, xfs_daddr_t, + int, unsigned int); extern void libxfs_putbuf (xfs_buf_t *); #endif @@ -371,11 +389,11 @@ extern int libxfs_bcache_overflowed(void); extern int libxfs_bcache_usage(void); /* Buffer (Raw) Interfaces */ -extern xfs_buf_t *libxfs_getbufr(dev_t, xfs_daddr_t, int); +extern xfs_buf_t *libxfs_getbufr(struct xfs_buftarg *, xfs_daddr_t, int); extern void libxfs_putbufr(xfs_buf_t *); extern int libxfs_writebuf_int(xfs_buf_t *, int); -extern int libxfs_readbufr(dev_t, xfs_daddr_t, xfs_buf_t *, int, int); +extern int libxfs_readbufr(struct xfs_buftarg *, xfs_daddr_t, xfs_buf_t *, int, int); extern int libxfs_bhash_size; extern int libxfs_ihash_size; @@ -461,24 +479,26 @@ extern int libxfs_trans_read_buf (xfs_mount_t *, xfs_trans_t *, dev_t, xfs_daddr_t, int, uint, struct xfs_buf **); */ -struct xfs_buf *libxfs_trans_get_buf_map(struct xfs_trans *tp, dev_t dev, - struct xfs_buf_map *map, int nmaps, - uint flags); +struct xfs_buf *libxfs_trans_get_buf_map(struct xfs_trans *tp, + struct xfs_buftarg *btp, + struct xfs_buf_map *map, int nmaps, + uint flags); static inline struct xfs_buf * libxfs_trans_get_buf( struct xfs_trans *tp, - dev_t dev, + struct xfs_buftarg *btp, xfs_daddr_t blkno, int numblks, uint flags) { DEFINE_SINGLE_BUF_MAP(map, blkno, numblks); - return libxfs_trans_get_buf_map(tp, dev, &map, 1, flags); + return libxfs_trans_get_buf_map(tp, btp, &map, 1, flags); } int libxfs_trans_read_buf_map(struct xfs_mount *mp, - struct xfs_trans *tp, dev_t dev, + struct xfs_trans *tp, + struct xfs_buftarg *btp, struct xfs_buf_map *map, int nmaps, uint flags, struct xfs_buf **bpp, const struct xfs_buf_ops *ops); @@ -487,7 +507,7 @@ static inline int libxfs_trans_read_buf( struct xfs_mount *mp, struct xfs_trans *tp, - dev_t dev, + struct xfs_buftarg *btp, xfs_daddr_t blkno, int numblks, uint flags, @@ -495,7 +515,7 @@ libxfs_trans_read_buf( const struct xfs_buf_ops *ops) { DEFINE_SINGLE_BUF_MAP(map, blkno, numblks); - return libxfs_trans_read_buf_map(mp, tp, dev, &map, 1, + return libxfs_trans_read_buf_map(mp, tp, btp, &map, 1, flags, bpp, ops); } @@ -507,7 +527,7 @@ typedef struct xfs_inode { xfs_mount_t *i_mount; /* fs mount struct ptr */ xfs_ino_t i_ino; /* inode number (agno/agino) */ struct xfs_imap i_imap; /* location for xfs_imap() */ - dev_t i_dev; /* dev for this inode */ + struct xfs_buftarg i_dev; /* dev for this inode */ xfs_ifork_t *i_afp; /* attribute fork pointer */ xfs_ifork_t i_df; /* data fork */ xfs_trans_t *i_transp; /* ptr to owning transaction */ diff --git a/include/libxlog.h b/include/libxlog.h index 36ede59..b101a6e 100644 --- a/include/libxlog.h +++ b/include/libxlog.h @@ -28,7 +28,7 @@ struct xlog { xfs_lsn_t l_tail_lsn; /* lsn of 1st LR w/ unflush buffers */ xfs_lsn_t l_last_sync_lsn;/* lsn of last LR on disk */ xfs_mount_t *l_mp; /* mount point */ - dev_t l_dev; /* dev_t of log */ + struct xfs_buftarg *l_dev; /* dev_t of log */ xfs_daddr_t l_logBBstart; /* start block of log */ int l_logsize; /* size of log in bytes */ int l_logBBsize; /* size of log in 512 byte chunks */ diff --git a/include/xfs_dir2.h b/include/xfs_dir2.h index 8ab59b5..75e8596 100644 --- a/include/xfs_dir2.h +++ b/include/xfs_dir2.h @@ -104,4 +104,11 @@ extern void xfs_dir2_data_use_free(struct xfs_trans *tp, struct xfs_buf *bp, extern struct xfs_dir2_data_free *xfs_dir2_data_freefind( struct xfs_dir2_data_hdr *hdr, struct xfs_dir2_data_unused *dup); +extern const struct xfs_buf_ops xfs_dir3_block_buf_ops; +extern const struct xfs_buf_ops xfs_dir3_leafn_buf_ops; +extern const struct xfs_buf_ops xfs_dir3_leaf1_buf_ops; +extern const struct xfs_buf_ops xfs_dir3_free_buf_ops; +extern const struct xfs_buf_ops xfs_dir3_data_buf_ops; + + #endif /* __XFS_DIR2_H__ */ diff --git a/libxfs/init.c b/libxfs/init.c index 71da69b..e62f26a 100644 --- a/libxfs/init.c +++ b/libxfs/init.c @@ -457,7 +457,7 @@ rtmount_init( sbp = &mp->m_sb; if (sbp->sb_rblocks == 0) return 0; - if (mp->m_rtdev == 0 && !(flags & LIBXFS_MOUNT_DEBUGGER)) { + if (mp->m_rtdev_targp->dev == 0 && !(flags & LIBXFS_MOUNT_DEBUGGER)) { fprintf(stderr, _("%s: filesystem has a realtime subvolume\n"), progname); return -1; @@ -486,7 +486,7 @@ rtmount_init( return -1; } bp = libxfs_readbuf(mp->m_rtdev, - d - XFS_FSB_TO_BB(mp, 1), XFS_FSB_TO_BB(mp, 1), 0); + d - XFS_FSB_TO_BB(mp, 1), XFS_FSB_TO_BB(mp, 1), 0, NULL); if (bp == NULL) { fprintf(stderr, _("%s: realtime size check failed\n"), progname); @@ -599,6 +599,72 @@ out_unwind: return error; } +static struct xfs_buftarg * +libxfs_buftarg_alloc( + struct xfs_mount *mp, + dev_t dev) +{ + struct xfs_buftarg *btp; + + btp = malloc(sizeof(*btp)); + if (!btp) { + fprintf(stderr, _("%s: buftarg init failed\n"), + progname); + exit(1); + } + btp->bt_mount = mp; + btp->dev = dev; + return btp; +} + +void +libxfs_buftarg_init( + struct xfs_mount *mp, + dev_t dev, + dev_t logdev, + dev_t rtdev) +{ + if (mp->m_ddev_targp) { + /* should already have all buftargs initialised */ + if (mp->m_ddev_targp->dev != dev || + mp->m_ddev_targp->bt_mount != mp) { + fprintf(stderr, + _("%s: bad buftarg reinit, ddev\n"), + progname); + exit(1); + } + if (!logdev || logdev == dev) { + if (mp->m_logdev_targp != mp->m_ddev_targp) { + fprintf(stderr, + _("%s: bad buftarg reinit, ldev mismatch\n"), + progname); + exit(1); + } + } else if (mp->m_logdev_targp->dev != logdev || + mp->m_logdev_targp->bt_mount != mp) { + fprintf(stderr, + _("%s: bad buftarg reinit, logdev\n"), + progname); + exit(1); + } + if (rtdev && (mp->m_rtdev_targp->dev != rtdev || + mp->m_rtdev_targp->bt_mount != mp)) { + fprintf(stderr, + _("%s: bad buftarg reinit, rtdev\n"), + progname); + exit(1); + } + return; + } + + mp->m_ddev_targp = libxfs_buftarg_alloc(mp, dev); + if (!logdev || logdev == dev) + mp->m_logdev_targp = mp->m_ddev_targp; + else + mp->m_logdev_targp = libxfs_buftarg_alloc(mp, logdev); + mp->m_rtdev_targp = libxfs_buftarg_alloc(mp, rtdev); +} + /* * Mount structure initialization, provides a filled-in xfs_mount_t * such that the numerous XFS_* macros can be used. If dev is zero, @@ -618,9 +684,8 @@ libxfs_mount( xfs_sb_t *sbp; int error; - mp->m_dev = dev; - mp->m_rtdev = rtdev; - mp->m_logdev = logdev; + libxfs_buftarg_init(mp, dev, logdev, rtdev); + mp->m_flags = (LIBXFS_MOUNT_32BITINODES|LIBXFS_MOUNT_32BITINOOPT); mp->m_sb = *sb; INIT_RADIX_TREE(&mp->m_perag_tree, GFP_KERNEL); @@ -705,7 +770,7 @@ libxfs_mount( bp = libxfs_readbuf(mp->m_dev, d - XFS_FSS_TO_BB(mp, 1), XFS_FSS_TO_BB(mp, 1), - !(flags & LIBXFS_MOUNT_DEBUGGER)); + !(flags & LIBXFS_MOUNT_DEBUGGER), NULL); if (!bp) { fprintf(stderr, _("%s: data size check failed\n"), progname); if (!(flags & LIBXFS_MOUNT_DEBUGGER)) @@ -713,13 +778,14 @@ libxfs_mount( } else libxfs_putbuf(bp); - if (mp->m_logdev && mp->m_logdev != mp->m_dev) { + if (mp->m_logdev_targp->dev && + mp->m_logdev_targp->dev != mp->m_ddev_targp->dev) { d = (xfs_daddr_t) XFS_FSB_TO_BB(mp, mp->m_sb.sb_logblocks); if ( (XFS_BB_TO_FSB(mp, d) != mp->m_sb.sb_logblocks) || - (!(bp = libxfs_readbuf(mp->m_logdev, + (!(bp = libxfs_readbuf(mp->m_logdev_targp, d - XFS_FSB_TO_BB(mp, 1), XFS_FSB_TO_BB(mp, 1), - !(flags & LIBXFS_MOUNT_DEBUGGER)))) ) { + !(flags & LIBXFS_MOUNT_DEBUGGER), NULL))) ) { fprintf(stderr, _("%s: log size checks failed\n"), progname); if (!(flags & LIBXFS_MOUNT_DEBUGGER)) diff --git a/libxfs/logitem.c b/libxfs/logitem.c index 84e4c14..73d5a9e 100644 --- a/libxfs/logitem.c +++ b/libxfs/logitem.c @@ -32,7 +32,7 @@ kmem_zone_t *xfs_ili_zone; /* inode log item zone */ xfs_buf_t * xfs_trans_buf_item_match( xfs_trans_t *tp, - dev_t dev, + struct xfs_buftarg *btp, struct xfs_buf_map *map, int nmaps) { @@ -47,7 +47,7 @@ xfs_trans_buf_item_match( list_for_each_entry(lidp, &tp->t_items, lid_trans) { blip = (struct xfs_buf_log_item *)lidp->lid_item; if (blip->bli_item.li_type == XFS_LI_BUF && - blip->bli_buf->b_dev == dev && + blip->bli_buf->b_target->dev == btp->dev && XFS_BUF_ADDR(blip->bli_buf) == map[0].bm_bn && blip->bli_buf->b_bcount == BBTOB(len)) { ASSERT(blip->bli_buf->b_map_count == nmaps); diff --git a/libxfs/rdwr.c b/libxfs/rdwr.c index e9cc7b1..f91a5d0 100644 --- a/libxfs/rdwr.c +++ b/libxfs/rdwr.c @@ -27,7 +27,7 @@ #define IO_BCOMPARE_CHECK void -libxfs_device_zero(dev_t dev, xfs_daddr_t start, uint len) +libxfs_device_zero(struct xfs_buftarg *btp, xfs_daddr_t start, uint len) { xfs_off_t start_offset, end_offset, offset; ssize_t zsize, bytes; @@ -43,7 +43,7 @@ libxfs_device_zero(dev_t dev, xfs_daddr_t start, uint len) } memset(z, 0, zsize); - fd = libxfs_device_to_fd(dev); + fd = libxfs_device_to_fd(btp->dev); start_offset = LIBXFS_BBTOOFF64(start); if ((lseek64(fd, start_offset, SEEK_SET)) < 0) { @@ -102,7 +102,7 @@ static xfs_caddr_t next(xfs_caddr_t ptr, int offset, void *private) int libxfs_log_clear( - dev_t device, + struct xfs_buftarg *btp, xfs_daddr_t start, uint length, uuid_t *fs_uuid, @@ -113,16 +113,16 @@ libxfs_log_clear( xfs_buf_t *bp; int len; - if (!device || !fs_uuid) + if (!btp->dev || !fs_uuid) return -EINVAL; /* first zero the log */ - libxfs_device_zero(device, start, length); + libxfs_device_zero(btp, start, length); /* then write a log record header */ len = ((version == 2) && sunit) ? BTOBB(sunit) : 2; len = MAX(len, 2); - bp = libxfs_getbufr(device, start, len); + bp = libxfs_getbufr(btp, start, len); libxfs_log_header(XFS_BUF_PTR(bp), fs_uuid, version, sunit, fmt, next, bp); bp->b_flags |= LIBXFS_B_DIRTY; @@ -200,12 +200,15 @@ libxfs_log_header( #undef libxfs_getbuf_flags #undef libxfs_putbuf -xfs_buf_t *libxfs_readbuf(dev_t, xfs_daddr_t, int, int); -xfs_buf_t *libxfs_readbuf_map(dev_t, struct xfs_buf_map *, int, int); +xfs_buf_t *libxfs_readbuf(struct xfs_buftarg *, xfs_daddr_t, int, int, + const struct xfs_buf_map *); +xfs_buf_t *libxfs_readbuf_map(struct xfs_buftarg *, struct xfs_buf_map *, + int, int, const struct xfs_buf_map *); int libxfs_writebuf(xfs_buf_t *, int); -xfs_buf_t *libxfs_getbuf(dev_t, xfs_daddr_t, int); -xfs_buf_t *libxfs_getbuf_map(dev_t, struct xfs_buf_map *, int); -xfs_buf_t *libxfs_getbuf_flags(dev_t, xfs_daddr_t, int, unsigned int); +xfs_buf_t *libxfs_getbuf(struct xfs_buftarg *, xfs_daddr_t, int); +xfs_buf_t *libxfs_getbuf_map(struct xfs_buftarg *, struct xfs_buf_map *, int); +xfs_buf_t *libxfs_getbuf_flags(struct xfs_buftarg *, xfs_daddr_t, int, + unsigned int); void libxfs_putbuf (xfs_buf_t *); #define __add_trace(bp, func, file, line) \ @@ -219,18 +222,20 @@ do { \ xfs_buf_t * libxfs_trace_readbuf(const char *func, const char *file, int line, - dev_t dev, xfs_daddr_t blkno, int len, int flags) + struct xfs_buftarg *btp, xfs_daddr_t blkno, int len, int flags, + const struct xfs_buf_ops *ops) { - xfs_buf_t *bp = libxfs_readbuf(dev, blkno, len, flags); + xfs_buf_t *bp = libxfs_readbuf(btp, blkno, len, flags, ops); __add_trace(bp, func, file, line); return bp; } xfs_buf_t * libxfs_trace_readbuf_map(const char *func, const char *file, int line, - dev_t dev, struct xfs_buf_map *map, int nmaps, int flags) + struct xfs_buftarg *btp, struct xfs_buf_map *map, int nmaps, int flags, + const struct xfs_buf_ops *ops) { - xfs_buf_t *bp = libxfs_readbuf_map(dev, map, nmaps, flags); + xfs_buf_t *bp = libxfs_readbuf_map(btp, map, nmaps, flags, ops); __add_trace(bp, func, file, line); return bp; } @@ -244,27 +249,27 @@ libxfs_trace_writebuf(const char *func, const char *file, int line, xfs_buf_t *b xfs_buf_t * libxfs_trace_getbuf(const char *func, const char *file, int line, - dev_t device, xfs_daddr_t blkno, int len) + struct xfs_buftarg *btp, xfs_daddr_t blkno, int len) { - xfs_buf_t *bp = libxfs_getbuf(device, blkno, len); + xfs_buf_t *bp = libxfs_getbuf(btp, blkno, len); __add_trace(bp, func, file, line); return bp; } xfs_buf_t * libxfs_trace_getbuf_map(const char *func, const char *file, int line, - dev_t device, struct xfs_buf_map *map, int nmaps) + struct xfs_buftarg *btp, struct xfs_buf_map *map, int nmaps) { - xfs_buf_t *bp = libxfs_getbuf_map(device, map, nmaps); + xfs_buf_t *bp = libxfs_getbuf_map(btp, map, nmaps); __add_trace(bp, func, file, line); return bp; } xfs_buf_t * libxfs_trace_getbuf_flags(const char *func, const char *file, int line, - dev_t device, xfs_daddr_t blkno, int len, unsigned int flags) + struct xfs_buftarg *btp, xfs_daddr_t blkno, int len, unsigned int flags) { - xfs_buf_t *bp = libxfs_getbuf_flags(device, blkno, len, flags); + xfs_buf_t *bp = libxfs_getbuf_flags(btp, blkno, len, flags); __add_trace(bp, func, file, line); return bp; } @@ -283,8 +288,8 @@ libxfs_trace_putbuf(const char *func, const char *file, int line, xfs_buf_t *bp) xfs_buf_t * libxfs_getsb(xfs_mount_t *mp, int flags) { - return libxfs_readbuf(mp->m_dev, XFS_SB_DADDR, - XFS_FSS_TO_BB(mp, 1), flags); + return libxfs_readbuf(mp->m_ddev_targp, XFS_SB_DADDR, + XFS_FSS_TO_BB(mp, 1), flags, &xfs_sb_buf_ops); } kmem_zone_t *xfs_buf_zone; @@ -302,7 +307,7 @@ static struct cache_mru xfs_buf_freelist = * buffer initialisation instead of a contiguous buffer. */ struct xfs_bufkey { - dev_t device; + struct xfs_buftarg *buftarg; xfs_daddr_t blkno; unsigned int bblen; struct xfs_buf_map *map; @@ -322,7 +327,7 @@ libxfs_bcompare(struct cache_node *node, cache_key_t key) struct xfs_bufkey *bkey = (struct xfs_bufkey *)key; #ifdef IO_BCOMPARE_CHECK - if (bp->b_dev == bkey->device && + if (bp->b_target->dev == bkey->buftarg->dev && bp->b_bn == bkey->blkno && bp->b_bcount != BBTOB(bkey->bblen)) fprintf(stderr, "%lx: Badness in key lookup (length)\n" @@ -332,7 +337,7 @@ libxfs_bcompare(struct cache_node *node, cache_key_t key) (unsigned long long)bkey->blkno, BBTOB(bkey->bblen)); #endif - return (bp->b_dev == bkey->device && + return (bp->b_target->dev == bkey->buftarg->dev && bp->b_bn == bkey->blkno && bp->b_bcount == BBTOB(bkey->bblen)); } @@ -346,13 +351,14 @@ libxfs_bprint(xfs_buf_t *bp) } static void -__initbuf(xfs_buf_t *bp, dev_t device, xfs_daddr_t bno, unsigned int bytes) +__initbuf(xfs_buf_t *bp, struct xfs_buftarg *btp, xfs_daddr_t bno, + unsigned int bytes) { bp->b_flags = 0; bp->b_bn = bno; bp->b_bcount = bytes; bp->b_length = BTOBB(bytes); - bp->b_dev = device; + bp->b_target = btp; bp->b_error = 0; if (!bp->b_addr) bp->b_addr = memalign(libxfs_device_alignment(), bytes); @@ -369,16 +375,19 @@ __initbuf(xfs_buf_t *bp, dev_t device, xfs_daddr_t bno, unsigned int bytes) pthread_mutex_init(&bp->b_lock, NULL); bp->b_holder = 0; bp->b_recur = 0; + bp->b_ops = NULL; } static void -libxfs_initbuf(xfs_buf_t *bp, dev_t device, xfs_daddr_t bno, unsigned int bytes) +libxfs_initbuf(xfs_buf_t *bp, struct xfs_buftarg *btp, xfs_daddr_t bno, + unsigned int bytes) { - __initbuf(bp, device, bno, bytes); + __initbuf(bp, btp, bno, bytes); } static void -libxfs_initbuf_map(xfs_buf_t *bp, dev_t device, struct xfs_buf_map *map, int nmaps) +libxfs_initbuf_map(xfs_buf_t *bp, struct xfs_buftarg *btp, + struct xfs_buf_map *map, int nmaps) { unsigned int bytes = 0; int i; @@ -401,7 +410,7 @@ libxfs_initbuf_map(xfs_buf_t *bp, dev_t device, struct xfs_buf_map *map, int nma bytes += BBTOB(map[i].bm_len); } - __initbuf(bp, device, map[0].bm_bn, bytes); + __initbuf(bp, btp, map[0].bm_bn, bytes); bp->b_flags |= LIBXFS_B_DISCONTIG; } @@ -441,14 +450,14 @@ __libxfs_getbufr(int blen) } xfs_buf_t * -libxfs_getbufr(dev_t device, xfs_daddr_t blkno, int bblen) +libxfs_getbufr(struct xfs_buftarg *btp, xfs_daddr_t blkno, int bblen) { xfs_buf_t *bp; int blen = BBTOB(bblen); bp =__libxfs_getbufr(blen); if (bp) - libxfs_initbuf(bp, device, blkno, blen); + libxfs_initbuf(bp, btp, blkno, blen); #ifdef IO_DEBUG printf("%lx: %s: allocated %u bytes buffer, key=0x%llx(0x%llx), %p\n", pthread_self(), __FUNCTION__, blen, @@ -459,7 +468,7 @@ libxfs_getbufr(dev_t device, xfs_daddr_t blkno, int bblen) } xfs_buf_t * -libxfs_getbufr_map(dev_t device, xfs_daddr_t blkno, int bblen, +libxfs_getbufr_map(struct xfs_buftarg *btp, xfs_daddr_t blkno, int bblen, struct xfs_buf_map *map, int nmaps) { xfs_buf_t *bp; @@ -481,7 +490,7 @@ libxfs_getbufr_map(dev_t device, xfs_daddr_t blkno, int bblen, bp =__libxfs_getbufr(blen); if (bp) - libxfs_initbuf_map(bp, device, map, nmaps); + libxfs_initbuf_map(bp, btp, map, nmaps); #ifdef IO_DEBUG printf("%lx: %s: allocated %u bytes buffer, key=0x%llx(0x%llx), %p\n", pthread_self(), __FUNCTION__, blen, @@ -552,11 +561,12 @@ out_put: } struct xfs_buf * -libxfs_getbuf_flags(dev_t device, xfs_daddr_t blkno, int len, unsigned int flags) +libxfs_getbuf_flags(struct xfs_buftarg *btp, xfs_daddr_t blkno, int len, + unsigned int flags) { struct xfs_bufkey key = {0}; - key.device = device; + key.buftarg = btp; key.blkno = blkno; key.bblen = len; @@ -564,18 +574,18 @@ libxfs_getbuf_flags(dev_t device, xfs_daddr_t blkno, int len, unsigned int flags } struct xfs_buf * -libxfs_getbuf(dev_t device, xfs_daddr_t blkno, int len) +libxfs_getbuf(struct xfs_buftarg *btp, xfs_daddr_t blkno, int len) { - return libxfs_getbuf_flags(device, blkno, len, 0); + return libxfs_getbuf_flags(btp, blkno, len, 0); } struct xfs_buf * -libxfs_getbuf_map(dev_t device, struct xfs_buf_map *map, int nmaps) +libxfs_getbuf_map(struct xfs_buftarg *btp, struct xfs_buf_map *map, int nmaps) { struct xfs_bufkey key = {0}; int i; - key.device = device; + key.buftarg = btp; key.blkno = map[0].bm_bn; for (i = 0; i < nmaps; i++) { key.bblen += map[i].bm_len; @@ -612,9 +622,9 @@ libxfs_purgebuf(xfs_buf_t *bp) { struct xfs_bufkey key = {0}; - key.device = bp->b_dev; + key.buftarg = bp->b_target; key.blkno = bp->b_bn; - key.bblen = bp->b_bcount >> BBSHIFT; + key.bblen = bp->b_length; cache_node_purge(libxfs_bcache, &key, (struct cache_node *)bp); } @@ -626,10 +636,10 @@ libxfs_balloc(cache_key_t key) if (bufkey->map) return (struct cache_node *) - libxfs_getbufr_map(bufkey->device, + libxfs_getbufr_map(bufkey->buftarg, bufkey->blkno, bufkey->bblen, bufkey->map, bufkey->nmaps); - return (struct cache_node *)libxfs_getbufr(bufkey->device, + return (struct cache_node *)libxfs_getbufr(bufkey->buftarg, bufkey->blkno, bufkey->bblen); } @@ -658,9 +668,10 @@ __read_buf(int fd, void *buf, int len, off64_t offset, int flags) } int -libxfs_readbufr(dev_t dev, xfs_daddr_t blkno, xfs_buf_t *bp, int len, int flags) +libxfs_readbufr(struct xfs_buftarg *btp, xfs_daddr_t blkno, xfs_buf_t *bp, + int len, int flags) { - int fd = libxfs_device_to_fd(dev); + int fd = libxfs_device_to_fd(btp->dev); int bytes = BBTOB(len); int error; @@ -668,7 +679,7 @@ libxfs_readbufr(dev_t dev, xfs_daddr_t blkno, xfs_buf_t *bp, int len, int flags) error = __read_buf(fd, bp->b_addr, bytes, LIBXFS_BBTOOFF64(blkno), flags); if (!error && - bp->b_dev == dev && + bp->b_target->dev == btp->dev && bp->b_bn == blkno && bp->b_bcount == bytes) bp->b_flags |= LIBXFS_B_UPTODATE; @@ -681,22 +692,38 @@ libxfs_readbufr(dev_t dev, xfs_daddr_t blkno, xfs_buf_t *bp, int len, int flags) } xfs_buf_t * -libxfs_readbuf(dev_t dev, xfs_daddr_t blkno, int len, int flags) +libxfs_readbuf(struct xfs_buftarg *btp, xfs_daddr_t blkno, int len, int flags, + const struct xfs_buf_ops *ops) { xfs_buf_t *bp; int error; - bp = libxfs_getbuf(dev, blkno, len); - if (bp && !(bp->b_flags & (LIBXFS_B_UPTODATE|LIBXFS_B_DIRTY))) { - error = libxfs_readbufr(dev, blkno, bp, len, flags); - if (error) - bp->b_error = error; - } + bp = libxfs_getbuf(btp, blkno, len); + if (!bp) + return NULL; + if ((bp->b_flags & (LIBXFS_B_UPTODATE|LIBXFS_B_DIRTY))) + return bp; + + /* + * only set the ops on a cache miss (i.e. first physical read) as the + * verifier may change the ops to match the typ eof buffer it contains. + * A cache hit might reset the verifier to the original type if we set + * it again, but it won't get called again and set to match the buffer + * contents. *cough* xfs_da_node_buf_ops *cough*. + */ + bp->b_error = 0; + bp->b_ops = ops; + error = libxfs_readbufr(btp, blkno, bp, len, flags); + if (error) + bp->b_error = error; + else if (bp->b_ops) + bp->b_ops->verify_read(bp); return bp; } struct xfs_buf * -libxfs_readbuf_map(dev_t dev, struct xfs_buf_map *map, int nmaps, int flags) +libxfs_readbuf_map(struct xfs_buftarg *btp, struct xfs_buf_map *map, int nmaps, + int flags, const struct xfs_buf_ops *ops) { xfs_buf_t *bp; int error = 0; @@ -705,15 +732,21 @@ libxfs_readbuf_map(dev_t dev, struct xfs_buf_map *map, int nmaps, int flags) char *buf; if (nmaps == 1) - return libxfs_readbuf(dev, map[0].bm_bn, map[0].bm_len, flags); + return libxfs_readbuf(btp, map[0].bm_bn, map[0].bm_len, + flags, ops); - bp = libxfs_getbuf_map(dev, map, nmaps); - if (!bp || (bp->b_flags & (LIBXFS_B_UPTODATE|LIBXFS_B_DIRTY))) + bp = libxfs_getbuf_map(btp, map, nmaps); + if (!bp) + return NULL; + + bp->b_error = 0; + bp->b_ops = ops; + if ((bp->b_flags & (LIBXFS_B_UPTODATE|LIBXFS_B_DIRTY))) return bp; ASSERT(bp->b_nmaps = nmaps); - fd = libxfs_device_to_fd(dev); + fd = libxfs_device_to_fd(btp->dev); buf = bp->b_addr; for (i = 0; i < bp->b_nmaps; i++) { off64_t offset = LIBXFS_BBTOOFF64(bp->b_map[i].bm_bn); @@ -731,8 +764,11 @@ libxfs_readbuf_map(dev_t dev, struct xfs_buf_map *map, int nmaps, int flags) offset += len; } - if (!error) + if (!error) { bp->b_flags |= LIBXFS_B_UPTODATE; + if (bp->b_ops) + bp->b_ops->verify_read(bp); + } #ifdef IO_DEBUG printf("%lx: %s: read %lu bytes, error %d, blkno=%llu(%llu), %p\n", pthread_self(), __FUNCTION__, buf - (char *)bp->b_addr, error, @@ -767,9 +803,42 @@ __write_buf(int fd, void *buf, int len, off64_t offset, int flags) int libxfs_writebufr(xfs_buf_t *bp) { - int fd = libxfs_device_to_fd(bp->b_dev); + int fd = libxfs_device_to_fd(bp->b_target->dev); int error = 0; + /* + * we never write buffers that are marked stale. This indicates they + * contain data that has been invalidated, and even if the buffer is + * dirty it must *never* be written. Verifiers are wonderful for finding + * bugs like this. Make sure the error is obvious as to the cause. + */ + if (bp->b_flags & LIBXFS_B_STALE) { + bp->b_error = ESTALE; + return bp->b_error; + } + + /* + * clear any pre-existing error status on the buffer. This can occur if + * the buffer is corrupt on disk and the repair process doesn't clear + * the error before fixing and writing it back. + */ + bp->b_error = 0; + if (bp->b_ops) { + bp->b_ops->verify_write(bp); + if (bp->b_error) { + fprintf(stderr, + _("%s: write verifer failed on bno 0x%llx/0x%x\n"), + __func__, (long long)bp->b_bn, bp->b_bcount); + return bp->b_error; + } + } + + if (bp->b_ops) { + bp->b_ops->verify_write(bp); + if (bp->b_error) + return bp->b_error; + } + if (!(bp->b_flags & LIBXFS_B_DISCONTIG)) { error = __write_buf(fd, bp->b_addr, bp->b_bcount, LIBXFS_BBTOOFF64(bp->b_bn), bp->b_flags); diff --git a/libxfs/trans.c b/libxfs/trans.c index 831e42a..97220e7 100644 --- a/libxfs/trans.c +++ b/libxfs/trans.c @@ -386,7 +386,7 @@ libxfs_trans_bhold( xfs_buf_t * libxfs_trans_get_buf_map( xfs_trans_t *tp, - dev_t dev, + struct xfs_buftarg *btp, struct xfs_buf_map *map, int nmaps, uint f) @@ -395,9 +395,9 @@ libxfs_trans_get_buf_map( xfs_buf_log_item_t *bip; if (tp == NULL) - return libxfs_getbuf_map(dev, map, nmaps); + return libxfs_getbuf_map(btp, map, nmaps); - bp = xfs_trans_buf_item_match(tp, dev, map, nmaps); + bp = xfs_trans_buf_item_match(tp, btp, map, nmaps); if (bp != NULL) { ASSERT(XFS_BUF_FSPRIVATE2(bp, xfs_trans_t *) == tp); bip = XFS_BUF_FSPRIVATE(bp, xfs_buf_log_item_t *); @@ -406,7 +406,7 @@ libxfs_trans_get_buf_map( return bp; } - bp = libxfs_getbuf_map(dev, map, nmaps); + bp = libxfs_getbuf_map(btp, map, nmaps); if (bp == NULL) return NULL; #ifdef XACT_DEBUG @@ -465,7 +465,7 @@ int libxfs_trans_read_buf_map( xfs_mount_t *mp, xfs_trans_t *tp, - dev_t dev, + struct xfs_buftarg *btp, struct xfs_buf_map *map, int nmaps, uint flags, @@ -479,7 +479,7 @@ libxfs_trans_read_buf_map( *bpp = NULL; if (tp == NULL) { - bp = libxfs_readbuf_map(dev, map, nmaps, flags); + bp = libxfs_readbuf_map(btp, map, nmaps, flags, ops); if (!bp) { return (flags & XBF_TRYLOCK) ? EAGAIN : XFS_ERROR(ENOMEM); @@ -489,7 +489,7 @@ libxfs_trans_read_buf_map( goto done; } - bp = xfs_trans_buf_item_match(tp, dev, map, nmaps); + bp = xfs_trans_buf_item_match(tp, btp, map, nmaps); if (bp != NULL) { ASSERT(XFS_BUF_FSPRIVATE2(bp, xfs_trans_t *) == tp); ASSERT(XFS_BUF_FSPRIVATE(bp, void *) != NULL); @@ -498,7 +498,7 @@ libxfs_trans_read_buf_map( goto done; } - bp = libxfs_readbuf_map(dev, map, nmaps, flags); + bp = libxfs_readbuf_map(btp, map, nmaps, flags, ops); if (!bp) { return (flags & XBF_TRYLOCK) ? EAGAIN : XFS_ERROR(ENOMEM); diff --git a/libxfs/xfs.h b/libxfs/xfs.h index 6bec18e..9246f36 100644 --- a/libxfs/xfs.h +++ b/libxfs/xfs.h @@ -55,9 +55,6 @@ typedef __uint32_t inst_t; /* an instruction */ #define EWRONGFS EINVAL #endif -#define m_ddev_targp m_dev -#define m_logdev_targp m_logdev -#define m_rtdev_targp m_rtdev #define xfs_error_level 0 #define STATIC static @@ -187,11 +184,7 @@ roundup_pow_of_two(uint v) NULL; \ }) #define xfs_buf_relse(bp) libxfs_putbuf(bp) -#define xfs_read_buf(mp,devp,blkno,len,f,bpp) \ - (*(bpp) = libxfs_readbuf((devp), \ - (blkno), (len), 1), 0) -#define xfs_buf_get(devp,blkno,len,f) \ - (libxfs_getbuf((devp), (blkno), (len))) +#define xfs_buf_get(devp,blkno,len,f) (libxfs_getbuf((devp), (blkno), (len))) #define xfs_bwrite(bp) libxfs_writebuf((bp), 0) #define XBRW_READ LIBXFS_BREAD @@ -372,7 +365,7 @@ void xfs_buf_item_init (xfs_buf_t *, xfs_mount_t *); void xfs_buf_item_log (xfs_buf_log_item_t *, uint, uint); /* xfs_trans_buf.c */ -xfs_buf_t *xfs_trans_buf_item_match(xfs_trans_t *, dev_t, +xfs_buf_t *xfs_trans_buf_item_match(xfs_trans_t *, struct xfs_buftarg *, struct xfs_buf_map *, int); /* local source files */ diff --git a/libxfs/xfs_dir2_priv.h b/libxfs/xfs_dir2_priv.h index 7cf573c..6743eda 100644 --- a/libxfs/xfs_dir2_priv.h +++ b/libxfs/xfs_dir2_priv.h @@ -30,8 +30,6 @@ extern int xfs_dir_cilookup_result(struct xfs_da_args *args, const unsigned char *name, int len); /* xfs_dir2_block.c */ -extern const struct xfs_buf_ops xfs_dir3_block_buf_ops; - extern int xfs_dir2_block_addname(struct xfs_da_args *args); extern int xfs_dir2_block_getdents(struct xfs_inode *dp, void *dirent, xfs_off_t *offset, filldir_t filldir); @@ -48,9 +46,6 @@ extern int xfs_dir2_leaf_to_block(struct xfs_da_args *args, #define xfs_dir3_data_check(dp,bp) #endif -extern const struct xfs_buf_ops xfs_dir3_data_buf_ops; -extern const struct xfs_buf_ops xfs_dir3_free_buf_ops; - extern int __xfs_dir3_data_check(struct xfs_inode *dp, struct xfs_buf *bp); extern int xfs_dir3_data_read(struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t bno, xfs_daddr_t mapped_bno, struct xfs_buf **bpp); @@ -78,9 +73,6 @@ extern void xfs_dir2_data_use_free(struct xfs_trans *tp, struct xfs_buf *bp, xfs_dir2_data_aoff_t len, int *needlogp, int *needscanp); /* xfs_dir2_leaf.c */ -extern const struct xfs_buf_ops xfs_dir3_leaf1_buf_ops; -extern const struct xfs_buf_ops xfs_dir3_leafn_buf_ops; - extern int xfs_dir3_leafn_read(struct xfs_trans *tp, struct xfs_inode *dp, xfs_dablk_t fbno, xfs_daddr_t mappedbno, struct xfs_buf **bpp); extern int xfs_dir2_block_to_leaf(struct xfs_da_args *args, diff --git a/logprint/logprint.c b/logprint/logprint.c index 3fbcdba..7a56462 100644 --- a/logprint/logprint.c +++ b/logprint/logprint.c @@ -140,6 +140,7 @@ main(int argc, char **argv) setlocale(LC_ALL, ""); bindtextdomain(PACKAGE, LOCALEDIR); textdomain(PACKAGE); + memset(&mount, 0, sizeof(mount)); progname = basename(argv[0]); while ((c = getopt(argc, argv, "bC:cdefl:iqnors:tDVv")) != EOF) { @@ -220,6 +221,7 @@ main(int argc, char **argv) exit(1); logstat(&mount); + libxfs_buftarg_init(&mount, x.ddev, x.logdev, x.rtdev); logfd = (x.logfd < 0) ? x.dfd : x.logfd; @@ -236,7 +238,7 @@ main(int argc, char **argv) ASSERT(x.logBBsize <= INT_MAX); - log.l_dev = x.logdev; + log.l_dev = mount.m_logdev_targp; log.l_logsize = BBTOB(x.logBBsize); log.l_logBBstart = x.logBBstart; log.l_logBBsize = x.logBBsize; diff --git a/mkfs/proto.c b/mkfs/proto.c index f201096..ee84699 100644 --- a/mkfs/proto.c +++ b/mkfs/proto.c @@ -676,7 +676,7 @@ rtinit( error); } for (i = 0, ep = map; i < nmap; i++, ep++) { - libxfs_device_zero(mp->m_dev, + libxfs_device_zero(mp->m_ddev_targp, XFS_FSB_TO_DADDR(mp, ep->br_startblock), XFS_FSB_TO_BB(mp, ep->br_blockcount)); bno += ep->br_blockcount; @@ -713,7 +713,7 @@ rtinit( error); } for (i = 0, ep = map; i < nmap; i++, ep++) { - libxfs_device_zero(mp->m_dev, + libxfs_device_zero(mp->m_ddev_targp, XFS_FSB_TO_DADDR(mp, ep->br_startblock), XFS_FSB_TO_BB(mp, ep->br_blockcount)); bno += ep->br_blockcount; diff --git a/mkfs/xfs_mkfs.c b/mkfs/xfs_mkfs.c index a393607..3864932 100644 --- a/mkfs/xfs_mkfs.c +++ b/mkfs/xfs_mkfs.c @@ -2435,13 +2435,15 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), * swap (somewhere around the page size), jfs (32k), * ext[2,3] and reiserfs (64k) - and hopefully all else. */ - buf = libxfs_getbuf(xi.ddev, 0, BTOBB(WHACK_SIZE)); + libxfs_buftarg_init(mp, xi.ddev, xi.logdev, xi.rtdev); + buf = libxfs_getbuf(mp->m_ddev_targp, 0, BTOBB(WHACK_SIZE)); memset(XFS_BUF_PTR(buf), 0, WHACK_SIZE); libxfs_writebuf(buf, LIBXFS_EXIT_ON_FAILURE); libxfs_purgebuf(buf); /* OK, now write the superblock */ - buf = libxfs_getbuf(xi.ddev, XFS_SB_DADDR, XFS_FSS_TO_BB(mp, 1)); + buf = libxfs_getbuf(mp->m_ddev_targp, XFS_SB_DADDR, XFS_FSS_TO_BB(mp, 1)); + buf->b_ops = &xfs_sb_buf_ops; memset(XFS_BUF_PTR(buf), 0, sectorsize); libxfs_sb_to_disk((void *)XFS_BUF_PTR(buf), sbp, XFS_SB_ALL_BITS); libxfs_writebuf(buf, LIBXFS_EXIT_ON_FAILURE); @@ -2460,10 +2462,11 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), /* * Zero out the end of the device, to obliterate any * old MD RAID (or other) metadata at the end of the device. - * (MD sb is ~64k from the end, take out a wider swath to be sure) + * (MD sb is ~64k from the end, take out a wider swath to be sure) */ if (!xi.disfile) { - buf = libxfs_getbuf(xi.ddev, (xi.dsize - BTOBB(WHACK_SIZE)), + buf = libxfs_getbuf(mp->m_ddev_targp, + (xi.dsize - BTOBB(WHACK_SIZE)), BTOBB(WHACK_SIZE)); memset(XFS_BUF_PTR(buf), 0, WHACK_SIZE); libxfs_writebuf(buf, LIBXFS_EXIT_ON_FAILURE); @@ -2471,14 +2474,12 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), } /* - * Zero the log if there is one. + * Zero the log.... */ - if (loginternal) - xi.logdev = xi.ddev; - if (xi.logdev) - libxfs_log_clear(xi.logdev, XFS_FSB_TO_DADDR(mp, logstart), - (xfs_extlen_t)XFS_FSB_TO_BB(mp, logblocks), - &sbp->sb_uuid, logversion, lsunit, XLOG_FMT); + libxfs_log_clear(mp->m_logdev_targp, + XFS_FSB_TO_DADDR(mp, logstart), + (xfs_extlen_t)XFS_FSB_TO_BB(mp, logblocks), + &sbp->sb_uuid, logversion, lsunit, XLOG_FMT); mp = libxfs_mount(mp, sbp, xi.ddev, xi.logdev, xi.rtdev, 1); if (mp == NULL) { @@ -2487,13 +2488,19 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), exit(1); } + /* + * XXX: this code is effectively shared with the kernel growfs code. + * These initialisations should be pulled into libxfs to keep the + * kernel/userspace header initialisation code the same. + */ for (agno = 0; agno < agcount; agno++) { /* * Superblock. */ - buf = libxfs_getbuf(xi.ddev, + buf = libxfs_getbuf(mp->m_ddev_targp, XFS_AG_DADDR(mp, agno, XFS_SB_DADDR), XFS_FSS_TO_BB(mp, 1)); + buf->b_ops = &xfs_sb_buf_ops; memset(XFS_BUF_PTR(buf), 0, sectorsize); libxfs_sb_to_disk((void *)XFS_BUF_PTR(buf), sbp, XFS_SB_ALL_BITS); libxfs_writebuf(buf, LIBXFS_EXIT_ON_FAILURE); @@ -2501,9 +2508,10 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), /* * AG header block: freespace */ - buf = libxfs_getbuf(mp->m_dev, + buf = libxfs_getbuf(mp->m_ddev_targp, XFS_AG_DADDR(mp, agno, XFS_AGF_DADDR(mp)), XFS_FSS_TO_BB(mp, 1)); + buf->b_ops = &xfs_agf_buf_ops; agf = XFS_BUF_TO_AGF(buf); memset(agf, 0, sectorsize); if (agno == agcount - 1) @@ -2534,10 +2542,11 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), /* * AG header block: inodes */ - buf = libxfs_getbuf(mp->m_dev, + buf = libxfs_getbuf(mp->m_ddev_targp, XFS_AG_DADDR(mp, agno, XFS_AGI_DADDR(mp)), XFS_FSS_TO_BB(mp, 1)); agi = XFS_BUF_TO_AGI(buf); + buf->b_ops = &xfs_agi_buf_ops; memset(agi, 0, sectorsize); agi->agi_magicnum = cpu_to_be32(XFS_AGI_MAGIC); agi->agi_versionnum = cpu_to_be32(XFS_AGI_VERSION); @@ -2556,9 +2565,10 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), /* * BNO btree root block */ - buf = libxfs_getbuf(mp->m_dev, + buf = libxfs_getbuf(mp->m_ddev_targp, XFS_AGB_TO_DADDR(mp, agno, XFS_BNO_BLOCK(mp)), bsize); + buf->b_ops = &xfs_allocbt_buf_ops; block = XFS_BUF_TO_BLOCK(buf); memset(block, 0, blocksize); block->bb_magic = cpu_to_be32(XFS_ABTB_MAGIC); @@ -2608,9 +2618,10 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), /* * CNT btree root block */ - buf = libxfs_getbuf(mp->m_dev, + buf = libxfs_getbuf(mp->m_ddev_targp, XFS_AGB_TO_DADDR(mp, agno, XFS_CNT_BLOCK(mp)), bsize); + buf->b_ops = &xfs_allocbt_buf_ops; block = XFS_BUF_TO_BLOCK(buf); memset(block, 0, blocksize); block->bb_magic = cpu_to_be32(XFS_ABTC_MAGIC); @@ -2650,9 +2661,10 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), /* * INO btree root block */ - buf = libxfs_getbuf(mp->m_dev, + buf = libxfs_getbuf(mp->m_ddev_targp, XFS_AGB_TO_DADDR(mp, agno, XFS_IBT_BLOCK(mp)), bsize); + buf->b_ops = &xfs_inobt_buf_ops; block = XFS_BUF_TO_BLOCK(buf); memset(block, 0, blocksize); block->bb_magic = cpu_to_be32(XFS_IBT_MAGIC); @@ -2666,7 +2678,7 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), /* * Touch last block, make fs the right size if it's a file. */ - buf = libxfs_getbuf(mp->m_dev, + buf = libxfs_getbuf(mp->m_ddev_targp, (xfs_daddr_t)XFS_FSB_TO_BB(mp, dblocks - 1LL), bsize); memset(XFS_BUF_PTR(buf), 0, blocksize); libxfs_writebuf(buf, LIBXFS_EXIT_ON_FAILURE); @@ -2674,8 +2686,8 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), /* * Make sure we can write the last block in the realtime area. */ - if (mp->m_rtdev && rtblocks > 0) { - buf = libxfs_getbuf(mp->m_rtdev, + if (mp->m_rtdev_targp->dev && rtblocks > 0) { + buf = libxfs_getbuf(mp->m_rtdev_targp, XFS_FSB_TO_BB(mp, rtblocks - 1LL), bsize); memset(XFS_BUF_PTR(buf), 0, blocksize); libxfs_writebuf(buf, LIBXFS_EXIT_ON_FAILURE); @@ -2728,7 +2740,7 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), XFS_AGB_TO_DADDR(mp, mp->m_sb.sb_agcount-1, XFS_SB_DADDR), XFS_FSS_TO_BB(mp, 1), - LIBXFS_EXIT_ON_FAILURE); + LIBXFS_EXIT_ON_FAILURE, &xfs_sb_buf_ops); XFS_BUF_TO_SBP(buf)->sb_rootino = cpu_to_be64( mp->m_sb.sb_rootino); libxfs_writebuf(buf, LIBXFS_EXIT_ON_FAILURE); @@ -2740,7 +2752,7 @@ an AG size that is one stripe unit smaller, for example %llu.\n"), XFS_AGB_TO_DADDR(mp, (mp->m_sb.sb_agcount-1)/2, XFS_SB_DADDR), XFS_FSS_TO_BB(mp, 1), - LIBXFS_EXIT_ON_FAILURE); + LIBXFS_EXIT_ON_FAILURE, &xfs_sb_buf_ops); XFS_BUF_TO_SBP(buf)->sb_rootino = cpu_to_be64( mp->m_sb.sb_rootino); libxfs_writebuf(buf, LIBXFS_EXIT_ON_FAILURE); diff --git a/repair/attr_repair.c b/repair/attr_repair.c index 331cbb3..13e9034 100644 --- a/repair/attr_repair.c +++ b/repair/attr_repair.c @@ -170,7 +170,7 @@ traverse_int_dablock(xfs_mount_t *mp, goto error_out; bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, fsbno), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, &xfs_da3_node_buf_ops); if (!bp) { if (whichfork == XFS_DATA_FORK) do_warn( @@ -552,7 +552,7 @@ verify_da_path(xfs_mount_t *mp, } bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, fsbno), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, &xfs_da3_node_buf_ops); if (!bp) { do_warn( _("can't read block %u (%" PRIu64 ") for directory inode %" PRIu64 "\n"), @@ -986,7 +986,7 @@ rmtval_get(xfs_mount_t *mp, xfs_ino_t ino, blkmap_t *blkmap, break; } bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, bno), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, NULL); if (!bp) { do_warn( _("can't read remote block for attributes of inode %" PRIu64 "\n"), ino); @@ -1315,7 +1315,7 @@ process_leaf_attr_level(xfs_mount_t *mp, } bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, dev_bno), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, NULL); if (!bp) { do_warn( _("can't read file block %u (fsbno %" PRIu64 ") for attribute fork of inode %" PRIu64 "\n"), @@ -1497,7 +1497,7 @@ process_longform_attr( } bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, bno), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, NULL); if (!bp) { do_warn( _("can't read block 0 of inode %" PRIu64 " attribute fork\n"), diff --git a/repair/dino_chunks.c b/repair/dino_chunks.c index b625109..21078d0 100644 --- a/repair/dino_chunks.c +++ b/repair/dino_chunks.c @@ -52,7 +52,7 @@ check_aginode_block(xfs_mount_t *mp, * so no one else will overlap them. */ bp = libxfs_readbuf(mp->m_dev, XFS_AGB_TO_DADDR(mp, agno, agbno), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, NULL); if (!bp) { do_warn(_("cannot read agbno (%u/%u), disk block %" PRId64 "\n"), agno, agbno, XFS_AGB_TO_DADDR(mp, agno, agbno)); @@ -65,6 +65,8 @@ check_aginode_block(xfs_mount_t *mp, XFS_OFFBNO_TO_AGINO(mp, agbno, i))) cnt++; } + if (cnt) + bp->b_ops = &xfs_inode_buf_ops; libxfs_putbuf(bp); return(cnt); @@ -625,7 +627,8 @@ process_inode_chunk( bplist[bp_index] = libxfs_readbuf(mp->m_dev, XFS_AGB_TO_DADDR(mp, agno, agbno), - XFS_FSB_TO_BB(mp, blks_per_cluster), 0); + XFS_FSB_TO_BB(mp, blks_per_cluster), 0, + NULL); if (!bplist[bp_index]) { do_warn(_("cannot read inode %" PRIu64 ", disk block %" PRId64 ", cnt %d\n"), XFS_AGINO_TO_INO(mp, agno, first_irec->ino_startnum), @@ -639,6 +642,7 @@ process_inode_chunk( return(1); } agbno += blks_per_cluster; + bplist[bp_index]->b_ops = &xfs_inode_buf_ops; pftrace("readbuf %p (%llu, %d) in AG %d", bplist[bp_index], (long long)XFS_BUF_ADDR(bplist[bp_index]), diff --git a/repair/dinode.c b/repair/dinode.c index 1906ceb..66eedc2 100644 --- a/repair/dinode.c +++ b/repair/dinode.c @@ -836,7 +836,8 @@ get_agino_buf(xfs_mount_t *mp, size = XFS_FSB_TO_BB(mp, MAX(1, XFS_INODES_PER_CHUNK/inodes_per_block)); bp = libxfs_readbuf(mp->m_dev, XFS_AGB_TO_DADDR(mp, agno, - XFS_AGINO_TO_AGBNO(mp, irec->ino_startnum)), size, 0); + XFS_AGINO_TO_AGBNO(mp, irec->ino_startnum)), size, 0, + &xfs_inode_buf_ops); if (!bp) { do_warn(_("cannot read inode (%u/%u), disk block %" PRIu64 "\n"), agno, irec->ino_startnum, @@ -947,7 +948,7 @@ getfunc_btree(xfs_mount_t *mp, ASSERT(verify_dfsbno(mp, fsbno)); bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, fsbno), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, NULL); if (!bp) { do_error(_("cannot read bmap block %" PRIu64 "\n"), fsbno); return(NULLDFSBNO); @@ -1004,7 +1005,7 @@ _("- # of bmap records in inode %" PRIu64 " less than minimum (%u, min - %u), pr */ libxfs_putbuf(bp); bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, fsbno), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, NULL); if (!bp) { do_error(_("cannot read bmap block %" PRIu64 "\n"), fsbno); @@ -1510,7 +1511,8 @@ process_symlink( if (fsbno != NULLDFSBNO) bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, fsbno), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, + &xfs_symlink_buf_ops); if (!bp || fsbno == NULLDFSBNO) { do_warn( _("cannot read inode %" PRIu64 ", file block %d, disk block %" PRIu64 "\n"), diff --git a/repair/dir2.c b/repair/dir2.c index ae80a6b..a71a276 100644 --- a/repair/dir2.c +++ b/repair/dir2.c @@ -103,7 +103,8 @@ static struct xfs_buf * da_read_buf( xfs_mount_t *mp, int nex, - bmap_ext_t *bmp) + bmap_ext_t *bmp, + const struct xfs_buf_ops *ops) { #define MAP_ARRAY_SZ 4 struct xfs_buf_map map_array[MAP_ARRAY_SZ]; @@ -125,7 +126,7 @@ da_read_buf( map[i].bm_bn = XFS_FSB_TO_DADDR(mp, bmp[i].startblock); map[i].bm_len = XFS_FSB_TO_BB(mp, bmp[i].blockcount); } - bp = libxfs_readbuf_map(mp->m_dev, map, nex, 0); + bp = libxfs_readbuf_map(mp->m_dev, map, nex, 0, ops); if (map != map_array) free(map); return bp; @@ -172,7 +173,7 @@ traverse_int_dir2block(xfs_mount_t *mp, if (nex == 0) goto error_out; - bp = da_read_buf(mp, nex, bmp); + bp = da_read_buf(mp, nex, bmp, &xfs_da3_node_buf_ops); if (bmp != &lbmp) free(bmp); if (bp == NULL) { @@ -536,7 +537,7 @@ _("can't get map info for block %u of directory inode %" PRIu64 "\n"), return(1); } - bp = da_read_buf(mp, nex, bmp); + bp = da_read_buf(mp, nex, bmp, &xfs_da3_node_buf_ops); if (bmp != &lbmp) free(bmp); @@ -1581,7 +1582,7 @@ _("block %u for directory inode %" PRIu64 " is missing\n"), mp->m_dirdatablk, ino); return 1; } - bp = da_read_buf(mp, nex, bmp); + bp = da_read_buf(mp, nex, bmp, &xfs_dir3_block_buf_ops); if (bmp != &lbmp) free(bmp); if (bp == NULL) { @@ -1711,7 +1712,7 @@ _("can't map block %u for directory inode %" PRIu64 "\n"), da_bno, ino); goto error_out; } - bp = da_read_buf(mp, nex, bmp); + bp = da_read_buf(mp, nex, bmp, &xfs_dir3_leafn_buf_ops); if (bmp != &lbmp) free(bmp); bmp = NULL; @@ -1897,7 +1898,7 @@ _("block %" PRIu64 " for directory inode %" PRIu64 " is missing\n"), dbno, ino); continue; } - bp = da_read_buf(mp, nex, bmp); + bp = da_read_buf(mp, nex, bmp, &xfs_dir3_data_buf_ops); if (bmp != &lbmp) free(bmp); if (bp == NULL) { diff --git a/repair/phase2.c b/repair/phase2.c index 382cd7b..2817fed 100644 --- a/repair/phase2.c +++ b/repair/phase2.c @@ -40,18 +40,15 @@ zero_log(xfs_mount_t *mp) int error; struct xlog log; xfs_daddr_t head_blk, tail_blk; - dev_t logdev = (mp->m_sb.sb_logstart == 0) ? x.logdev : x.ddev; memset(&log, 0, sizeof(log)); - if (!x.logdev) - x.logdev = x.ddev; x.logBBsize = XFS_FSB_TO_BB(mp, mp->m_sb.sb_logblocks); x.logBBstart = XFS_FSB_TO_DADDR(mp, mp->m_sb.sb_logstart); x.lbsize = BBSIZE; if (xfs_sb_version_hassector(&mp->m_sb)) x.lbsize <<= (mp->m_sb.sb_logsectlog - BBSHIFT); - log.l_dev = logdev; + log.l_dev = mp->m_logdev_targp; log.l_logsize = BBTOB(x.logBBsize); log.l_logBBsize = x.logBBsize; log.l_logBBstart = x.logBBstart; @@ -96,7 +93,7 @@ zero_log(xfs_mount_t *mp) } } - libxfs_log_clear(logdev, + libxfs_log_clear(log.l_dev, XFS_FSB_TO_DADDR(mp, mp->m_sb.sb_logstart), (xfs_extlen_t)XFS_FSB_TO_BB(mp, mp->m_sb.sb_logblocks), &mp->m_sb.sb_uuid, diff --git a/repair/phase3.c b/repair/phase3.c index 80c66b5..3e43938 100644 --- a/repair/phase3.c +++ b/repair/phase3.c @@ -40,7 +40,7 @@ process_agi_unlinked( bp = libxfs_readbuf(mp->m_dev, XFS_AG_DADDR(mp, agno, XFS_AGI_DADDR(mp)), - mp->m_sb.sb_sectsize/BBSIZE, 0); + mp->m_sb.sb_sectsize/BBSIZE, 0, &xfs_agi_buf_ops); if (!bp) do_error(_("cannot read agi block %" PRId64 " for ag %u\n"), XFS_AG_DADDR(mp, agno, XFS_AGI_DADDR(mp)), agno); diff --git a/repair/phase6.c b/repair/phase6.c index bd1fad4..8b8df10 100644 --- a/repair/phase6.c +++ b/repair/phase6.c @@ -510,7 +510,7 @@ mk_rbmino(xfs_mount_t *mp) error); } for (i = 0, ep = map; i < nmap; i++, ep++) { - libxfs_device_zero(mp->m_dev, + libxfs_device_zero(mp->m_ddev_targp, XFS_FSB_TO_DADDR(mp, ep->br_startblock), XFS_FSB_TO_BB(mp, ep->br_blockcount)); bno += ep->br_blockcount; @@ -765,7 +765,7 @@ mk_rsumino(xfs_mount_t *mp) error); } for (i = 0, ep = map; i < nmap; i++, ep++) { - libxfs_device_zero(mp->m_dev, + libxfs_device_zero(mp->m_ddev_targp, XFS_FSB_TO_DADDR(mp, ep->br_startblock), XFS_FSB_TO_BB(mp, ep->br_blockcount)); bno += ep->br_blockcount; @@ -1829,7 +1829,8 @@ longform_dir2_check_leaf( struct xfs_dir2_leaf_entry *ents; da_bno = mp->m_dirleafblk; - if (libxfs_da_read_buf(NULL, ip, da_bno, -1, &bp, XFS_DATA_FORK, NULL)) { + if (libxfs_da_read_buf(NULL, ip, da_bno, -1, &bp, XFS_DATA_FORK, + &xfs_dir3_leaf1_buf_ops)) { do_error( _("can't read block %u for directory inode %" PRIu64 "\n"), da_bno, ip->i_ino); @@ -1906,7 +1907,7 @@ longform_dir2_check_node( if (bmap_next_offset(NULL, ip, &next_da_bno, XFS_DATA_FORK)) break; if (libxfs_da_read_buf(NULL, ip, da_bno, -1, &bp, - XFS_DATA_FORK, NULL)) { + XFS_DATA_FORK, &xfs_dir3_leafn_buf_ops)) { do_warn( _("can't read leaf block %u for directory inode %" PRIu64 "\n"), da_bno, ip->i_ino); @@ -1953,7 +1954,7 @@ longform_dir2_check_node( if (bmap_next_offset(NULL, ip, &next_da_bno, XFS_DATA_FORK)) break; if (libxfs_da_read_buf(NULL, ip, da_bno, -1, &bp, - XFS_DATA_FORK, NULL)) { + XFS_DATA_FORK, &xfs_dir3_free_buf_ops)) { do_warn( _("can't read freespace block %u for directory inode %" PRIu64 "\n"), da_bno, ip->i_ino); @@ -2075,7 +2076,7 @@ longform_dir2_entry_check(xfs_mount_t *mp, num_bps * sizeof(struct xfs_buf*)); } if (libxfs_da_read_buf(NULL, ip, da_bno, -1, &bplist[db], - XFS_DATA_FORK, NULL)) { + XFS_DATA_FORK, &xfs_dir3_data_buf_ops)) { do_warn( _("can't read data block %u for directory inode %" PRIu64 "\n"), da_bno, ino); diff --git a/repair/prefetch.c b/repair/prefetch.c index 3a8177e..93b4146 100644 --- a/repair/prefetch.c +++ b/repair/prefetch.c @@ -221,7 +221,7 @@ pf_scan_lbtree( int rc; bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, dbno), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, NULL); if (!bp) return 0; @@ -720,7 +720,7 @@ init_prefetch( xfs_mount_t *pmp) { mp = pmp; - mp_fd = libxfs_device_to_fd(mp->m_dev); + mp_fd = libxfs_device_to_fd(mp->m_ddev_targp->dev); pf_max_bytes = sysconf(_SC_PAGE_SIZE) << 7; pf_max_bbs = pf_max_bytes >> BBSHIFT; pf_max_fsbs = pf_max_bytes >> mp->m_sb.sb_blocklog; diff --git a/repair/rt.c b/repair/rt.c index d6ecd56..042ff46 100644 --- a/repair/rt.c +++ b/repair/rt.c @@ -206,7 +206,7 @@ process_rtbitmap(xfs_mount_t *mp, continue; } bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, bno), - XFS_FSB_TO_BB(mp, 1)); + XFS_FSB_TO_BB(mp, 1), NULL); if (!bp) { do_warn(_("can't read block %d for rtbitmap inode\n"), bmbno); @@ -268,7 +268,7 @@ process_rtsummary(xfs_mount_t *mp, continue; } bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, bno), - XFS_FSB_TO_BB(mp, 1)); + XFS_FSB_TO_BB(mp, 1), NULL); if (!bp) { do_warn(_("can't read block %d for rtsummary inode\n"), sumbno); diff --git a/repair/scan.c b/repair/scan.c index f79342a..0b5ab1b 100644 --- a/repair/scan.c +++ b/repair/scan.c @@ -85,7 +85,7 @@ scan_sbtree( xfs_buf_t *bp; bp = libxfs_readbuf(mp->m_dev, XFS_AGB_TO_DADDR(mp, agno, root), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, NULL); if (!bp) { do_error(_("can't read btree block %d/%d\n"), agno, root); return; @@ -130,7 +130,7 @@ scan_lbtree( int dirty = 0; bp = libxfs_readbuf(mp->m_dev, XFS_FSB_TO_DADDR(mp, root), - XFS_FSB_TO_BB(mp, 1), 0); + XFS_FSB_TO_BB(mp, 1), 0, NULL); if (!bp) { do_error(_("can't read btree block %d/%d\n"), XFS_FSB_TO_AGNO(mp, root), @@ -1060,7 +1060,7 @@ scan_freelist( agflbuf = libxfs_readbuf(mp->m_dev, XFS_AG_DADDR(mp, agno, XFS_AGFL_DADDR(mp)), - XFS_FSS_TO_BB(mp, 1), 0); + XFS_FSS_TO_BB(mp, 1), 0, &xfs_agfl_buf_ops); if (!agflbuf) { do_abort(_("can't read agfl block for ag %d\n"), agno); return; @@ -1207,7 +1207,7 @@ scan_ag( int status; sbbuf = libxfs_readbuf(mp->m_dev, XFS_AG_DADDR(mp, agno, XFS_SB_DADDR), - XFS_FSS_TO_BB(mp, 1), 0); + XFS_FSS_TO_BB(mp, 1), 0, &xfs_sb_buf_ops); if (!sbbuf) { do_error(_("can't get root superblock for ag %d\n"), agno); return; @@ -1223,7 +1223,7 @@ scan_ag( agfbuf = libxfs_readbuf(mp->m_dev, XFS_AG_DADDR(mp, agno, XFS_AGF_DADDR(mp)), - XFS_FSS_TO_BB(mp, 1), 0); + XFS_FSS_TO_BB(mp, 1), 0, &xfs_agf_buf_ops); if (!agfbuf) { do_error(_("can't read agf block for ag %d\n"), agno); libxfs_putbuf(sbbuf); @@ -1234,7 +1234,7 @@ scan_ag( agibuf = libxfs_readbuf(mp->m_dev, XFS_AG_DADDR(mp, agno, XFS_AGI_DADDR(mp)), - XFS_FSS_TO_BB(mp, 1), 0); + XFS_FSS_TO_BB(mp, 1), 0, &xfs_agi_buf_ops); if (!agibuf) { do_error(_("can't read agi block for ag %d\n"), agno); libxfs_putbuf(agfbuf); @@ -1353,7 +1353,8 @@ scan_ags( } memset(agcnts, 0, mp->m_sb.sb_agcount * sizeof(*agcnts)); - create_work_queue(&wq, mp, scan_threads); + create_work_queue(&wq, mp, 1); + //create_work_queue(&wq, mp, scan_threads); for (i = 0; i < mp->m_sb.sb_agcount; i++) queue_work(&wq, scan_ag, i, &agcnts[i]); diff --git a/repair/xfs_repair.c b/repair/xfs_repair.c index 67a7446..7623560 100644 --- a/repair/xfs_repair.c +++ b/repair/xfs_repair.c @@ -558,9 +558,11 @@ main(int argc, char **argv) } /* prepare the mount structure */ - sbp = libxfs_readbuf(x.ddev, XFS_SB_DADDR, - 1 << (XFS_MAX_SECTORSIZE_LOG - BBSHIFT), 0); memset(&xfs_m, 0, sizeof(xfs_mount_t)); + libxfs_buftarg_init(&xfs_m, x.ddev, x.logdev, x.rtdev); + sbp = libxfs_readbuf(xfs_m.m_ddev_targp, XFS_SB_DADDR, + 1 << (XFS_MAX_SECTORSIZE_LOG - BBSHIFT), 0, + &xfs_sb_buf_ops); libxfs_sb_from_disk(&xfs_m.m_sb, XFS_BUF_TO_SBP(sbp)); /* -- 1.7.10.4 _______________________________________________ xfs mailing list xfs@xxxxxxxxxxx http://oss.sgi.com/mailman/listinfo/xfs