Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Refactor table condition handling. #472

Merged
merged 4 commits into from
May 14, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 5 additions & 1 deletion include/bitcoin/database/file/utilities.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ constexpr auto invalid = -1;
using path = std::filesystem::path;

/// True only if directory existed.
BCD_API bool is_directory(const path& filename) NOEXCEPT;
BCD_API bool is_directory(const path& directory) NOEXCEPT;

/// Clear and recreate directory, true if path existed/created.
BCD_API bool clear_directory(const path& directory) NOEXCEPT;
Expand Down Expand Up @@ -70,8 +70,12 @@ BCD_API bool size(size_t& out, int file_descriptor) NOEXCEPT;
/// File size from name.
BCD_API bool size(size_t& out, const path& filename) NOEXCEPT;

/// Volume space from path.
BCD_API bool space(size_t& out, const path& filename) NOEXCEPT;

/// System page size.
BCD_API size_t page() NOEXCEPT;

} // namespace file
} // namespace database
} // namespace libbitcoin
Expand Down
14 changes: 10 additions & 4 deletions include/bitcoin/database/impl/primitives/arraymap.ipp
Original file line number Diff line number Diff line change
Expand Up @@ -107,15 +107,21 @@ bool CLASS::truncate(const Link& count) NOEXCEPT
// ----------------------------------------------------------------------------

TEMPLATE
code CLASS::get_error() const NOEXCEPT
code CLASS::get_fault() const NOEXCEPT
{
return manager_.get_error();
return manager_.get_fault();
}

TEMPLATE
void CLASS::clear_error() NOEXCEPT
bool CLASS::is_full() const NOEXCEPT
{
manager_.clear_error();
manager_.is_full();
}

TEMPLATE
void CLASS::reset_full() NOEXCEPT
{
manager_.reset_full();
}

// query interface
Expand Down
14 changes: 10 additions & 4 deletions include/bitcoin/database/impl/primitives/hashmap.ipp
Original file line number Diff line number Diff line change
Expand Up @@ -107,15 +107,21 @@ Link CLASS::count() const NOEXCEPT
// ----------------------------------------------------------------------------

TEMPLATE
code CLASS::get_error() const NOEXCEPT
code CLASS::get_fault() const NOEXCEPT
{
return manager_.get_error();
return manager_.get_fault();
}

TEMPLATE
void CLASS::clear_error() NOEXCEPT
bool CLASS::is_full() const NOEXCEPT
{
manager_.clear_error();
manager_.is_full();
}

TEMPLATE
void CLASS::reset_full() NOEXCEPT
{
manager_.reset_full();
}

// query interface
Expand Down
14 changes: 10 additions & 4 deletions include/bitcoin/database/impl/primitives/manager.ipp
Original file line number Diff line number Diff line change
Expand Up @@ -90,15 +90,21 @@ memory_ptr CLASS::get(const Link& value) const NOEXCEPT
// ----------------------------------------------------------------------------

TEMPLATE
code CLASS::get_error() const NOEXCEPT
code CLASS::get_fault() const NOEXCEPT
{
return file_.get_error();
return file_.get_fault();
}

TEMPLATE
void CLASS::clear_error() NOEXCEPT
bool CLASS::is_full() const NOEXCEPT
{
file_.clear_error();
file_.is_full();
}

TEMPLATE
void CLASS::reset_full() NOEXCEPT
{
file_.reset_full();
}

// private
Expand Down
26 changes: 19 additions & 7 deletions include/bitcoin/database/impl/query/query.ipp
Original file line number Diff line number Diff line change
Expand Up @@ -75,26 +75,38 @@ CLASS::query(Store& value) NOEXCEPT
}

TEMPLATE
bool CLASS::is_full() const NOEXCEPT
code CLASS::get_code() const NOEXCEPT
{
auto ec = store_.get_fault();
return !ec && is_full() ? error::disk_full : error::success;
}

TEMPLATE
code CLASS::get_fault() const NOEXCEPT
{
return store_.is_error(error::disk_full);
return store_.get_fault();
}

TEMPLATE
bool CLASS::is_fault() const NOEXCEPT
{
return !!store_.get_fault();
return !!get_fault();
}

TEMPLATE
code CLASS::get_code() const NOEXCEPT
bool CLASS::is_full() const NOEXCEPT
{
return store_.is_full();
}

TEMPLATE
void CLASS::reset_full() NOEXCEPT
{
return is_full() ? error::disk_full : store_.get_fault();
return store_.reset_full();
}

TEMPLATE
code CLASS::snapshot(
const typename Store::event_handler& handler) const NOEXCEPT
code CLASS::snapshot(const typename Store::event_handler& handler) const NOEXCEPT
{
return store_.snapshot(handler);
}
Expand Down
130 changes: 57 additions & 73 deletions include/bitcoin/database/impl/store.ipp
Original file line number Diff line number Diff line change
Expand Up @@ -975,95 +975,79 @@ const typename CLASS::transactor CLASS::get_transactor() NOEXCEPT
TEMPLATE
code CLASS::get_fault() const NOEXCEPT
{
const auto fault = [](const auto& storage) NOEXCEPT
{
const auto ec = storage.get_error();
return ec == error::disk_full ? error::success : ec;
};

code ec{};
if ((ec = fault(header_body_))) return ec;
if ((ec = fault(input_body_))) return ec;
if ((ec = fault(output_body_))) return ec;
if ((ec = fault(point_body_))) return ec;
if ((ec = fault(puts_body_))) return ec;
if ((ec = fault(spend_body_))) return ec;
if ((ec = fault(tx_body_))) return ec;
if ((ec = fault(txs_body_))) return ec;
if ((ec = fault(candidate_body_))) return ec;
if ((ec = fault(confirmed_body_))) return ec;
if ((ec = fault(strong_tx_body_))) return ec;
if ((ec = fault(validated_bk_body_))) return ec;
if ((ec = fault(validated_tx_body_))) return ec;
if ((ec = fault(address_body_))) return ec;
if ((ec = fault(neutrino_body_))) return ec;
////if ((ec = fault(bootstrap_body_))) return ec;
////if ((ec = fault(buffer_body_))) return ec;
if ((ec = header_body_.get_fault())) return ec;
if ((ec = input_body_.get_fault())) return ec;
if ((ec = output_body_.get_fault())) return ec;
if ((ec = point_body_.get_fault())) return ec;
if ((ec = puts_body_.get_fault())) return ec;
if ((ec = spend_body_.get_fault())) return ec;
if ((ec = tx_body_.get_fault())) return ec;
if ((ec = txs_body_.get_fault())) return ec;
if ((ec = candidate_body_.get_fault())) return ec;
if ((ec = confirmed_body_.get_fault())) return ec;
if ((ec = strong_tx_body_.get_fault())) return ec;
if ((ec = validated_bk_body_.get_fault())) return ec;
if ((ec = validated_tx_body_.get_fault())) return ec;
if ((ec = address_body_.get_fault())) return ec;
if ((ec = neutrino_body_.get_fault())) return ec;
////if ((ec = bootstrap_body_.get_fault())) return ec;
////if ((ec = buffer_body_.get_fault())) return ec;
return ec;
}

TEMPLATE
bool CLASS::is_error(const code& ec) const NOEXCEPT
bool CLASS::is_full() const NOEXCEPT
{
// A disk full error will not leave a flush lock, but others will.
// There may be other error codes as well so check all.

bool found{};
const auto match = [&ec, &found](const auto& storage) NOEXCEPT
{
const auto error = storage.get_error();
if (error == ec) found = true;
return !error || found;
};

return match(header_body_)
&& match(input_body_)
&& match(output_body_)
&& match(point_body_)
&& match(puts_body_)
&& match(spend_body_)
&& match(tx_body_)
&& match(txs_body_)
&& match(candidate_body_)
&& match(confirmed_body_)
&& match(strong_tx_body_)
&& match(validated_bk_body_)
&& match(validated_tx_body_)
&& match(address_body_)
&& match(neutrino_body_)
////&& match(bootstrap_body_)
////&& match(buffer_body_)
&& found;
return header_body_.is_full()
|| input_body_.is_full()
|| output_body_.is_full()
|| point_body_.is_full()
|| puts_body_.is_full()
|| spend_body_.is_full()
|| tx_body_.is_full()
|| txs_body_.is_full()
|| candidate_body_.is_full()
|| confirmed_body_.is_full()
|| strong_tx_body_.is_full()
|| validated_bk_body_.is_full()
|| validated_tx_body_.is_full()
|| address_body_.is_full()
|| neutrino_body_.is_full();
////|| bootstrap_body_.is_full()
////|| buffer_body_.is_full();
}

TEMPLATE
void CLASS::clear_errors() NOEXCEPT
void CLASS::reset_full() NOEXCEPT
{
header_body_.clear_error();
input_body_.clear_error();
output_body_.clear_error();
point_body_.clear_error();
puts_body_.clear_error();
spend_body_.clear_error();
tx_body_.clear_error();
txs_body_.clear_error();
candidate_body_.clear_error();
confirmed_body_.clear_error();
strong_tx_body_.clear_error();
validated_bk_body_.clear_error();
validated_tx_body_.clear_error();
address_body_.clear_error();
neutrino_body_.clear_error();
////bootstrap_body_.clear_error();
////buffer_body_.clear_error();
header_body_.reset_full();
input_body_.reset_full();
output_body_.reset_full();
point_body_.reset_full();
puts_body_.reset_full();
spend_body_.reset_full();
tx_body_.reset_full();
txs_body_.reset_full();
candidate_body_.reset_full();
confirmed_body_.reset_full();
strong_tx_body_.reset_full();
validated_bk_body_.reset_full();
validated_tx_body_.reset_full();
address_body_.reset_full();
neutrino_body_.reset_full();
////bootstrap_body_.reset_full();
////buffer_body_.reset_full();
}

TEMPLATE
void CLASS::report_errors(const error_handler& handler) const NOEXCEPT
void CLASS::report_condition(const error_handler& handler) const NOEXCEPT
{
const auto report = [&handler](const auto& storage, table_t table) NOEXCEPT
{
handler(storage.get_error(), table);
auto ec = storage.get_fault();
if (!ec && storage.is_full()) ec = error::disk_full;
handler(ec, table);
};

report(header_body_, table_t::header_body);
Expand Down
11 changes: 7 additions & 4 deletions include/bitcoin/database/memory/interfaces/storage.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -67,11 +67,14 @@ class storage
/// Get r/w access to start/offset of memory map (or null).
virtual memory_ptr get(size_t offset=zero) const NOEXCEPT = 0;

/// Get the current error condition.
virtual code get_error() const NOEXCEPT = 0;
/// Get the fault condition.
virtual code get_fault() const NOEXCEPT = 0;

/// Clear the error condition.
virtual void clear_error() NOEXCEPT = 0;
/// Get the disk full condition.
virtual bool is_full() const NOEXCEPT = 0;

/// Clear the disk full condition.
virtual void reset_full() NOEXCEPT = 0;
};

} // namespace database
Expand Down
27 changes: 11 additions & 16 deletions include/bitcoin/database/memory/map.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -90,24 +90,18 @@ class BCD_API map
/// Get r/w access to start/offset of memory map (or null).
memory_ptr get(size_t offset=zero) const NOEXCEPT override;

/// Get the current error condition.
code get_error() const NOEXCEPT override;
/// Get the fault condition.
code get_fault() const NOEXCEPT override;

/// Clear the error condition.
void clear_error() NOEXCEPT override;
/// Get the disk full condition.
bool is_full() const NOEXCEPT override;

/// Clear the disk full condition.
void reset_full() NOEXCEPT override;

protected:
void set_first_code(const error::error_t& value) NOEXCEPT;
size_t to_capacity(size_t required) const NOEXCEPT
{
BC_PUSH_WARNING(NO_STATIC_CAST)
const auto resize = required * ((expansion_ + 100.0) / 100.0);
const auto target = std::max(minimum_, static_cast<size_t>(resize));
BC_POP_WARNING()

BC_ASSERT_MSG(target >= required, "unexpected truncation");
return target;
}
size_t to_capacity(size_t required) const NOEXCEPT;
void set_first_code(const error::error_t& ec) NOEXCEPT;

private:
using path = std::filesystem::path;
Expand Down Expand Up @@ -140,7 +134,8 @@ class BCD_API map
size_t logical_{};
mutable std::shared_mutex field_mutex_{};

// This is thread safe;
// These are thread safe;
std::atomic<bool> full_{ false };
std::atomic<error::error_t> error_{ error::success };
};

Expand Down
11 changes: 7 additions & 4 deletions include/bitcoin/database/primitives/arraymap.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -71,11 +71,14 @@ class arraymap
/// Errors.
/// -----------------------------------------------------------------------

/// Get the current error condition.
code get_error() const NOEXCEPT;
/// Get the fault condition.
code get_fault() const NOEXCEPT;

/// Clear the error condition.
void clear_error() NOEXCEPT;
/// Get the disk full condition.
bool is_full() const NOEXCEPT;

/// Clear the disk full condition.
void reset_full() NOEXCEPT;

/// Query interface.
/// -----------------------------------------------------------------------
Expand Down
11 changes: 7 additions & 4 deletions include/bitcoin/database/primitives/hashmap.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -77,11 +77,14 @@ class hashmap
/// Errors.
/// -----------------------------------------------------------------------

/// Get the current error condition.
code get_error() const NOEXCEPT;
/// Get the fault condition.
code get_fault() const NOEXCEPT;

/// Clear the error condition.
void clear_error() NOEXCEPT;
/// Get the disk full condition.
bool is_full() const NOEXCEPT;

/// Clear the disk full condition.
void reset_full() NOEXCEPT;

/// Query interface, iterator is not thread safe.
/// -----------------------------------------------------------------------
Expand Down
Loading
Loading