diff --git a/Makefile.in b/Makefile.in index eaff125..e67b300 100644 --- a/Makefile.in +++ b/Makefile.in @@ -70,6 +70,7 @@ SOURCE=\ persistent-data/space-maps/recursive.cc \ persistent-data/space_map.cc \ persistent-data/transaction_manager.cc \ + persistent-data/validators.cc \ thin-provisioning/device_tree.cc \ thin-provisioning/human_readable_format.cc \ thin-provisioning/mapping_tree.cc \ diff --git a/persistent-data/data-structures/btree.h b/persistent-data/data-structures/btree.h index 3966148..b91fb20 100644 --- a/persistent-data/data-structures/btree.h +++ b/persistent-data/data-structures/btree.h @@ -22,6 +22,7 @@ #include "base/endian_utils.h" #include "persistent-data/transaction_manager.h" #include "persistent-data/data-structures/ref_counter.h" +#include "persistent-data/data-structures/btree_disk_structures.h" #include #include @@ -61,36 +62,6 @@ namespace persistent_data { using namespace base; using namespace std; - uint32_t const BTREE_CSUM_XOR = 121107; - - //------------------------------------------------ - // On disk data layout for btree nodes - enum node_flags { - INTERNAL_NODE = 1, - LEAF_NODE = 1 << 1 - }; - - struct node_header { - le32 csum; - le32 flags; - le64 blocknr; /* which block this node is supposed to live in */ - - le32 nr_entries; - le32 max_entries; - le32 value_size; - le32 padding; - } __attribute__((packed)); - - struct disk_node { - struct node_header header; - le64 keys[0]; - } __attribute__((packed)); - - enum node_type { - INTERNAL, - LEAF - }; - //------------------------------------------------ // Class that acts as an interface over the raw little endian btree // node data. diff --git a/persistent-data/data-structures/btree.tcc b/persistent-data/data-structures/btree.tcc index cd19fc4..80f2b94 100644 --- a/persistent-data/data-structures/btree.tcc +++ b/persistent-data/data-structures/btree.tcc @@ -21,6 +21,7 @@ #include "persistent-data/errors.h" #include "persistent-data/checksum.h" #include "persistent-data/transaction_manager.h" +#include "persistent-data/validators.h" #include @@ -32,35 +33,6 @@ namespace { using namespace btree_detail; using namespace std; - struct btree_node_validator : public bcache::validator { - virtual void check(void const *raw, block_address location) const { - disk_node const *data = reinterpret_cast(raw); - node_header const *n = &data->header; - crc32c sum(BTREE_CSUM_XOR); - sum.append(&n->flags, MD_BLOCK_SIZE - sizeof(uint32_t)); - if (sum.get_sum() != to_cpu(n->csum)) { - std::ostringstream out; - out << "bad checksum in btree node (block " << location << ")"; - throw checksum_error(out.str()); - } - - if (to_cpu(n->blocknr) != location) { - std::ostringstream out; - out << "bad block nr in btree node (block = " << location << ")"; - throw checksum_error(out.str()); - } - } - - virtual void prepare(void *raw, block_address location) const { - disk_node *data = reinterpret_cast(raw); - node_header *n = &data->header; - n->blocknr = to_disk(location); - - crc32c sum(BTREE_CSUM_XOR); - sum.append(&n->flags, MD_BLOCK_SIZE - sizeof(uint32_t)); - n->csum = to_disk(sum.get_sum()); - } - }; } //---------------------------------------------------------------- @@ -416,7 +388,7 @@ namespace persistent_data { destroy_(false), internal_rc_(tm.get_sm()), rc_(rc), - validator_(new btree_node_validator) + validator_(create_btree_node_validator()) { using namespace btree_detail; @@ -450,7 +422,7 @@ namespace persistent_data { root_(root), internal_rc_(tm.get_sm()), rc_(rc), - validator_(new btree_node_validator) + validator_(create_btree_node_validator()) { } diff --git a/persistent-data/validators.cc b/persistent-data/validators.cc new file mode 100644 index 0000000..b9c163c --- /dev/null +++ b/persistent-data/validators.cc @@ -0,0 +1,53 @@ +#include "persistent-data/block.h" +#include "persistent-data/checksum.h" +#include "persistent-data/data-structures/btree_disk_structures.h" +#include "persistent-data/errors.h" +#include "persistent-data/validators.h" + +using namespace bcache; +using namespace persistent_data; + +//---------------------------------------------------------------- + +namespace { + using namespace btree_detail; + + struct btree_node_validator : public bcache::validator { + virtual void check(void const *raw, block_address location) const { + disk_node const *data = reinterpret_cast(raw); + node_header const *n = &data->header; + crc32c sum(BTREE_CSUM_XOR); + sum.append(&n->flags, MD_BLOCK_SIZE - sizeof(uint32_t)); + if (sum.get_sum() != to_cpu(n->csum)) { + std::ostringstream out; + out << "bad checksum in btree node (block " << location << ")"; + throw checksum_error(out.str()); + } + + if (to_cpu(n->blocknr) != location) { + std::ostringstream out; + out << "bad block nr in btree node (block = " << location << ")"; + throw checksum_error(out.str()); + } + } + + virtual void prepare(void *raw, block_address location) const { + disk_node *data = reinterpret_cast(raw); + node_header *n = &data->header; + n->blocknr = to_disk(location); + + crc32c sum(BTREE_CSUM_XOR); + sum.append(&n->flags, MD_BLOCK_SIZE - sizeof(uint32_t)); + n->csum = to_disk(sum.get_sum()); + } + }; +} + +//---------------------------------------------------------------- + +bcache::validator::ptr persistent_data::create_btree_node_validator() +{ + return bcache::validator::ptr(new btree_node_validator()); +} + +//---------------------------------------------------------------- diff --git a/persistent-data/validators.h b/persistent-data/validators.h new file mode 100644 index 0000000..0068883 --- /dev/null +++ b/persistent-data/validators.h @@ -0,0 +1,14 @@ +#ifndef PERSISTENT_DATA_VALIDATORS_H +#define PERSISTENT_DATA_VALIDATORS_H + +#include "block-cache/block_cache.h" + +//---------------------------------------------------------------- + +namespace persistent_data { + bcache::validator::ptr create_btree_node_validator(); +} + +//---------------------------------------------------------------- + +#endif