ubi: Use bitmaps in Fastmap self-check code

...don't waste memory by allocating one sizeof(int) per
PEB.

Signed-off-by: Richard Weinberger <richard@nod.at>
This commit is contained in:
Richard Weinberger 2016-06-14 10:12:18 +02:00
parent 74f2c6e9a4
commit 5d71afb008

View File

@ -15,20 +15,22 @@
*/ */
#include <linux/crc32.h> #include <linux/crc32.h>
#include <linux/bitmap.h>
#include "ubi.h" #include "ubi.h"
/** /**
* init_seen - allocate memory for used for debugging. * init_seen - allocate memory for used for debugging.
* @ubi: UBI device description object * @ubi: UBI device description object
*/ */
static inline int *init_seen(struct ubi_device *ubi) static inline unsigned long *init_seen(struct ubi_device *ubi)
{ {
int *ret; unsigned long *ret;
if (!ubi_dbg_chk_fastmap(ubi)) if (!ubi_dbg_chk_fastmap(ubi))
return NULL; return NULL;
ret = kcalloc(ubi->peb_count, sizeof(int), GFP_KERNEL); ret = kcalloc(BITS_TO_LONGS(ubi->peb_count), sizeof(unsigned long),
GFP_KERNEL);
if (!ret) if (!ret)
return ERR_PTR(-ENOMEM); return ERR_PTR(-ENOMEM);
@ -39,7 +41,7 @@ static inline int *init_seen(struct ubi_device *ubi)
* free_seen - free the seen logic integer array. * free_seen - free the seen logic integer array.
* @seen: integer array of @ubi->peb_count size * @seen: integer array of @ubi->peb_count size
*/ */
static inline void free_seen(int *seen) static inline void free_seen(unsigned long *seen)
{ {
kfree(seen); kfree(seen);
} }
@ -50,12 +52,12 @@ static inline void free_seen(int *seen)
* @pnum: The PEB to be makred as seen * @pnum: The PEB to be makred as seen
* @seen: integer array of @ubi->peb_count size * @seen: integer array of @ubi->peb_count size
*/ */
static inline void set_seen(struct ubi_device *ubi, int pnum, int *seen) static inline void set_seen(struct ubi_device *ubi, int pnum, unsigned long *seen)
{ {
if (!ubi_dbg_chk_fastmap(ubi) || !seen) if (!ubi_dbg_chk_fastmap(ubi) || !seen)
return; return;
seen[pnum] = 1; set_bit(pnum, seen);
} }
/** /**
@ -63,7 +65,7 @@ static inline void set_seen(struct ubi_device *ubi, int pnum, int *seen)
* @ubi: UBI device description object * @ubi: UBI device description object
* @seen: integer array of @ubi->peb_count size * @seen: integer array of @ubi->peb_count size
*/ */
static int self_check_seen(struct ubi_device *ubi, int *seen) static int self_check_seen(struct ubi_device *ubi, unsigned long *seen)
{ {
int pnum, ret = 0; int pnum, ret = 0;
@ -71,7 +73,7 @@ static int self_check_seen(struct ubi_device *ubi, int *seen)
return 0; return 0;
for (pnum = 0; pnum < ubi->peb_count; pnum++) { for (pnum = 0; pnum < ubi->peb_count; pnum++) {
if (!seen[pnum] && ubi->lookuptbl[pnum]) { if (test_bit(pnum, seen) && ubi->lookuptbl[pnum]) {
ubi_err(ubi, "self-check failed for PEB %d, fastmap didn't see it", pnum); ubi_err(ubi, "self-check failed for PEB %d, fastmap didn't see it", pnum);
ret = -EINVAL; ret = -EINVAL;
} }
@ -1139,7 +1141,7 @@ static int ubi_write_fastmap(struct ubi_device *ubi,
struct rb_node *tmp_rb; struct rb_node *tmp_rb;
int ret, i, j, free_peb_count, used_peb_count, vol_count; int ret, i, j, free_peb_count, used_peb_count, vol_count;
int scrub_peb_count, erase_peb_count; int scrub_peb_count, erase_peb_count;
int *seen_pebs = NULL; unsigned long *seen_pebs = NULL;
fm_raw = ubi->fm_buf; fm_raw = ubi->fm_buf;
memset(ubi->fm_buf, 0, ubi->fm_size); memset(ubi->fm_buf, 0, ubi->fm_size);