From: NeilBrown <neilb@suse.de>
To: linux-raid@vger.kernel.org
Subject: [md PATCH 08/24] md/bitmap: separate bitmap file allocation to its own function.
Date: Tue, 17 Apr 2012 18:43:40 +1000 [thread overview]
Message-ID: <20120417084340.6433.93849.stgit@notabene.brown> (raw)
In-Reply-To: <20120417084324.6433.68345.stgit@notabene.brown>
This will allow allocation before swapping in a new bitmap.
Signed-off-by: NeilBrown <neilb@suse.de>
---
drivers/md/bitmap.c | 113 ++++++++++++++++++++++++++++++---------------------
1 file changed, 67 insertions(+), 46 deletions(-)
diff --git a/drivers/md/bitmap.c b/drivers/md/bitmap.c
index 9221f97..0819ec2 100644
--- a/drivers/md/bitmap.c
+++ b/drivers/md/bitmap.c
@@ -714,6 +714,58 @@ static inline struct page *filemap_get_page(struct bitmap_storage *store,
- file_page_index(store, 0)];
}
+static int bitmap_storage_alloc(struct bitmap_storage *store,
+ unsigned long chunks, int with_super)
+{
+ int pnum;
+ unsigned long num_pages;
+ unsigned long bytes;
+
+ bytes = DIV_ROUND_UP(chunks, 8);
+ if (with_super)
+ bytes += sizeof(bitmap_super_t);
+
+ num_pages = DIV_ROUND_UP(bytes, PAGE_SIZE);
+
+ store->filemap = kmalloc(sizeof(struct page *)
+ * num_pages, GFP_KERNEL);
+ if (!store->filemap)
+ return -ENOMEM;
+
+ if (with_super && !store->sb_page) {
+ store->sb_page = alloc_page(GFP_KERNEL);
+ if (store->sb_page == NULL)
+ return -ENOMEM;
+ store->sb_page->index = 0;
+ }
+ pnum = 0;
+ if (store->sb_page) {
+ store->filemap[0] = store->sb_page;
+ pnum = 1;
+ }
+ for ( ; pnum < num_pages; pnum++) {
+ store->filemap[pnum] = alloc_page(GFP_KERNEL);
+ if (!store->filemap[pnum]) {
+ store->file_pages = pnum;
+ return -ENOMEM;
+ }
+ store->filemap[pnum]->index = pnum;
+ }
+ store->file_pages = pnum;
+
+ /* We need 4 bits per page, rounded up to a multiple
+ * of sizeof(unsigned long) */
+ store->filemap_attr = kzalloc(
+ roundup(DIV_ROUND_UP(num_pages*4, 8), sizeof(unsigned long)),
+ GFP_KERNEL);
+ if (!store->filemap_attr)
+ return -ENOMEM;
+
+ store->bytes = bytes;
+
+ return 0;
+}
+
static void bitmap_file_unmap(struct bitmap *bitmap)
{
struct page **map, *sb_page;
@@ -938,11 +990,10 @@ static void bitmap_set_memory_bits(struct bitmap *bitmap, sector_t offset, int n
static int bitmap_init_from_disk(struct bitmap *bitmap, sector_t start)
{
unsigned long i, chunks, index, oldindex, bit;
- int pnum;
struct page *page = NULL;
- unsigned long num_pages, bit_cnt = 0;
+ unsigned long bit_cnt = 0;
struct file *file;
- unsigned long bytes, offset;
+ unsigned long offset;
int outofdate;
int ret = -ENOSPC;
void *paddr;
@@ -971,53 +1022,23 @@ static int bitmap_init_from_disk(struct bitmap *bitmap, sector_t start)
printk(KERN_INFO "%s: bitmap file is out of date, doing full "
"recovery\n", bmname(bitmap));
- bytes = DIV_ROUND_UP(bitmap->chunks, 8);
- if (!bitmap->mddev->bitmap_info.external)
- bytes += sizeof(bitmap_super_t);
-
- store->bytes = bytes;
-
- num_pages = DIV_ROUND_UP(bytes, PAGE_SIZE);
-
- if (file && i_size_read(file->f_mapping->host) < bytes) {
+ if (file && i_size_read(file->f_mapping->host) < store->bytes) {
printk(KERN_INFO "%s: bitmap file too short %lu < %lu\n",
- bmname(bitmap),
- (unsigned long) i_size_read(file->f_mapping->host),
- bytes);
+ bmname(bitmap),
+ (unsigned long) i_size_read(file->f_mapping->host),
+ store->bytes);
goto err;
}
- ret = -ENOMEM;
-
- store->filemap = kmalloc(sizeof(struct page *)
- * num_pages, GFP_KERNEL);
- if (!store->filemap)
+ ret = bitmap_storage_alloc(&bitmap->storage, bitmap->chunks,
+ !bitmap->mddev->bitmap_info.external);
+ if (ret)
goto err;
- pnum = 0;
+ oldindex = ~0L;
offset = 0;
- if (store->sb_page) {
- store->filemap[0] = store->sb_page;
- pnum = 1;
+ if (!bitmap->mddev->bitmap_info.external)
offset = sizeof(bitmap_super_t);
- }
- for ( ; pnum < num_pages; pnum++) {
- store->filemap[pnum] = alloc_page(GFP_KERNEL);
- if (!store->filemap[pnum]) {
- store->file_pages = pnum;
- goto err;
- }
- }
- store->file_pages = pnum;
-
- /* We need 4 bits per page, rounded up to a multiple of sizeof(unsigned long) */
- store->filemap_attr = kzalloc(
- roundup(DIV_ROUND_UP(num_pages*4, 8), sizeof(unsigned long)),
- GFP_KERNEL);
- if (!store->filemap_attr)
- goto err;
-
- oldindex = ~0L;
for (i = 0; i < chunks; i++) {
int b;
@@ -1026,8 +1047,8 @@ static int bitmap_init_from_disk(struct bitmap *bitmap, sector_t start)
if (index != oldindex) { /* this is a new page, read it in */
int count;
/* unmap the old page, we're done with it */
- if (index == num_pages-1)
- count = bytes - index * PAGE_SIZE;
+ if (index == store->file_pages-1)
+ count = store->bytes - index * PAGE_SIZE;
else
count = PAGE_SIZE;
page = store->filemap[index];
@@ -1081,9 +1102,9 @@ static int bitmap_init_from_disk(struct bitmap *bitmap, sector_t start)
}
printk(KERN_INFO "%s: bitmap initialized from disk: "
- "read %lu/%lu pages, set %lu of %lu bits\n",
+ "read %lu pages, set %lu of %lu bits\n",
bmname(bitmap), store->file_pages,
- num_pages, bit_cnt, chunks);
+ bit_cnt, chunks);
return 0;
next prev parent reply other threads:[~2012-04-17 8:43 UTC|newest]
Thread overview: 27+ messages / expand[flat|nested] mbox.gz Atom feed top
2012-04-17 8:43 [md PATCH 00/24] Allow bitmaps to be resized NeilBrown
2012-04-17 8:43 ` [md PATCH 01/24] md/bitmap: disentangle two different 'pending' flags NeilBrown
2012-04-17 8:43 ` [md PATCH 02/24] md/bitmap: add new 'space' attribute for bitmaps NeilBrown
2012-04-17 8:43 ` [md PATCH 07/24] md/bitmap: store bytes in file rather than just in last page NeilBrown
2012-04-17 8:43 ` NeilBrown [this message]
2012-04-17 8:43 ` [md PATCH 03/24] md/bitmap: allow a bitmap with no backing storage NeilBrown
2012-04-17 8:43 ` [md PATCH 06/24] md/bitmap: move some fields of 'struct bitmap' into a 'storage' substruct NeilBrown
2012-04-17 8:43 ` [md PATCH 05/24] md/bitmap: change *_page_attr() to take a page number, not a page NeilBrown
2012-04-17 8:43 ` [md PATCH 04/24] md/bitmap: centralise allocation of bitmap file pages NeilBrown
2012-04-17 8:43 ` [md PATCH 09/24] md/bitmap: move storage allocation from bitmap_load to bitmap_create NeilBrown
2012-04-17 8:43 ` [md PATCH 16/24] md/bitmap: make _page_attr bitops atomic NeilBrown
2012-04-17 8:43 ` [md PATCH 11/24] md/bitmap: remove single-bit manipulation on sb->state NeilBrown
2012-04-17 8:43 ` [md PATCH 13/24] md/bitmap: convert some spin_lock_irqsave to spin_lock_irq NeilBrown
2012-04-17 8:43 ` [md PATCH 10/24] md/bitmap: remove bitmap_mask_state NeilBrown
2012-04-17 8:43 ` [md PATCH 15/24] md/bitmap: merge bitmap_file_unmap and bitmap_file_put NeilBrown
2012-04-17 8:43 ` [md PATCH 12/24] md/bitmap: use set_bit, test_bit, etc for operation on bitmap->flags NeilBrown
2012-04-17 8:43 ` [md PATCH 14/24] md/bitmap: remove async freeing of bitmap file NeilBrown
2012-04-17 8:43 ` [md PATCH 23/24] md/raid10: resize bitmap when required during reshape NeilBrown
2012-04-17 8:43 ` [md PATCH 18/24] md/bitmap: create a 'struct bitmap_counts' substructure of 'struct bitmap' NeilBrown
2012-04-17 8:43 ` [md PATCH 17/24] md/bitmap: make bitmap bitops atomic NeilBrown
2012-04-17 8:43 ` [md PATCH 20/24] md/bitmap: add bitmap_resize function to allow bitmap resizing NeilBrown
2012-04-17 8:43 ` [md PATCH 19/24] md/bitmap: use DIV_ROUND_UP instead of open-code NeilBrown
2012-04-17 8:43 ` [md PATCH 22/24] md: allow array to be resized while bitmap is present NeilBrown
2012-04-17 8:43 ` [md PATCH 21/24] md/bitmap: make sure reshape request are reflected in superblock NeilBrown
2012-04-17 8:43 ` [md PATCH 24/24] md/raid5: Allow reshape while a bitmap is present NeilBrown
2012-04-18 2:07 ` [md PATCH 00/24] Allow bitmaps to be resized Jack Wang
2012-04-18 3:35 ` NeilBrown
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20120417084340.6433.93849.stgit@notabene.brown \
--to=neilb@suse.de \
--cc=linux-raid@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).