Commit ab45e763 authored by Vishal Verma's avatar Vishal Verma Committed by Dan Williams

libnvdimm, btt: consolidate arena validation

Use arena_is_valid as a common routine for checking the validity of an
info block from both discover_arenas, and nd_btt_probe.

As a result, don't check for validity of the BTT's UUID, and lbasize.
The checksum in the BTT info block guarantees self-consistency, and when
we're called from nd_btt_probe, we don't have a valid uuid or lbasize
available to check against.

Also cleanup to return a bool instead of an int.
Signed-off-by: default avatarVishal Verma <vishal.l.verma@intel.com>
Signed-off-by: default avatarDan Williams <dan.j.williams@intel.com>
parent fbde1414
...@@ -582,32 +582,6 @@ static void free_arenas(struct btt *btt) ...@@ -582,32 +582,6 @@ static void free_arenas(struct btt *btt)
} }
} }
/*
* This function checks if the metadata layout is valid and error free
*/
static int arena_is_valid(struct nd_btt *nd_btt, struct btt_sb *super)
{
u64 checksum;
if (memcmp(super->uuid, nd_btt->uuid, 16))
return 0;
checksum = le64_to_cpu(super->checksum);
super->checksum = 0;
if (checksum != nd_btt_sb_checksum(super))
return 0;
super->checksum = cpu_to_le64(checksum);
if (nd_btt->lbasize != le32_to_cpu(super->external_lbasize))
return 0;
/* TODO: figure out action for this */
if ((le32_to_cpu(super->flags) & IB_FLAG_ERROR_MASK) != 0)
dev_info(&nd_btt->dev, "Found arena with an error flag\n");
return 1;
}
/* /*
* This function reads an existing valid btt superblock and * This function reads an existing valid btt superblock and
* populates the corresponding arena_info struct * populates the corresponding arena_info struct
...@@ -665,7 +639,7 @@ static int discover_arenas(struct btt *btt) ...@@ -665,7 +639,7 @@ static int discover_arenas(struct btt *btt)
if (ret) if (ret)
goto out; goto out;
if (!arena_is_valid(btt->nd_btt, super)) { if (!nd_btt_arena_is_valid(btt->nd_btt, super)) {
if (remaining == btt->rawsize) { if (remaining == btt->rawsize) {
btt->init_state = INIT_NOTFOUND; btt->init_state = INIT_NOTFOUND;
dev_info(to_dev(arena), "No existing arenas\n"); dev_info(to_dev(arena), "No existing arenas\n");
......
...@@ -182,4 +182,7 @@ struct btt { ...@@ -182,4 +182,7 @@ struct btt {
int init_state; int init_state;
int num_arenas; int num_arenas;
}; };
bool nd_btt_arena_is_valid(struct nd_btt *nd_btt, struct btt_sb *super);
#endif #endif
...@@ -342,6 +342,38 @@ struct device *nd_btt_create(struct nd_region *nd_region) ...@@ -342,6 +342,38 @@ struct device *nd_btt_create(struct nd_region *nd_region)
return dev; return dev;
} }
/**
* nd_btt_arena_is_valid - check if the metadata layout is valid
* @nd_btt: device with BTT geometry and backing device info
* @super: pointer to the arena's info block being tested
*
* Check consistency of the btt info block with itself by validating
* the checksum.
*
* Returns:
* false for an invalid info block, true for a valid one
*/
bool nd_btt_arena_is_valid(struct nd_btt *nd_btt, struct btt_sb *super)
{
u64 checksum;
if (memcmp(super->signature, BTT_SIG, BTT_SIG_LEN) != 0)
return false;
checksum = le64_to_cpu(super->checksum);
super->checksum = 0;
if (checksum != nd_btt_sb_checksum(super))
return false;
super->checksum = cpu_to_le64(checksum);
/* TODO: figure out action for this */
if ((le32_to_cpu(super->flags) & IB_FLAG_ERROR_MASK) != 0)
dev_info(&nd_btt->dev, "Found arena with an error flag\n");
return true;
}
EXPORT_SYMBOL(nd_btt_arena_is_valid);
/* /*
* nd_btt_sb_checksum: compute checksum for btt info block * nd_btt_sb_checksum: compute checksum for btt info block
* *
...@@ -364,8 +396,6 @@ EXPORT_SYMBOL(nd_btt_sb_checksum); ...@@ -364,8 +396,6 @@ EXPORT_SYMBOL(nd_btt_sb_checksum);
static int __nd_btt_probe(struct nd_btt *nd_btt, static int __nd_btt_probe(struct nd_btt *nd_btt,
struct nd_namespace_common *ndns, struct btt_sb *btt_sb) struct nd_namespace_common *ndns, struct btt_sb *btt_sb)
{ {
u64 checksum;
if (!btt_sb || !ndns || !nd_btt) if (!btt_sb || !ndns || !nd_btt)
return -ENODEV; return -ENODEV;
...@@ -375,14 +405,8 @@ static int __nd_btt_probe(struct nd_btt *nd_btt, ...@@ -375,14 +405,8 @@ static int __nd_btt_probe(struct nd_btt *nd_btt,
if (nvdimm_namespace_capacity(ndns) < SZ_16M) if (nvdimm_namespace_capacity(ndns) < SZ_16M)
return -ENXIO; return -ENXIO;
if (memcmp(btt_sb->signature, BTT_SIG, BTT_SIG_LEN) != 0) if (!nd_btt_arena_is_valid(nd_btt, btt_sb))
return -ENODEV;
checksum = le64_to_cpu(btt_sb->checksum);
btt_sb->checksum = 0;
if (checksum != nd_btt_sb_checksum(btt_sb))
return -ENODEV; return -ENODEV;
btt_sb->checksum = cpu_to_le64(checksum);
nd_btt->lbasize = le32_to_cpu(btt_sb->external_lbasize); nd_btt->lbasize = le32_to_cpu(btt_sb->external_lbasize);
nd_btt->uuid = kmemdup(btt_sb->uuid, 16, GFP_KERNEL); nd_btt->uuid = kmemdup(btt_sb->uuid, 16, GFP_KERNEL);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment