1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-05-28 11:45:11 +00:00

LibSQL: Use Block::Index everywhere; rename pointer to block_index

No functional changes.
This commit is contained in:
Jelle Raaijmakers 2023-04-23 13:59:56 +02:00 committed by Tim Flynn
parent 6601ff9d65
commit fdac8331cc
19 changed files with 202 additions and 203 deletions

View file

@ -153,7 +153,7 @@ void insert_and_get_to_and_from_btree(int num_keys)
for (auto ix = 0; ix < num_keys; ix++) { for (auto ix = 0; ix < num_keys; ix++) {
SQL::Key k(btree->descriptor()); SQL::Key k(btree->descriptor());
k[0] = keys[ix]; k[0] = keys[ix];
k.set_pointer(pointers[ix]); k.set_block_index(pointers[ix]);
btree->insert(k); btree->insert(k);
} }
#ifdef LIST_TREE #ifdef LIST_TREE
@ -189,7 +189,7 @@ void insert_into_and_scan_btree(int num_keys)
for (auto ix = 0; ix < num_keys; ix++) { for (auto ix = 0; ix < num_keys; ix++) {
SQL::Key k(btree->descriptor()); SQL::Key k(btree->descriptor());
k[0] = keys[ix]; k[0] = keys[ix];
k.set_pointer(pointers[ix]); k.set_block_index(pointers[ix]);
btree->insert(k); btree->insert(k);
} }
@ -213,7 +213,7 @@ void insert_into_and_scan_btree(int num_keys)
auto key_value = key[0].to_int<i32>(); auto key_value = key[0].to_int<i32>();
for (auto ix = 0; ix < num_keys; ix++) { for (auto ix = 0; ix < num_keys; ix++) {
if (keys[ix] == key_value) { if (keys[ix] == key_value) {
EXPECT_EQ(key.pointer(), pointers[ix]); EXPECT_EQ(key.block_index(), pointers[ix]);
break; break;
} }
} }

View file

@ -127,12 +127,12 @@ NonnullRefPtr<SQL::HashIndex> setup_hash_index(SQL::Serializer& serializer)
tuple_descriptor->append({ "schema", "table", "key_value", SQL::SQLType::Integer, SQL::Order::Ascending }); tuple_descriptor->append({ "schema", "table", "key_value", SQL::SQLType::Integer, SQL::Order::Ascending });
tuple_descriptor->append({ "schema", "table", "text_value", SQL::SQLType::Text, SQL::Order::Ascending }); tuple_descriptor->append({ "schema", "table", "text_value", SQL::SQLType::Text, SQL::Order::Ascending });
auto directory_pointer = serializer.heap().user_value(0); auto directory_block_index = serializer.heap().user_value(0);
if (!directory_pointer) { if (!directory_block_index) {
directory_pointer = serializer.heap().request_new_block_index(); directory_block_index = serializer.heap().request_new_block_index();
serializer.heap().set_user_value(0, directory_pointer); serializer.heap().set_user_value(0, directory_block_index);
} }
auto hash_index = SQL::HashIndex::construct(serializer, tuple_descriptor, directory_pointer); auto hash_index = SQL::HashIndex::construct(serializer, tuple_descriptor, directory_block_index);
return hash_index; return hash_index;
} }
@ -149,7 +149,7 @@ void insert_and_get_to_and_from_hash_index(int num_keys)
SQL::Key k(hash_index->descriptor()); SQL::Key k(hash_index->descriptor());
k[0] = keys[ix]; k[0] = keys[ix];
k[1] = DeprecatedString::formatted("The key value is {} and the pointer is {}", keys[ix], pointers[ix]); k[1] = DeprecatedString::formatted("The key value is {} and the pointer is {}", keys[ix], pointers[ix]);
k.set_pointer(pointers[ix]); k.set_block_index(pointers[ix]);
hash_index->insert(k); hash_index->insert(k);
} }
#ifdef LIST_HASH_INDEX #ifdef LIST_HASH_INDEX
@ -247,7 +247,7 @@ void insert_into_and_scan_hash_index(int num_keys)
SQL::Key k(hash_index->descriptor()); SQL::Key k(hash_index->descriptor());
k[0] = keys[ix]; k[0] = keys[ix];
k[1] = DeprecatedString::formatted("The key value is {} and the pointer is {}", keys[ix], pointers[ix]); k[1] = DeprecatedString::formatted("The key value is {} and the pointer is {}", keys[ix], pointers[ix]);
k.set_pointer(pointers[ix]); k.set_block_index(pointers[ix]);
hash_index->insert(k); hash_index->insert(k);
} }
#ifdef LIST_HASH_INDEX #ifdef LIST_HASH_INDEX
@ -273,7 +273,7 @@ void insert_into_and_scan_hash_index(int num_keys)
for (auto ix = 0; ix < num_keys; ix++) { for (auto ix = 0; ix < num_keys; ix++) {
if (keys[ix] == key_value) { if (keys[ix] == key_value) {
EXPECT_EQ(key.pointer(), pointers[ix]); EXPECT_EQ(key.block_index(), pointers[ix]);
if (found[ix]) if (found[ix])
FAIL(DeprecatedString::formatted("Key {}, index {} already found previously", *key_value, ix)); FAIL(DeprecatedString::formatted("Key {}, index {} already found previously", *key_value, ix));
found[ix] = true; found[ix] = true;

View file

@ -9,14 +9,14 @@
namespace SQL { namespace SQL {
BTree::BTree(Serializer& serializer, NonnullRefPtr<TupleDescriptor> const& descriptor, bool unique, u32 pointer) BTree::BTree(Serializer& serializer, NonnullRefPtr<TupleDescriptor> const& descriptor, bool unique, Block::Index block_index)
: Index(serializer, descriptor, unique, pointer) : Index(serializer, descriptor, unique, block_index)
, m_root(nullptr) , m_root(nullptr)
{ {
} }
BTree::BTree(Serializer& serializer, NonnullRefPtr<TupleDescriptor> const& descriptor, u32 pointer) BTree::BTree(Serializer& serializer, NonnullRefPtr<TupleDescriptor> const& descriptor, Block::Index block_index)
: BTree(serializer, descriptor, true, pointer) : BTree(serializer, descriptor, true, block_index)
{ {
} }
@ -35,16 +35,16 @@ BTreeIterator BTree::end()
void BTree::initialize_root() void BTree::initialize_root()
{ {
if (pointer()) { if (block_index()) {
if (serializer().has_block(pointer())) { if (serializer().has_block(block_index())) {
serializer().read_storage(pointer()); serializer().read_storage(block_index());
m_root = serializer().make_and_deserialize<TreeNode>(*this, pointer()); m_root = serializer().make_and_deserialize<TreeNode>(*this, block_index());
} else { } else {
m_root = make<TreeNode>(*this, nullptr, pointer()); m_root = make<TreeNode>(*this, nullptr, block_index());
} }
} else { } else {
set_pointer(request_new_block_index()); set_block_index(request_new_block_index());
m_root = make<TreeNode>(*this, nullptr, pointer()); m_root = make<TreeNode>(*this, nullptr, block_index());
if (on_new_root) if (on_new_root)
on_new_root(); on_new_root();
} }
@ -53,8 +53,8 @@ void BTree::initialize_root()
TreeNode* BTree::new_root() TreeNode* BTree::new_root()
{ {
set_pointer(request_new_block_index()); set_block_index(request_new_block_index());
m_root = make<TreeNode>(*this, nullptr, m_root.leak_ptr(), pointer()); m_root = make<TreeNode>(*this, nullptr, m_root.leak_ptr(), block_index());
serializer().serialize_and_write(*m_root.ptr()); serializer().serialize_and_write(*m_root.ptr());
if (on_new_root) if (on_new_root)
on_new_root(); on_new_root();

View file

@ -32,28 +32,28 @@ namespace SQL {
*/ */
class DownPointer { class DownPointer {
public: public:
explicit DownPointer(TreeNode*, u32 = 0); explicit DownPointer(TreeNode*, Block::Index = 0);
DownPointer(TreeNode*, TreeNode*); DownPointer(TreeNode*, TreeNode*);
DownPointer(DownPointer&&); DownPointer(DownPointer&&);
DownPointer(TreeNode*, DownPointer&); DownPointer(TreeNode*, DownPointer&);
~DownPointer() = default; ~DownPointer() = default;
[[nodiscard]] u32 pointer() const { return m_pointer; } [[nodiscard]] Block::Index block_index() const { return m_block_index; }
TreeNode* node(); TreeNode* node();
private: private:
void deserialize(Serializer&); void deserialize(Serializer&);
TreeNode* m_owner; TreeNode* m_owner;
u32 m_pointer { 0 }; Block::Index m_block_index { 0 };
OwnPtr<TreeNode> m_node { nullptr }; OwnPtr<TreeNode> m_node { nullptr };
friend TreeNode; friend TreeNode;
}; };
class TreeNode : public IndexNode { class TreeNode : public IndexNode {
public: public:
TreeNode(BTree&, u32 = 0); TreeNode(BTree&, Block::Index = 0);
TreeNode(BTree&, TreeNode*, u32 = 0); TreeNode(BTree&, TreeNode*, Block::Index = 0);
TreeNode(BTree&, TreeNode*, TreeNode*, u32 = 0); TreeNode(BTree&, TreeNode*, TreeNode*, Block::Index = 0);
~TreeNode() override = default; ~TreeNode() override = default;
[[nodiscard]] BTree& tree() const { return m_tree; } [[nodiscard]] BTree& tree() const { return m_tree; }
@ -61,7 +61,7 @@ public:
[[nodiscard]] size_t size() const { return m_entries.size(); } [[nodiscard]] size_t size() const { return m_entries.size(); }
[[nodiscard]] size_t length() const; [[nodiscard]] size_t length() const;
[[nodiscard]] Vector<Key> entries() const { return m_entries; } [[nodiscard]] Vector<Key> entries() const { return m_entries; }
[[nodiscard]] u32 down_pointer(size_t) const; [[nodiscard]] Block::Index down_pointer(size_t) const;
[[nodiscard]] TreeNode* down_node(size_t); [[nodiscard]] TreeNode* down_node(size_t);
[[nodiscard]] bool is_leaf() const { return m_is_leaf; } [[nodiscard]] bool is_leaf() const { return m_is_leaf; }
@ -97,7 +97,7 @@ class BTree : public Index {
public: public:
~BTree() override = default; ~BTree() override = default;
u32 root() const { return (m_root) ? m_root->pointer() : 0; } Block::Index root() const { return m_root ? m_root->block_index() : 0; }
bool insert(Key const&); bool insert(Key const&);
bool update_key_pointer(Key const&); bool update_key_pointer(Key const&);
Optional<u32> get(Key&); Optional<u32> get(Key&);
@ -109,8 +109,8 @@ public:
Function<void(void)> on_new_root; Function<void(void)> on_new_root;
private: private:
BTree(Serializer&, NonnullRefPtr<TupleDescriptor> const&, bool unique, u32 pointer); BTree(Serializer&, NonnullRefPtr<TupleDescriptor> const&, bool unique, Block::Index);
BTree(Serializer&, NonnullRefPtr<TupleDescriptor> const&, u32 pointer); BTree(Serializer&, NonnullRefPtr<TupleDescriptor> const&, Block::Index);
void initialize_root(); void initialize_root();
TreeNode* new_root(); TreeNode* new_root();
OwnPtr<TreeNode> m_root { nullptr }; OwnPtr<TreeNode> m_root { nullptr };

View file

@ -107,7 +107,7 @@ BTreeIterator BTreeIterator::next() const
for (size_t i = 0; i < up->size(); i++) { for (size_t i = 0; i < up->size(); i++) {
// One level up, try to find the entry with the current // One level up, try to find the entry with the current
// node's pointer as the left pointer: // node's pointer as the left pointer:
if (up->down_pointer(i) == node->pointer()) if (up->down_pointer(i) == node->block_index())
// Found it. This is the iterator's next value: // Found it. This is the iterator's next value:
return BTreeIterator(up, (int)i); return BTreeIterator(up, (int)i);
} }
@ -182,7 +182,7 @@ BTreeIterator BTreeIterator::previous() const
for (size_t i = up->size(); i > 0; i--) { for (size_t i = up->size(); i > 0; i--) {
// One level up, try to find the entry with the current // One level up, try to find the entry with the current
// node's pointer as the right pointer: // node's pointer as the right pointer:
if (up->down_pointer(i) == node->pointer()) { if (up->down_pointer(i) == node->block_index()) {
// Found it. This is the iterator's next value: // Found it. This is the iterator's next value:
node = up; node = up;
ix = (int)i - 1; ix = (int)i - 1;
@ -218,7 +218,7 @@ bool BTreeIterator::update(Key const& new_value)
{ {
if (is_end()) if (is_end())
return false; return false;
if ((cmp(new_value) == 0) && (key().pointer() == new_value.pointer())) if ((cmp(new_value) == 0) && (key().block_index() == new_value.block_index()))
return true; return true;
auto previous_iter = previous(); auto previous_iter = previous();
auto next_iter = next(); auto next_iter = next();

View file

@ -158,7 +158,7 @@ ResultOr<NonnullRefPtr<TableDef>> Database::get_table(DeprecatedString const& sc
auto schema_def = TRY(get_schema(schema)); auto schema_def = TRY(get_schema(schema));
auto table_def = TableDef::construct(schema_def, name); auto table_def = TableDef::construct(schema_def, name);
table_def->set_pointer((*table_iterator).pointer()); table_def->set_block_index((*table_iterator).block_index());
m_table_cache.set(key.hash(), table_def); m_table_cache.set(key.hash(), table_def);
auto table_hash = table_def->hash(); auto table_hash = table_def->hash();
@ -173,8 +173,8 @@ ErrorOr<Vector<Row>> Database::select_all(TableDef& table)
{ {
VERIFY(m_table_cache.get(table.key().hash()).has_value()); VERIFY(m_table_cache.get(table.key().hash()).has_value());
Vector<Row> ret; Vector<Row> ret;
for (auto pointer = table.pointer(); pointer; pointer = ret.last().next_pointer()) for (auto block_index = table.block_index(); block_index; block_index = ret.last().next_block_index())
ret.append(m_serializer.deserialize_block<Row>(pointer, table, pointer)); ret.append(m_serializer.deserialize_block<Row>(block_index, table, block_index));
return ret; return ret;
} }
@ -185,11 +185,11 @@ ErrorOr<Vector<Row>> Database::match(TableDef& table, Key const& key)
// TODO Match key against indexes defined on table. If found, // TODO Match key against indexes defined on table. If found,
// use the index instead of scanning the table. // use the index instead of scanning the table.
for (auto pointer = table.pointer(); pointer;) { for (auto block_index = table.block_index(); block_index;) {
auto row = m_serializer.deserialize_block<Row>(pointer, table, pointer); auto row = m_serializer.deserialize_block<Row>(block_index, table, block_index);
if (row.match(key)) if (row.match(key))
ret.append(row); ret.append(row);
pointer = ret.last().next_pointer(); block_index = ret.last().next_block_index();
} }
return ret; return ret;
} }
@ -199,16 +199,16 @@ ErrorOr<void> Database::insert(Row& row)
VERIFY(m_table_cache.get(row.table().key().hash()).has_value()); VERIFY(m_table_cache.get(row.table().key().hash()).has_value());
// TODO: implement table constraints such as unique, foreign key, etc. // TODO: implement table constraints such as unique, foreign key, etc.
row.set_pointer(m_heap->request_new_block_index()); row.set_block_index(m_heap->request_new_block_index());
row.set_next_pointer(row.table().pointer()); row.set_next_block_index(row.table().block_index());
TRY(update(row)); TRY(update(row));
// TODO update indexes defined on table. // TODO update indexes defined on table.
auto table_key = row.table().key(); auto table_key = row.table().key();
table_key.set_pointer(row.pointer()); table_key.set_block_index(row.block_index());
VERIFY(m_tables->update_key_pointer(table_key)); VERIFY(m_tables->update_key_pointer(table_key));
row.table().set_pointer(row.pointer()); row.table().set_block_index(row.block_index());
return {}; return {};
} }
@ -217,25 +217,25 @@ ErrorOr<void> Database::remove(Row& row)
auto& table = row.table(); auto& table = row.table();
VERIFY(m_table_cache.get(table.key().hash()).has_value()); VERIFY(m_table_cache.get(table.key().hash()).has_value());
if (table.pointer() == row.pointer()) { if (table.block_index() == row.block_index()) {
auto table_key = table.key(); auto table_key = table.key();
table_key.set_pointer(row.next_pointer()); table_key.set_block_index(row.next_block_index());
m_tables->update_key_pointer(table_key); m_tables->update_key_pointer(table_key);
table.set_pointer(row.next_pointer()); table.set_block_index(row.next_block_index());
return {}; return {};
} }
for (auto pointer = table.pointer(); pointer;) { for (auto block_index = table.block_index(); block_index;) {
auto current = m_serializer.deserialize_block<Row>(pointer, table, pointer); auto current = m_serializer.deserialize_block<Row>(block_index, table, block_index);
if (current.next_pointer() == row.pointer()) { if (current.next_block_index() == row.block_index()) {
current.set_next_pointer(row.next_pointer()); current.set_next_block_index(row.next_block_index());
TRY(update(current)); TRY(update(current));
break; break;
} }
pointer = current.next_pointer(); block_index = current.next_block_index();
} }
return {}; return {};

View file

@ -66,13 +66,13 @@ void HashDirectoryNode::serialize(Serializer& serializer) const
serializer.serialize<u32>(next_node); serializer.serialize<u32>(next_node);
for (auto ix = 0u; ix < number_of_pointers(); ix++) { for (auto ix = 0u; ix < number_of_pointers(); ix++) {
auto& bucket = m_hash_index.m_buckets[m_offset + ix]; auto& bucket = m_hash_index.m_buckets[m_offset + ix];
dbgln_if(SQL_DEBUG, "Bucket index #{} pointer {} local depth {} size {}", ix, bucket->pointer(), bucket->local_depth(), bucket->size()); dbgln_if(SQL_DEBUG, "Bucket index #{} block_index {} local depth {} size {}", ix, bucket->block_index(), bucket->local_depth(), bucket->size());
serializer.serialize<u32>(bucket->pointer()); serializer.serialize<u32>(bucket->block_index());
serializer.serialize<u32>(bucket->local_depth()); serializer.serialize<u32>(bucket->local_depth());
} }
} }
HashBucket::HashBucket(HashIndex& hash_index, u32 index, u32 local_depth, u32 pointer) HashBucket::HashBucket(HashIndex& hash_index, Block::Index index, u32 local_depth, Block::Index pointer)
: IndexNode(pointer) : IndexNode(pointer)
, m_hash_index(hash_index) , m_hash_index(hash_index)
, m_local_depth(local_depth) , m_local_depth(local_depth)
@ -82,8 +82,8 @@ HashBucket::HashBucket(HashIndex& hash_index, u32 index, u32 local_depth, u32 po
void HashBucket::serialize(Serializer& serializer) const void HashBucket::serialize(Serializer& serializer) const
{ {
dbgln_if(SQL_DEBUG, "Serializing bucket: pointer {}, index #{}, local depth {} size {}", dbgln_if(SQL_DEBUG, "Serializing bucket: block_index {}, index #{}, local depth {} size {}",
pointer(), index(), local_depth(), size()); block_index(), index(), local_depth(), size());
serializer.serialize<u32>(local_depth()); serializer.serialize<u32>(local_depth());
serializer.serialize<u32>(size()); serializer.serialize<u32>(size());
for (auto& key : m_entries) for (auto& key : m_entries)
@ -92,9 +92,9 @@ void HashBucket::serialize(Serializer& serializer) const
void HashBucket::deserialize(Serializer& serializer) void HashBucket::deserialize(Serializer& serializer)
{ {
if (m_inflated || !pointer()) if (m_inflated || !block_index())
return; return;
dbgln_if(SQL_DEBUG, "Inflating Hash Bucket {}", pointer()); dbgln_if(SQL_DEBUG, "Inflating Hash Bucket {}", block_index());
m_local_depth = serializer.deserialize<u32>(); m_local_depth = serializer.deserialize<u32>();
dbgln_if(SQL_DEBUG, "Bucket Local Depth {}", m_local_depth); dbgln_if(SQL_DEBUG, "Bucket Local Depth {}", m_local_depth);
auto size = serializer.deserialize<u32>(); auto size = serializer.deserialize<u32>();
@ -120,8 +120,8 @@ Optional<u32> HashBucket::get(Key& key)
auto optional_index = find_key_in_bucket(key); auto optional_index = find_key_in_bucket(key);
if (optional_index.has_value()) { if (optional_index.has_value()) {
auto& k = m_entries[optional_index.value()]; auto& k = m_entries[optional_index.value()];
key.set_pointer(k.pointer()); key.set_block_index(k.block_index());
return k.pointer(); return k.block_index();
} }
return {}; return {};
} }
@ -129,7 +129,7 @@ Optional<u32> HashBucket::get(Key& key)
bool HashBucket::insert(Key const& key) bool HashBucket::insert(Key const& key)
{ {
if (!m_inflated) if (!m_inflated)
m_hash_index.serializer().deserialize_block_to(pointer(), *this); m_hash_index.serializer().deserialize_block_to(block_index(), *this);
if (find_key_in_bucket(key).has_value()) if (find_key_in_bucket(key).has_value())
return false; return false;
if (length() + key.length() > Block::DATA_SIZE) { if (length() + key.length() > Block::DATA_SIZE) {
@ -155,7 +155,7 @@ HashBucket const* HashBucket::next_bucket()
{ {
for (auto ix = m_index + 1; ix < m_hash_index.size(); ix++) { for (auto ix = m_index + 1; ix < m_hash_index.size(); ix++) {
auto bucket = m_hash_index.get_bucket_by_index(ix); auto bucket = m_hash_index.get_bucket_by_index(ix);
m_hash_index.serializer().deserialize_block_to<HashBucket>(bucket->pointer(), *bucket); m_hash_index.serializer().deserialize_block_to<HashBucket>(bucket->block_index(), *bucket);
if (bucket->size()) if (bucket->size())
return bucket; return bucket;
} }
@ -166,7 +166,7 @@ HashBucket const* HashBucket::previous_bucket()
{ {
for (auto ix = m_index - 1; ix > 0; ix--) { for (auto ix = m_index - 1; ix > 0; ix--) {
auto bucket = m_hash_index.get_bucket_by_index(ix); auto bucket = m_hash_index.get_bucket_by_index(ix);
if (bucket->pointer()) if (bucket->block_index() > 0)
return bucket; return bucket;
} }
return nullptr; return nullptr;
@ -175,14 +175,14 @@ HashBucket const* HashBucket::previous_bucket()
Vector<Key> const& HashBucket::entries() Vector<Key> const& HashBucket::entries()
{ {
if (!m_inflated) if (!m_inflated)
m_hash_index.serializer().deserialize_block_to(pointer(), *this); m_hash_index.serializer().deserialize_block_to(block_index(), *this);
return m_entries; return m_entries;
} }
Key const& HashBucket::operator[](size_t ix) Key const& HashBucket::operator[](size_t ix)
{ {
if (!m_inflated) if (!m_inflated)
m_hash_index.serializer().deserialize_block_to(pointer(), *this); m_hash_index.serializer().deserialize_block_to(block_index(), *this);
return m_entries[ix]; return m_entries[ix];
} }
@ -193,28 +193,26 @@ Key const& HashBucket::operator[](size_t ix) const
void HashBucket::list_bucket() void HashBucket::list_bucket()
{ {
warnln("Bucket #{} size {} local depth {} pointer {}{}", warnln("Bucket #{} size {} local depth {} block_index {}{}",
index(), size(), local_depth(), pointer(), (pointer() ? "" : " (VIRTUAL)")); index(), size(), local_depth(), block_index(), (block_index() > 0 ? "" : " (VIRTUAL)"));
for (auto& key : entries()) for (auto& key : entries())
warnln(" {} hash {}", key.to_deprecated_string(), key.hash()); warnln(" {} hash {}", key.to_deprecated_string(), key.hash());
} }
HashIndex::HashIndex(Serializer& serializer, NonnullRefPtr<TupleDescriptor> const& descriptor, u32 first_node) HashIndex::HashIndex(Serializer& serializer, NonnullRefPtr<TupleDescriptor> const& descriptor, Block::Index first_node)
: Index(serializer, descriptor, true, first_node) : Index(serializer, descriptor, true, first_node)
, m_nodes()
, m_buckets()
{ {
if (!first_node) if (first_node == 0)
set_pointer(request_new_block_index()); set_block_index(request_new_block_index());
if (serializer.has_block(first_node)) { if (serializer.has_block(first_node)) {
u32 pointer = first_node; Block::Index block_index = first_node;
do { do {
VERIFY(serializer.has_block(pointer)); VERIFY(serializer.has_block(block_index));
auto node = serializer.deserialize_block<HashDirectoryNode>(pointer, *this, pointer); auto node = serializer.deserialize_block<HashDirectoryNode>(block_index, *this, block_index);
if (node.is_last()) if (node.is_last())
break; break;
pointer = m_nodes.last(); // FIXME Ugly block_index = m_nodes.last(); // FIXME Ugly
} while (pointer); } while (block_index);
} else { } else {
auto bucket = append_bucket(0u, 1u, request_new_block_index()); auto bucket = append_bucket(0u, 1u, request_new_block_index());
bucket->m_inflated = true; bucket->m_inflated = true;
@ -231,7 +229,7 @@ HashBucket* HashIndex::get_bucket(u32 index)
{ {
VERIFY(index < m_buckets.size()); VERIFY(index < m_buckets.size());
auto divisor = size() / 2; auto divisor = size() / 2;
while (!m_buckets[index]->pointer()) { while (m_buckets[index]->block_index() == 0) {
VERIFY(divisor > 1); VERIFY(divisor > 1);
index = index % divisor; index = index % divisor;
divisor /= 2; divisor /= 2;
@ -265,8 +263,8 @@ HashBucket* HashIndex::get_bucket_for_insert(Key const& key)
auto moved = 0; auto moved = 0;
for (auto entry_index = (int)bucket->m_entries.size() - 1; entry_index >= 0; entry_index--) { for (auto entry_index = (int)bucket->m_entries.size() - 1; entry_index >= 0; entry_index--) {
if (bucket->m_entries[entry_index].hash() % size() == ix) { if (bucket->m_entries[entry_index].hash() % size() == ix) {
if (!sub_bucket->pointer()) if (!sub_bucket->block_index())
sub_bucket->set_pointer(request_new_block_index()); sub_bucket->set_block_index(request_new_block_index());
sub_bucket->insert(bucket->m_entries.take(entry_index)); sub_bucket->insert(bucket->m_entries.take(entry_index));
moved++; moved++;
} }

View file

@ -24,7 +24,7 @@ namespace SQL {
class HashBucket : public IndexNode class HashBucket : public IndexNode
, public Weakable<HashBucket> { , public Weakable<HashBucket> {
public: public:
HashBucket(HashIndex&, u32 index, u32 local_depth, u32 pointer); HashBucket(HashIndex&, Block::Index index, u32 local_depth, Block::Index pointer);
~HashBucket() override = default; ~HashBucket() override = default;
Optional<u32> get(Key&); Optional<u32> get(Key&);
bool insert(Key const&); bool insert(Key const&);
@ -35,7 +35,7 @@ public:
[[nodiscard]] u32 size() { return entries().size(); } [[nodiscard]] u32 size() { return entries().size(); }
[[nodiscard]] size_t length() const; [[nodiscard]] size_t length() const;
[[nodiscard]] u32 size() const { return m_entries.size(); } [[nodiscard]] u32 size() const { return m_entries.size(); }
[[nodiscard]] u32 index() const { return m_index; } [[nodiscard]] Block::Index index() const { return m_index; }
void serialize(Serializer&) const; void serialize(Serializer&) const;
void deserialize(Serializer&); void deserialize(Serializer&);
[[nodiscard]] HashIndex const& hash_index() const { return m_hash_index; } [[nodiscard]] HashIndex const& hash_index() const { return m_hash_index; }
@ -45,12 +45,12 @@ public:
private: private:
Optional<size_t> find_key_in_bucket(Key const&); Optional<size_t> find_key_in_bucket(Key const&);
void set_index(u32 index) { m_index = index; } void set_index(Block::Index index) { m_index = index; }
void set_local_depth(u32 depth) { m_local_depth = depth; } void set_local_depth(u32 depth) { m_local_depth = depth; }
HashIndex& m_hash_index; HashIndex& m_hash_index;
u32 m_local_depth { 1 }; u32 m_local_depth { 1 };
u32 m_index { 0 }; Block::Index m_index { 0 };
Vector<Key> m_entries; Vector<Key> m_entries;
bool m_inflated { false }; bool m_inflated { false };
@ -79,7 +79,7 @@ public:
void list_hash(); void list_hash();
private: private:
HashIndex(Serializer&, NonnullRefPtr<TupleDescriptor> const&, u32); HashIndex(Serializer&, NonnullRefPtr<TupleDescriptor> const&, Block::Index);
void expand(); void expand();
void write_directory(); void write_directory();

View file

@ -74,25 +74,25 @@ public:
bool has_block(Block::Index) const; bool has_block(Block::Index) const;
[[nodiscard]] Block::Index request_new_block_index() { return m_next_block++; } [[nodiscard]] Block::Index request_new_block_index() { return m_next_block++; }
u32 schemas_root() const { return m_schemas_root; } Block::Index schemas_root() const { return m_schemas_root; }
void set_schemas_root(u32 root) void set_schemas_root(Block::Index root)
{ {
m_schemas_root = root; m_schemas_root = root;
update_zero_block().release_value_but_fixme_should_propagate_errors(); update_zero_block().release_value_but_fixme_should_propagate_errors();
} }
u32 tables_root() const { return m_tables_root; } Block::Index tables_root() const { return m_tables_root; }
void set_tables_root(u32 root) void set_tables_root(Block::Index root)
{ {
m_tables_root = root; m_tables_root = root;
update_zero_block().release_value_but_fixme_should_propagate_errors(); update_zero_block().release_value_but_fixme_should_propagate_errors();
} }
u32 table_columns_root() const { return m_table_columns_root; } Block::Index table_columns_root() const { return m_table_columns_root; }
void set_table_columns_root(u32 root) void set_table_columns_root(Block::Index root)
{ {
m_table_columns_root = root; m_table_columns_root = root;
update_zero_block().release_value_but_fixme_should_propagate_errors(); update_zero_block().release_value_but_fixme_should_propagate_errors();
@ -130,13 +130,13 @@ private:
OwnPtr<Core::BufferedFile> m_file; OwnPtr<Core::BufferedFile> m_file;
Block::Index m_highest_block_written { 0 }; Block::Index m_highest_block_written { 0 };
u32 m_next_block { 1 }; Block::Index m_next_block { 1 };
u32 m_schemas_root { 0 }; Block::Index m_schemas_root { 0 };
u32 m_tables_root { 0 }; Block::Index m_tables_root { 0 };
u32 m_table_columns_root { 0 }; Block::Index m_table_columns_root { 0 };
u32 m_version { VERSION }; u32 m_version { VERSION };
Array<u32, 16> m_user_values { 0 }; Array<u32, 16> m_user_values { 0 };
HashMap<u32, ByteBuffer> m_write_ahead_log; HashMap<Block::Index, ByteBuffer> m_write_ahead_log;
}; };
} }

View file

@ -10,18 +10,18 @@
namespace SQL { namespace SQL {
Index::Index(Serializer& serializer, NonnullRefPtr<TupleDescriptor> const& descriptor, bool unique, u32 pointer) Index::Index(Serializer& serializer, NonnullRefPtr<TupleDescriptor> const& descriptor, bool unique, Block::Index block_index)
: m_serializer(serializer) : m_serializer(serializer)
, m_descriptor(descriptor) , m_descriptor(descriptor)
, m_unique(unique) , m_unique(unique)
, m_pointer(pointer) , m_block_index(block_index)
{ {
} }
Index::Index(Serializer& serializer, NonnullRefPtr<TupleDescriptor> const& descriptor, u32 pointer) Index::Index(Serializer& serializer, NonnullRefPtr<TupleDescriptor> const& descriptor, Block::Index block_index)
: m_serializer(serializer) : m_serializer(serializer)
, m_descriptor(descriptor) , m_descriptor(descriptor)
, m_pointer(pointer) , m_block_index(block_index)
{ {
} }

View file

@ -16,19 +16,19 @@ namespace SQL {
class IndexNode { class IndexNode {
public: public:
virtual ~IndexNode() = default; virtual ~IndexNode() = default;
[[nodiscard]] u32 pointer() const { return m_pointer; } [[nodiscard]] Block::Index block_index() const { return m_block_index; }
IndexNode* as_index_node() { return dynamic_cast<IndexNode*>(this); } IndexNode* as_index_node() { return dynamic_cast<IndexNode*>(this); }
protected: protected:
explicit IndexNode(u32 pointer) explicit IndexNode(Block::Index block_index)
: m_pointer(pointer) : m_block_index(block_index)
{ {
} }
void set_pointer(u32 pointer) { m_pointer = pointer; } void set_block_index(Block::Index block_index) { m_block_index = block_index; }
private: private:
u32 m_pointer; Block::Index m_block_index;
}; };
class Index : public Core::Object { class Index : public Core::Object {
@ -40,21 +40,21 @@ public:
NonnullRefPtr<TupleDescriptor> descriptor() const { return m_descriptor; } NonnullRefPtr<TupleDescriptor> descriptor() const { return m_descriptor; }
[[nodiscard]] bool duplicates_allowed() const { return !m_unique; } [[nodiscard]] bool duplicates_allowed() const { return !m_unique; }
[[nodiscard]] bool unique() const { return m_unique; } [[nodiscard]] bool unique() const { return m_unique; }
[[nodiscard]] u32 pointer() const { return m_pointer; } [[nodiscard]] Block::Index block_index() const { return m_block_index; }
protected: protected:
Index(Serializer&, NonnullRefPtr<TupleDescriptor> const&, bool unique, u32 pointer); Index(Serializer&, NonnullRefPtr<TupleDescriptor> const&, bool unique, Block::Index block_index);
Index(Serializer&, NonnullRefPtr<TupleDescriptor> const&, u32 pointer); Index(Serializer&, NonnullRefPtr<TupleDescriptor> const&, Block::Index block_index);
[[nodiscard]] Serializer& serializer() { return m_serializer; } [[nodiscard]] Serializer& serializer() { return m_serializer; }
void set_pointer(u32 pointer) { m_pointer = pointer; } void set_block_index(Block::Index block_index) { m_block_index = block_index; }
u32 request_new_block_index() { return m_serializer.request_new_block_index(); } u32 request_new_block_index() { return m_serializer.request_new_block_index(); }
private: private:
Serializer m_serializer; Serializer m_serializer;
NonnullRefPtr<TupleDescriptor> m_descriptor; NonnullRefPtr<TupleDescriptor> m_descriptor;
bool m_unique { false }; bool m_unique { false };
u32 m_pointer { 0 }; Block::Index m_block_index { 0 };
}; };
} }

View file

@ -29,7 +29,7 @@ Key SchemaDef::key() const
{ {
auto key = Key(index_def()->to_tuple_descriptor()); auto key = Key(index_def()->to_tuple_descriptor());
key["schema_name"] = name(); key["schema_name"] = name();
key.set_pointer(pointer()); key.set_block_index(block_index());
return key; return key;
} }
@ -171,7 +171,7 @@ Key TableDef::key() const
auto key = Key(index_def()->to_tuple_descriptor()); auto key = Key(index_def()->to_tuple_descriptor());
key["schema_hash"] = parent_relation()->key().hash(); key["schema_hash"] = parent_relation()->key().hash();
key["table_name"] = name(); key["table_name"] = name();
key.set_pointer(pointer()); key.set_block_index(block_index());
return key; return key;
} }

View file

@ -12,6 +12,7 @@
#include <AK/Vector.h> #include <AK/Vector.h>
#include <LibCore/Object.h> #include <LibCore/Object.h>
#include <LibSQL/Forward.h> #include <LibSQL/Forward.h>
#include <LibSQL/Heap.h>
#include <LibSQL/Type.h> #include <LibSQL/Type.h>
#include <LibSQL/Value.h> #include <LibSQL/Value.h>
@ -27,29 +28,29 @@ class Relation : public Core::Object {
public: public:
u32 hash() const; u32 hash() const;
u32 pointer() const { return m_pointer; } Block::Index block_index() const { return m_block_index; }
void set_pointer(u32 pointer) { m_pointer = pointer; } void set_block_index(Block::Index block_index) { m_block_index = block_index; }
~Relation() override = default; ~Relation() override = default;
virtual Key key() const = 0; virtual Key key() const = 0;
Relation const* parent_relation() const { return dynamic_cast<Relation const*>(parent()); } Relation const* parent_relation() const { return dynamic_cast<Relation const*>(parent()); }
protected: protected:
Relation(DeprecatedString name, u32 pointer, Relation* parent = nullptr) Relation(DeprecatedString name, Block::Index block_index, Relation* parent = nullptr)
: Core::Object(parent) : Core::Object(parent)
, m_pointer(pointer) , m_block_index(block_index)
{ {
set_name(move(name)); set_name(move(name));
} }
explicit Relation(DeprecatedString name, Relation* parent = nullptr) explicit Relation(DeprecatedString name, Relation* parent = nullptr)
: Core::Object(parent) : Core::Object(parent)
, m_pointer(0) , m_block_index(0)
{ {
set_name(move(name)); set_name(move(name));
} }
private: private:
u32 m_pointer { 0 }; Block::Index m_block_index { 0 };
}; };
class SchemaDef : public Relation { class SchemaDef : public Relation {

View file

@ -9,23 +9,23 @@
namespace SQL { namespace SQL {
Row::Row(NonnullRefPtr<TableDef> table, u32 pointer) Row::Row(NonnullRefPtr<TableDef> table, Block::Index block_index)
: Tuple(table->to_tuple_descriptor()) : Tuple(table->to_tuple_descriptor())
, m_table(move(table)) , m_table(move(table))
{ {
set_pointer(pointer); set_block_index(block_index);
} }
void Row::deserialize(Serializer& serializer) void Row::deserialize(Serializer& serializer)
{ {
Tuple::deserialize(serializer); Tuple::deserialize(serializer);
m_next_pointer = serializer.deserialize<u32>(); m_next_block_index = serializer.deserialize<Block::Index>();
} }
void Row::serialize(Serializer& serializer) const void Row::serialize(Serializer& serializer) const
{ {
Tuple::serialize(serializer); Tuple::serialize(serializer);
serializer.serialize<u32>(next_pointer()); serializer.serialize<Block::Index>(next_block_index());
} }
} }

View file

@ -25,22 +25,22 @@ namespace SQL {
*/ */
class Row : public Tuple { class Row : public Tuple {
public: public:
explicit Row(NonnullRefPtr<TableDef>, u32 pointer = 0); explicit Row(NonnullRefPtr<TableDef>, Block::Index block_index = 0);
virtual ~Row() override = default; virtual ~Row() override = default;
[[nodiscard]] u32 next_pointer() const { return m_next_pointer; } [[nodiscard]] Block::Index next_block_index() const { return m_next_block_index; }
void set_next_pointer(u32 ptr) { m_next_pointer = ptr; } void set_next_block_index(Block::Index index) { m_next_block_index = index; }
TableDef const& table() const { return *m_table; } TableDef const& table() const { return *m_table; }
TableDef& table() { return *m_table; } TableDef& table() { return *m_table; }
[[nodiscard]] virtual size_t length() const override { return Tuple::length() + sizeof(u32); } [[nodiscard]] virtual size_t length() const override { return Tuple::length() + sizeof(Block::Index); }
virtual void serialize(Serializer&) const override; virtual void serialize(Serializer&) const override;
virtual void deserialize(Serializer&) override; virtual void deserialize(Serializer&) override;
private: private:
NonnullRefPtr<TableDef> m_table; NonnullRefPtr<TableDef> m_table;
u32 m_next_pointer { 0 }; Block::Index m_next_block_index { 0 };
}; };
} }

View file

@ -42,16 +42,16 @@ public:
} }
template<typename T, typename... Args> template<typename T, typename... Args>
T deserialize_block(u32 pointer, Args&&... args) T deserialize_block(Block::Index block_index, Args&&... args)
{ {
read_storage(pointer); read_storage(block_index);
return deserialize<T>(forward<Args>(args)...); return deserialize<T>(forward<Args>(args)...);
} }
template<typename T> template<typename T>
void deserialize_block_to(u32 pointer, T& t) void deserialize_block_to(Block::Index block_index, T& t)
{ {
read_storage(pointer); read_storage(block_index);
return deserialize_to<T>(t); return deserialize_to<T>(t);
} }
@ -107,7 +107,7 @@ public:
VERIFY(!m_heap.is_null()); VERIFY(!m_heap.is_null());
reset(); reset();
serialize<T>(t); serialize<T>(t);
m_heap->write_storage(t.pointer(), m_buffer).release_value_but_fixme_should_propagate_errors(); m_heap->write_storage(t.block_index(), m_buffer).release_value_but_fixme_should_propagate_errors();
return true; return true;
} }

View file

@ -12,30 +12,30 @@
namespace SQL { namespace SQL {
DownPointer::DownPointer(TreeNode* owner, u32 pointer) DownPointer::DownPointer(TreeNode* owner, Block::Index block_index)
: m_owner(owner) : m_owner(owner)
, m_pointer(pointer) , m_block_index(block_index)
, m_node(nullptr) , m_node(nullptr)
{ {
} }
DownPointer::DownPointer(TreeNode* owner, TreeNode* node) DownPointer::DownPointer(TreeNode* owner, TreeNode* node)
: m_owner(owner) : m_owner(owner)
, m_pointer((node) ? node->pointer() : 0) , m_block_index((node) ? node->block_index() : 0)
, m_node(adopt_own_if_nonnull(node)) , m_node(adopt_own_if_nonnull(node))
{ {
} }
DownPointer::DownPointer(TreeNode* owner, DownPointer& down) DownPointer::DownPointer(TreeNode* owner, DownPointer& down)
: m_owner(owner) : m_owner(owner)
, m_pointer(down.m_pointer) , m_block_index(down.m_block_index)
, m_node(move(down.m_node)) , m_node(move(down.m_node))
{ {
} }
DownPointer::DownPointer(DownPointer&& other) DownPointer::DownPointer(DownPointer&& other)
: m_owner(other.m_owner) : m_owner(other.m_owner)
, m_pointer(other.pointer()) , m_block_index(other.block_index())
, m_node(other.m_node ? move(other.m_node) : nullptr) , m_node(other.m_node ? move(other.m_node) : nullptr)
{ {
} }
@ -49,14 +49,14 @@ TreeNode* DownPointer::node()
void DownPointer::deserialize(Serializer& serializer) void DownPointer::deserialize(Serializer& serializer)
{ {
if (m_node || !m_pointer) if (m_node || !m_block_index)
return; return;
serializer.read_storage(m_pointer); serializer.read_storage(m_block_index);
m_node = serializer.make_and_deserialize<TreeNode>(m_owner->tree(), m_owner, m_pointer); m_node = serializer.make_and_deserialize<TreeNode>(m_owner->tree(), m_owner, m_block_index);
} }
TreeNode::TreeNode(BTree& tree, u32 pointer) TreeNode::TreeNode(BTree& tree, Block::Index block_index)
: IndexNode(pointer) : IndexNode(block_index)
, m_tree(tree) , m_tree(tree)
, m_up(nullptr) , m_up(nullptr)
, m_entries() , m_entries()
@ -64,8 +64,8 @@ TreeNode::TreeNode(BTree& tree, u32 pointer)
{ {
} }
TreeNode::TreeNode(BTree& tree, TreeNode* up, u32 pointer) TreeNode::TreeNode(BTree& tree, TreeNode* up, Block::Index block_index)
: IndexNode(pointer) : IndexNode(block_index)
, m_tree(tree) , m_tree(tree)
, m_up(up) , m_up(up)
, m_entries() , m_entries()
@ -75,8 +75,8 @@ TreeNode::TreeNode(BTree& tree, TreeNode* up, u32 pointer)
m_is_leaf = true; m_is_leaf = true;
} }
TreeNode::TreeNode(BTree& tree, TreeNode* up, DownPointer& left, u32 pointer) TreeNode::TreeNode(BTree& tree, TreeNode* up, DownPointer& left, Block::Index block_index)
: IndexNode(pointer) : IndexNode(block_index)
, m_tree(tree) , m_tree(tree)
, m_up(up) , m_up(up)
, m_entries() , m_entries()
@ -85,20 +85,20 @@ TreeNode::TreeNode(BTree& tree, TreeNode* up, DownPointer& left, u32 pointer)
if (left.m_node != nullptr) if (left.m_node != nullptr)
left.m_node->m_up = this; left.m_node->m_up = this;
m_down.append(DownPointer(this, left)); m_down.append(DownPointer(this, left));
m_is_leaf = left.pointer() == 0; m_is_leaf = left.block_index() == 0;
if (!pointer) if (!block_index)
set_pointer(m_tree.request_new_block_index()); set_block_index(m_tree.request_new_block_index());
} }
TreeNode::TreeNode(BTree& tree, TreeNode* up, TreeNode* left, u32 pointer) TreeNode::TreeNode(BTree& tree, TreeNode* up, TreeNode* left, Block::Index block_index)
: IndexNode(pointer) : IndexNode(block_index)
, m_tree(tree) , m_tree(tree)
, m_up(up) , m_up(up)
, m_entries() , m_entries()
, m_down() , m_down()
{ {
m_down.append(DownPointer(this, left)); m_down.append(DownPointer(this, left));
m_is_leaf = left->pointer() == 0; m_is_leaf = left->block_index() == 0;
} }
void TreeNode::deserialize(Serializer& serializer) void TreeNode::deserialize(Serializer& serializer)
@ -130,12 +130,12 @@ void TreeNode::serialize(Serializer& serializer) const
if (sz > 0) { if (sz > 0) {
for (auto ix = 0u; ix < size(); ix++) { for (auto ix = 0u; ix < size(); ix++) {
auto& entry = m_entries[ix]; auto& entry = m_entries[ix];
dbgln_if(SQL_DEBUG, "Serializing Left[{}] = {}", ix, m_down[ix].pointer()); dbgln_if(SQL_DEBUG, "Serializing Left[{}] = {}", ix, m_down[ix].block_index());
serializer.serialize<u32>(is_leaf() ? 0u : m_down[ix].pointer()); serializer.serialize<u32>(is_leaf() ? 0u : m_down[ix].block_index());
serializer.serialize<Key>(entry); serializer.serialize<Key>(entry);
} }
dbgln_if(SQL_DEBUG, "Serializing Right = {}", m_down[size()].pointer()); dbgln_if(SQL_DEBUG, "Serializing Right = {}", m_down[size()].block_index());
serializer.serialize<u32>(is_leaf() ? 0u : m_down[size()].pointer()); serializer.serialize<u32>(is_leaf() ? 0u : m_down[size()].block_index());
} }
} }
@ -151,7 +151,7 @@ size_t TreeNode::length() const
bool TreeNode::insert(Key const& key) bool TreeNode::insert(Key const& key)
{ {
dbgln_if(SQL_DEBUG, "[#{}] INSERT({})", pointer(), key.to_deprecated_string()); dbgln_if(SQL_DEBUG, "[#{}] INSERT({})", block_index(), key.to_deprecated_string());
if (!is_leaf()) if (!is_leaf())
return node_for(key)->insert_in_leaf(key); return node_for(key)->insert_in_leaf(key);
return insert_in_leaf(key); return insert_in_leaf(key);
@ -159,16 +159,16 @@ bool TreeNode::insert(Key const& key)
bool TreeNode::update_key_pointer(Key const& key) bool TreeNode::update_key_pointer(Key const& key)
{ {
dbgln_if(SQL_DEBUG, "[#{}] UPDATE({}, {})", pointer(), key.to_deprecated_string(), key.pointer()); dbgln_if(SQL_DEBUG, "[#{}] UPDATE({}, {})", block_index(), key.to_deprecated_string(), key.block_index());
if (!is_leaf()) if (!is_leaf())
return node_for(key)->update_key_pointer(key); return node_for(key)->update_key_pointer(key);
for (auto ix = 0u; ix < size(); ix++) { for (auto ix = 0u; ix < size(); ix++) {
if (key == m_entries[ix]) { if (key == m_entries[ix]) {
dbgln_if(SQL_DEBUG, "[#{}] {} == {}", dbgln_if(SQL_DEBUG, "[#{}] {} == {}",
pointer(), key.to_deprecated_string(), m_entries[ix].to_deprecated_string()); block_index(), key.to_deprecated_string(), m_entries[ix].to_deprecated_string());
if (m_entries[ix].pointer() != key.pointer()) { if (m_entries[ix].block_index() != key.block_index()) {
m_entries[ix].set_pointer(key.pointer()); m_entries[ix].set_block_index(key.block_index());
dump_if(SQL_DEBUG, "To WAL"); dump_if(SQL_DEBUG, "To WAL");
tree().serializer().serialize_and_write<TreeNode>(*this); tree().serializer().serialize_and_write<TreeNode>(*this);
} }
@ -184,20 +184,20 @@ bool TreeNode::insert_in_leaf(Key const& key)
if (!m_tree.duplicates_allowed()) { if (!m_tree.duplicates_allowed()) {
for (auto& entry : m_entries) { for (auto& entry : m_entries) {
if (key == entry) { if (key == entry) {
dbgln_if(SQL_DEBUG, "[#{}] duplicate key {}", pointer(), key.to_deprecated_string()); dbgln_if(SQL_DEBUG, "[#{}] duplicate key {}", block_index(), key.to_deprecated_string());
return false; return false;
} }
} }
} }
dbgln_if(SQL_DEBUG, "[#{}] insert_in_leaf({})", pointer(), key.to_deprecated_string()); dbgln_if(SQL_DEBUG, "[#{}] insert_in_leaf({})", block_index(), key.to_deprecated_string());
just_insert(key, nullptr); just_insert(key, nullptr);
return true; return true;
} }
u32 TreeNode::down_pointer(size_t ix) const Block::Index TreeNode::down_pointer(size_t ix) const
{ {
return m_down[ix].pointer(); return m_down[ix].block_index();
} }
TreeNode* TreeNode::down_node(size_t ix) TreeNode* TreeNode::down_node(size_t ix)
@ -213,12 +213,12 @@ TreeNode* TreeNode::node_for(Key const& key)
for (size_t ix = 0; ix < size(); ix++) { for (size_t ix = 0; ix < size(); ix++) {
if (key < m_entries[ix]) { if (key < m_entries[ix]) {
dbgln_if(SQL_DEBUG, "[{}] {} < {} v{}", dbgln_if(SQL_DEBUG, "[{}] {} < {} v{}",
pointer(), (DeprecatedString)key, (DeprecatedString)m_entries[ix], m_down[ix].pointer()); block_index(), (DeprecatedString)key, (DeprecatedString)m_entries[ix], m_down[ix].block_index());
return down_node(ix)->node_for(key); return down_node(ix)->node_for(key);
} }
} }
dbgln_if(SQL_DEBUG, "[#{}] {} >= {} v{}", dbgln_if(SQL_DEBUG, "[#{}] {} >= {} v{}",
pointer(), key.to_deprecated_string(), (DeprecatedString)m_entries[size() - 1], m_down[size()].pointer()); block_index(), key.to_deprecated_string(), (DeprecatedString)m_entries[size() - 1], m_down[size()].block_index());
return down_node(size())->node_for(key); return down_node(size())->node_for(key);
} }
@ -229,42 +229,42 @@ Optional<u32> TreeNode::get(Key& key)
if (key < m_entries[ix]) { if (key < m_entries[ix]) {
if (is_leaf()) { if (is_leaf()) {
dbgln_if(SQL_DEBUG, "[#{}] {} < {} -> 0", dbgln_if(SQL_DEBUG, "[#{}] {} < {} -> 0",
pointer(), key.to_deprecated_string(), (DeprecatedString)m_entries[ix]); block_index(), key.to_deprecated_string(), (DeprecatedString)m_entries[ix]);
return {}; return {};
} else { } else {
dbgln_if(SQL_DEBUG, "[{}] {} < {} ({} -> {})", dbgln_if(SQL_DEBUG, "[{}] {} < {} ({} -> {})",
pointer(), key.to_deprecated_string(), (DeprecatedString)m_entries[ix], block_index(), key.to_deprecated_string(), (DeprecatedString)m_entries[ix],
ix, m_down[ix].pointer()); ix, m_down[ix].block_index());
return down_node(ix)->get(key); return down_node(ix)->get(key);
} }
} }
if (key == m_entries[ix]) { if (key == m_entries[ix]) {
dbgln_if(SQL_DEBUG, "[#{}] {} == {} -> {}", dbgln_if(SQL_DEBUG, "[#{}] {} == {} -> {}",
pointer(), key.to_deprecated_string(), (DeprecatedString)m_entries[ix], block_index(), key.to_deprecated_string(), (DeprecatedString)m_entries[ix],
m_entries[ix].pointer()); m_entries[ix].block_index());
key.set_pointer(m_entries[ix].pointer()); key.set_block_index(m_entries[ix].block_index());
return m_entries[ix].pointer(); return m_entries[ix].block_index();
} }
} }
if (m_entries.is_empty()) { if (m_entries.is_empty()) {
dbgln_if(SQL_DEBUG, "[#{}] {} Empty node??", pointer(), key.to_deprecated_string()); dbgln_if(SQL_DEBUG, "[#{}] {} Empty node??", block_index(), key.to_deprecated_string());
VERIFY_NOT_REACHED(); VERIFY_NOT_REACHED();
} }
if (is_leaf()) { if (is_leaf()) {
dbgln_if(SQL_DEBUG, "[#{}] {} > {} -> 0", dbgln_if(SQL_DEBUG, "[#{}] {} > {} -> 0",
pointer(), key.to_deprecated_string(), (DeprecatedString)m_entries[size() - 1]); block_index(), key.to_deprecated_string(), (DeprecatedString)m_entries[size() - 1]);
return {}; return {};
} }
dbgln_if(SQL_DEBUG, "[#{}] {} > {} ({} -> {})", dbgln_if(SQL_DEBUG, "[#{}] {} > {} ({} -> {})",
pointer(), key.to_deprecated_string(), (DeprecatedString)m_entries[size() - 1], block_index(), key.to_deprecated_string(), (DeprecatedString)m_entries[size() - 1],
size(), m_down[size()].pointer()); size(), m_down[size()].block_index());
return down_node(size())->get(key); return down_node(size())->get(key);
} }
void TreeNode::just_insert(Key const& key, TreeNode* right) void TreeNode::just_insert(Key const& key, TreeNode* right)
{ {
dbgln_if(SQL_DEBUG, "[#{}] just_insert({}, right = {})", dbgln_if(SQL_DEBUG, "[#{}] just_insert({}, right = {})",
pointer(), (DeprecatedString)key, (right) ? right->pointer() : 0); block_index(), (DeprecatedString)key, (right) ? right->block_index() : 0);
dump_if(SQL_DEBUG, "Before"); dump_if(SQL_DEBUG, "Before");
for (auto ix = 0u; ix < size(); ix++) { for (auto ix = 0u; ix < size(); ix++) {
if (key < m_entries[ix]) { if (key < m_entries[ix]) {
@ -336,25 +336,25 @@ void TreeNode::dump_if(int flag, DeprecatedString&& msg)
if (!flag) if (!flag)
return; return;
StringBuilder builder; StringBuilder builder;
builder.appendff("[#{}] ", pointer()); builder.appendff("[#{}] ", block_index());
if (!msg.is_empty()) if (!msg.is_empty())
builder.appendff("{}", msg); builder.appendff("{}", msg);
builder.append(": "sv); builder.append(": "sv);
if (m_up) if (m_up)
builder.appendff("[^{}] -> ", m_up->pointer()); builder.appendff("[^{}] -> ", m_up->block_index());
else else
builder.append("* -> "sv); builder.append("* -> "sv);
for (size_t ix = 0; ix < m_entries.size(); ix++) { for (size_t ix = 0; ix < m_entries.size(); ix++) {
if (!is_leaf()) if (!is_leaf())
builder.appendff("[v{}] ", m_down[ix].pointer()); builder.appendff("[v{}] ", m_down[ix].block_index());
else else
VERIFY(m_down[ix].pointer() == 0); VERIFY(m_down[ix].block_index() == 0);
builder.appendff("'{}' ", (DeprecatedString)m_entries[ix]); builder.appendff("'{}' ", (DeprecatedString)m_entries[ix]);
} }
if (!is_leaf()) if (!is_leaf())
builder.appendff("[v{}]", m_down[size()].pointer()); builder.appendff("[v{}]", m_down[size()].block_index());
else else
VERIFY(m_down[size()].pointer() == 0); VERIFY(m_down[size()].block_index() == 0);
builder.appendff(" (size {}", (int)size()); builder.appendff(" (size {}", (int)size());
if (is_leaf()) if (is_leaf())
builder.append(", leaf"sv); builder.append(", leaf"sv);
@ -369,7 +369,7 @@ void TreeNode::list_node(int indent)
warn(" "); warn(" ");
}; };
do_indent(); do_indent();
warnln("--> #{}", pointer()); warnln("--> #{}", block_index());
for (auto ix = 0u; ix < size(); ix++) { for (auto ix = 0u; ix < size(); ix++) {
if (!is_leaf()) if (!is_leaf())
down_node(ix)->list_node(indent + 2); down_node(ix)->list_node(indent + 2);

View file

@ -19,10 +19,10 @@ Tuple::Tuple()
{ {
} }
Tuple::Tuple(NonnullRefPtr<TupleDescriptor> const& descriptor, u32 pointer) Tuple::Tuple(NonnullRefPtr<TupleDescriptor> const& descriptor, Block::Index block_index)
: m_descriptor(descriptor) : m_descriptor(descriptor)
, m_data() , m_data()
, m_pointer(pointer) , m_block_index(block_index)
{ {
for (auto& element : *descriptor) for (auto& element : *descriptor)
m_data.empend(element.type); m_data.empend(element.type);
@ -37,8 +37,8 @@ Tuple::Tuple(NonnullRefPtr<TupleDescriptor> const& descriptor, Serializer& seria
void Tuple::deserialize(Serializer& serializer) void Tuple::deserialize(Serializer& serializer)
{ {
dbgln_if(SQL_DEBUG, "deserialize tuple at offset {}", serializer.offset()); dbgln_if(SQL_DEBUG, "deserialize tuple at offset {}", serializer.offset());
serializer.deserialize_to<u32>(m_pointer); serializer.deserialize_to<u32>(m_block_index);
dbgln_if(SQL_DEBUG, "pointer: {}", m_pointer); dbgln_if(SQL_DEBUG, "block_index: {}", m_block_index);
auto number_of_elements = serializer.deserialize<u32>(); auto number_of_elements = serializer.deserialize<u32>();
m_data.clear(); m_data.clear();
m_descriptor->clear(); m_descriptor->clear();
@ -51,8 +51,8 @@ void Tuple::deserialize(Serializer& serializer)
void Tuple::serialize(Serializer& serializer) const void Tuple::serialize(Serializer& serializer) const
{ {
VERIFY(m_descriptor->size() == m_data.size()); VERIFY(m_descriptor->size() == m_data.size());
dbgln_if(SQL_DEBUG, "Serializing tuple pointer {}", pointer()); dbgln_if(SQL_DEBUG, "Serializing tuple with block_index {}", block_index());
serializer.serialize<u32>(pointer()); serializer.serialize<u32>(block_index());
serializer.serialize<u32>(m_descriptor->size()); serializer.serialize<u32>(m_descriptor->size());
for (auto ix = 0u; ix < m_descriptor->size(); ix++) { for (auto ix = 0u; ix < m_descriptor->size(); ix++) {
serializer.serialize<TupleElementDescriptor>((*m_descriptor)[ix]); serializer.serialize<TupleElementDescriptor>((*m_descriptor)[ix]);
@ -140,8 +140,8 @@ DeprecatedString Tuple::to_deprecated_string() const
builder.append('|'); builder.append('|');
builder.append(part.to_deprecated_string()); builder.append(part.to_deprecated_string());
} }
if (pointer() != 0) if (block_index() != 0)
builder.appendff(":{}", pointer()); builder.appendff(":{}", block_index());
return builder.to_deprecated_string(); return builder.to_deprecated_string();
} }
@ -155,7 +155,7 @@ void Tuple::copy_from(Tuple const& other)
m_data.clear(); m_data.clear();
for (auto& part : other.m_data) for (auto& part : other.m_data)
m_data.append(part); m_data.append(part);
m_pointer = other.pointer(); m_block_index = other.block_index();
} }
int Tuple::compare(Tuple const& other) const int Tuple::compare(Tuple const& other) const

View file

@ -27,7 +27,7 @@ namespace SQL {
class Tuple { class Tuple {
public: public:
Tuple(); Tuple();
explicit Tuple(NonnullRefPtr<TupleDescriptor> const&, u32 pointer = 0); explicit Tuple(NonnullRefPtr<TupleDescriptor> const&, Block::Index = 0);
Tuple(NonnullRefPtr<TupleDescriptor> const&, Serializer&); Tuple(NonnullRefPtr<TupleDescriptor> const&, Serializer&);
Tuple(Tuple const&); Tuple(Tuple const&);
virtual ~Tuple() = default; virtual ~Tuple() = default;
@ -55,8 +55,8 @@ public:
Tuple& operator+=(Value const&); Tuple& operator+=(Value const&);
void extend(Tuple const&); void extend(Tuple const&);
[[nodiscard]] u32 pointer() const { return m_pointer; } [[nodiscard]] Block::Index block_index() const { return m_block_index; }
void set_pointer(u32 ptr) { m_pointer = ptr; } void set_block_index(Block::Index index) { m_block_index = index; }
[[nodiscard]] size_t size() const { return m_data.size(); } [[nodiscard]] size_t size() const { return m_data.size(); }
[[nodiscard]] virtual size_t length() const; [[nodiscard]] virtual size_t length() const;
@ -77,7 +77,7 @@ protected:
private: private:
NonnullRefPtr<TupleDescriptor> m_descriptor; NonnullRefPtr<TupleDescriptor> m_descriptor;
Vector<Value> m_data; Vector<Value> m_data;
u32 m_pointer { 2 * sizeof(u32) }; Block::Index m_block_index { 0 };
friend Serializer; friend Serializer;
}; };