gfs2-utils: RHEL7 - libgfs2: Add support for allocating entire rgrp headers

Andrew Price andyp at fedoraproject.org
Mon Sep 8 17:34:34 UTC 2014


Gitweb:        http://git.fedorahosted.org/git/?p=gfs2-utils.git;a=commitdiff;h=75495994a710d09a8a9a7b6f4a09b73e01a2a772
Commit:        75495994a710d09a8a9a7b6f4a09b73e01a2a772
Parent:        dc2be884934f140393ead923c09f7798a7263e29
Author:        Andrew Price <anprice at redhat.com>
AuthorDate:    Tue Aug 26 23:26:30 2014 +0100
Committer:     Andrew Price <anprice at redhat.com>
CommitterDate: Fri Sep 5 14:57:46 2014 +0100

libgfs2: Add support for allocating entire rgrp headers

Before we can allocate files without writing buffers back to disk
immediately we need to hold the bitmap blocks for one rgrp in memory.
Add a lgfs2_rgrp_bitbuf_alloc() function which allocates the memory for
a resource group's bitmap blocks in one chunk, and also a matching _free
function.

Signed-off-by: Andrew Price <anprice at redhat.com>
---
 gfs2/libgfs2/libgfs2.h |    2 ++
 gfs2/libgfs2/rgrp.c    |   48 ++++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 50 insertions(+), 0 deletions(-)

diff --git a/gfs2/libgfs2/libgfs2.h b/gfs2/libgfs2/libgfs2.h
index 43529a0..d683dc7 100644
--- a/gfs2/libgfs2/libgfs2.h
+++ b/gfs2/libgfs2/libgfs2.h
@@ -201,6 +201,8 @@ extern uint32_t lgfs2_rgrp_align_len(const lgfs2_rgrps_t rgs, uint32_t len);
 extern unsigned lgfs2_rgsize_for_data(uint64_t blksreq, unsigned bsize);
 extern uint32_t lgfs2_rgrps_plan(const lgfs2_rgrps_t rgs, uint64_t space, uint32_t tgtsize);
 extern lgfs2_rgrp_t lgfs2_rgrps_append(lgfs2_rgrps_t rgs, struct gfs2_rindex *entry);
+extern int lgfs2_rgrp_bitbuf_alloc(lgfs2_rgrp_t rg);
+extern void lgfs2_rgrp_bitbuf_free(lgfs2_rgrp_t rg);
 extern int lgfs2_rgrp_write(int fd, lgfs2_rgrp_t rg);
 extern const struct gfs2_rindex *lgfs2_rgrp_index(lgfs2_rgrp_t rg);
 extern const struct gfs2_rgrp *lgfs2_rgrp_rgrp(lgfs2_rgrp_t rg);
diff --git a/gfs2/libgfs2/rgrp.c b/gfs2/libgfs2/rgrp.c
index 772e6d0..57551c6 100644
--- a/gfs2/libgfs2/rgrp.c
+++ b/gfs2/libgfs2/rgrp.c
@@ -99,6 +99,54 @@ struct rgrp_tree *gfs2_blk2rgrpd(struct gfs2_sbd *sdp, uint64_t blk)
 }
 
 /**
+ * Allocate a multi-block buffer for a resource group's bitmaps. This is done
+ * as one chunk and should be freed using lgfs2_rgrp_bitbuf_free().
+ * Returns 0 on success with the bitmap buffer allocated in the resource group,
+ * or non-zero on failure with errno set.
+ */
+int lgfs2_rgrp_bitbuf_alloc(lgfs2_rgrp_t rg)
+{
+	struct gfs2_sbd *sdp = rg->rgrps->sdp;
+	unsigned i;
+	char *bufs;
+
+	bufs = calloc(rg->ri.ri_length, sizeof(struct gfs2_buffer_head) + sdp->bsize);
+	if (bufs == NULL)
+		return 1;
+
+	rg->bits[0].bi_bh = (struct gfs2_buffer_head *)bufs;
+	rg->bits[0].bi_bh->iov.iov_base = (char *)(rg->bits[0].bi_bh + 1);
+	rg->bits[0].bi_bh->iov.iov_len = sdp->bsize;
+	rg->bits[0].bi_bh->b_blocknr = rg->ri.ri_addr;
+	rg->bits[0].bi_bh->sdp = sdp;
+
+	for (i = 1; i < rg->ri.ri_length; i++) {
+		char *nextbuf = rg->bits[i - 1].bi_bh->b_data + sdp->bsize;
+		rg->bits[i].bi_bh = (struct gfs2_buffer_head *)(nextbuf);
+		rg->bits[i].bi_bh->iov.iov_base = (char *)(rg->bits[i].bi_bh + 1);
+		rg->bits[i].bi_bh->iov.iov_len = sdp->bsize;
+		rg->bits[i].bi_bh->b_blocknr = rg->ri.ri_addr + i;
+		rg->bits[i].bi_bh->sdp = sdp;
+	}
+	return 0;
+}
+
+/**
+ * Free the multi-block bitmap buffer from a resource group. The buffer should
+ * have been allocated as a single chunk as in lgfs2_rgrp_bitbuf_alloc().
+ * This does not implicitly write the bitmaps to disk. Use lgfs2_rgrp_write()
+ * for that.
+ * rg: The resource groups whose bitmap buffer should be freed.
+ */
+void lgfs2_rgrp_bitbuf_free(lgfs2_rgrp_t rg)
+{
+	unsigned i;
+	free(rg->bits[0].bi_bh);
+	for (i = 0; i < rg->ri.ri_length; i++)
+		rg->bits[i].bi_bh = NULL;
+}
+
+/**
  * gfs2_rgrp_read - read in the resource group information from disk.
  * @rgd - resource group structure
  * returns: 0 if no error, otherwise the block number that failed


More information about the cluster-commits mailing list