commit 9ea2abec02ee82382786e0ee6613a67a669af87b Author: Bob Peterson <bob@ganesha.peterson> Date: Mon Aug 31 10:59:32 2009 -0500 Make gfs2_edit -p <block> blockalloc work for gfs1 file systems Several gfs2_edit options, like blockalloc, are designed to read in the resource group information to determine the block status according to the bitmap on disk. That was working fine for GFS2 file systems but not for GFS file systems. This patch allows gfs2_edit to read in the gfs1 rindex and parse the bitmaps by using libgfs2's gfs1 functions. rhbz#503529 diff --git a/gfs2/convert/gfs2_convert.c b/gfs2/convert/gfs2_convert.c index 0e0e5d8..1b4b1bd 100644 --- a/gfs2/convert/gfs2_convert.c +++ b/gfs2/convert/gfs2_convert.c @@ -1163,7 +1163,7 @@ static int init(struct gfs2_sbd *sbp) sbp->md.riinode->i_di.di_mode &= ~S_IFMT; sbp->md.riinode->i_di.di_mode |= S_IFDIR; printf("Examining file system"); - if (gfs1_ri_update(sbp, 0, &rgcount)){ + if (gfs1_ri_update(sbp, 0, &rgcount, 0)){ log_crit("Unable to fill in resource group information.\n"); return -1; } diff --git a/gfs2/edit/hexedit.c b/gfs2/edit/hexedit.c index 3f932da..a720aac 100644 --- a/gfs2/edit/hexedit.c +++ b/gfs2/edit/hexedit.c @@ -44,7 +44,9 @@ const char *mtypes[] = {"none", "sb", "rg", "rb", "di", "in", "lf", "jd", "lh", "ld", "ea", "ed", "lb", "13", "qc"}; -const char *allocdesc[] = {"Free ", "Data ", "Unlnk", "Meta ", "Resrv"}; +const char *allocdesc[2][5] = { + {"Free ", "Data ", "Unlnk", "Meta ", "Resrv"}, + {"Free ", "Data ", "FreeM", "Meta ", "Resrv"},}; int display(int identify_only); extern void eol(int col); @@ -591,7 +593,7 @@ int display_block_type(const char *lpBuffer, int from_restore) print_gfs2("(p.%d of %d--%s)", pgnum + 1, (sbd.bsize % screen_chunk_size) > 0 ? sbd.bsize / screen_chunk_size + 1 : sbd.bsize / - screen_chunk_size, allocdesc[type]); + screen_chunk_size, allocdesc[gfs1][type]); /*eol(9);*/ if ((*(lpBuffer+7) == GFS2_METATYPE_IN) || (*(lpBuffer+7) == GFS2_METATYPE_DI && @@ -1673,7 +1675,6 @@ void read_superblock(int fd) osi_list_init(&sbd.rglist); init_buf_list(&sbd, &sbd.buf_list, 128 << 20); init_buf_list(&sbd, &sbd.nvbuf_list, 0xffffffff); - compute_constants(&sbd); gfs2_sb_in(&sbd.sd_sb, buf); /* parse it out into the sb structure */ /* Check to see if this is really gfs1 */ if (sbd1->sb_fs_format == GFS_FORMAT_FS && @@ -1703,6 +1704,8 @@ void read_superblock(int fd) sizeof(uint64_t); sbd.md.riinode = gfs2_load_inode(&sbd, sbd1->sb_rindex_di.no_addr); + sbd.fssize = sbd.device.length; + gfs1_ri_update(&sbd, 0, &count, 1); } else { sbd.sd_inptrs = (sbd.bsize - sizeof(struct gfs2_meta_header)) / sizeof(uint64_t); @@ -1711,10 +1714,10 @@ void read_superblock(int fd) sbd.master_dir = gfs2_load_inode(&sbd, sbd.sd_sb.sb_master_dir.no_addr); gfs2_lookupi(sbd.master_dir, "rindex", 6, &sbd.md.riinode); + sbd.fssize = sbd.device.length; + ri_update(&sbd, 0, &count); } - sbd.fssize = sbd.device.length; - ri_update(&sbd, 0, &count); } /* ------------------------------------------------------------------------ */ @@ -2443,7 +2446,7 @@ void find_change_block_alloc(int *newval) printf("Error: value %d is not valid.\nValid values are:\n", *newval); for (i = GFS2_BLKST_FREE; i <= GFS2_BLKST_DINODE; i++) - printf("%d - %s\n", i, allocdesc[i]); + printf("%d - %s\n", i, allocdesc[gfs1][i]); gfs2_rgrp_free(&sbd.rglist, not_updated); exit(-1); } @@ -2460,7 +2463,7 @@ void find_change_block_alloc(int *newval) rgd = gfs2_blk2rgrpd(&sbd, block); if (rgd) { type = gfs2_get_bitmap(&sbd, block, rgd); - printf("%d (%s)\n", type, allocdesc[type]); + printf("%d (%s)\n", type, allocdesc[gfs1][type]); gfs2_rgrp_relse(rgd, not_updated); } else { gfs2_rgrp_free(&sbd.rglist, not_updated); diff --git a/gfs2/edit/savemeta.c b/gfs2/edit/savemeta.c index 064eaef..b5bf33f 100644 --- a/gfs2/edit/savemeta.c +++ b/gfs2/edit/savemeta.c @@ -551,7 +551,7 @@ void savemeta(char *out_fn, int saveoption) printf("Reading resource groups..."); fflush(stdout); if (gfs1) - slow = gfs1_ri_update(&sbd, 0, &rgcount); + slow = gfs1_ri_update(&sbd, 0, &rgcount, 0); else slow = ri_update(&sbd, 0, &rgcount); printf("Done.\n\n"); diff --git a/gfs2/libgfs2/gfs1.c b/gfs2/libgfs2/gfs1.c index c518e5a..bef6aef 100644 --- a/gfs2/libgfs2/gfs1.c +++ b/gfs2/libgfs2/gfs1.c @@ -290,7 +290,7 @@ int gfs1_rindex_read(struct gfs2_sbd *sdp, int fd, int *count1) * * Returns: 0 on success, -1 on failure. */ -int gfs1_ri_update(struct gfs2_sbd *sdp, int fd, int *rgcount) +int gfs1_ri_update(struct gfs2_sbd *sdp, int fd, int *rgcount, int quiet) { struct rgrp_list *rgd; osi_list_t *tmp; @@ -308,7 +308,7 @@ int gfs1_ri_update(struct gfs2_sbd *sdp, int fd, int *rgcount) if (errblock) return errblock; count2++; - if (count2 % 100 == 0) { + if (!quiet && count2 % 100 == 0) { printf("."); fflush(stdout); } diff --git a/gfs2/libgfs2/libgfs2.h b/gfs2/libgfs2/libgfs2.h index 64d36d0..1283353 100644 --- a/gfs2/libgfs2/libgfs2.h +++ b/gfs2/libgfs2/libgfs2.h @@ -582,7 +582,7 @@ void gfs1_block_map(struct gfs2_inode *ip, uint64_t lblock, int *new, int gfs1_readi(struct gfs2_inode *ip, void *buf, uint64_t offset, unsigned int size); int gfs1_rindex_read(struct gfs2_sbd *sdp, int fd, int *count1); -int gfs1_ri_update(struct gfs2_sbd *sdp, int fd, int *rgcount); +int gfs1_ri_update(struct gfs2_sbd *sdp, int fd, int *rgcount, int quiet); struct gfs2_inode *gfs_inode_get(struct gfs2_sbd *sdp, struct gfs2_buffer_head *bh);