-
Notifications
You must be signed in to change notification settings - Fork 270
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
fix: Fix races in slab allocator and lookup tables and add prepending for op_queues #4754
Changes from all commits
9084ab6
cebae8f
f854c92
2d484be
cae5d47
f1ce314
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -38,6 +38,73 @@ class ECCOpQueue { | |
|
||
Point get_accumulator() { return accumulator; } | ||
|
||
/** | ||
* @brief Prepend the information from the previous queue (used before accumulation/merge proof to be able to run | ||
* circuit construction separately) | ||
* | ||
* @param previous | ||
*/ | ||
void prepend_previous_queue(const ECCOpQueue& previous) | ||
{ | ||
// Allocate enough space | ||
std::vector<ECCVMOperation> raw_ops_updated(raw_ops.size() + previous.raw_ops.size()); | ||
// Copy the previous raw ops to the beginning of the new vector | ||
std::copy(previous.raw_ops.begin(), previous.raw_ops.end(), raw_ops_updated.begin()); | ||
// Copy the raw ops from current queue after the ones from the previous queue (concatenate them) | ||
std::copy(raw_ops.begin(), | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. i stared at this line quite a bit, can you be more explicit in comments? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Added a few |
||
raw_ops.end(), | ||
std::next(raw_ops_updated.begin(), static_cast<long>(previous.raw_ops.size()))); | ||
|
||
// Swap raw_ops underlying storage | ||
raw_ops.swap(raw_ops_updated); | ||
// Do the same 3 operations for ultra_ops | ||
for (size_t i = 0; i < 4; i++) { | ||
// Allocate new vector | ||
std::vector<Fr> current_ultra_op(ultra_ops[i].size() + previous.ultra_ops[i].size()); | ||
// Copy the previous ultra ops to the beginning of the new vector | ||
std::copy(previous.ultra_ops[i].begin(), previous.ultra_ops[i].end(), current_ultra_op.begin()); | ||
// Copy the ultra ops from current queue after the ones from the previous queue (concatenate them) | ||
std::copy(ultra_ops[i].begin(), | ||
ultra_ops[i].end(), | ||
std::next(current_ultra_op.begin(), static_cast<long>(previous.ultra_ops[i].size()))); | ||
// Swap storage | ||
ultra_ops[i].swap(current_ultra_op); | ||
} | ||
// Update sizes | ||
current_ultra_ops_size += previous.ultra_ops[0].size(); | ||
previous_ultra_ops_size += previous.ultra_ops[0].size(); | ||
// Update commitments | ||
ultra_ops_commitments = previous.ultra_ops_commitments; | ||
previous_ultra_ops_commitments = previous.previous_ultra_ops_commitments; | ||
} | ||
|
||
/** | ||
* @brief Enable using std::swap on queues | ||
* | ||
*/ | ||
friend void swap(ECCOpQueue& lhs, ECCOpQueue& rhs) | ||
{ | ||
// Swap vectors | ||
lhs.raw_ops.swap(rhs.raw_ops); | ||
for (size_t i = 0; i < 4; i++) { | ||
lhs.ultra_ops[i].swap(rhs.ultra_ops[i]); | ||
} | ||
// Swap sizes | ||
size_t temp = lhs.current_ultra_ops_size; | ||
lhs.current_ultra_ops_size = rhs.current_ultra_ops_size; | ||
rhs.current_ultra_ops_size = temp; | ||
temp = lhs.previous_ultra_ops_size; | ||
lhs.previous_ultra_ops_size = rhs.previous_ultra_ops_size; | ||
rhs.previous_ultra_ops_size = temp; | ||
// Swap commitments | ||
auto commit_temp = lhs.previous_ultra_ops_commitments; | ||
lhs.previous_ultra_ops_commitments = rhs.previous_ultra_ops_commitments; | ||
rhs.previous_ultra_ops_commitments = commit_temp; | ||
commit_temp = lhs.ultra_ops_commitments; | ||
lhs.ultra_ops_commitments = rhs.ultra_ops_commitments; | ||
rhs.ultra_ops_commitments = commit_temp; | ||
} | ||
|
||
/** | ||
* @brief Set the current and previous size of the ultra_ops transcript | ||
* | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,6 @@ | ||
#include "plookup_tables.hpp" | ||
#include "barretenberg/common/constexpr_utils.hpp" | ||
|
||
#include <mutex> | ||
namespace bb::plookup { | ||
|
||
using namespace bb; | ||
|
@@ -10,10 +10,21 @@ namespace { | |
// NOLINTNEXTLINE(cppcoreguidelines-avoid-non-const-global-variables) | ||
std::array<MultiTable, MultiTableId::NUM_MULTI_TABLES> MULTI_TABLES; | ||
// NOLINTNEXTLINE(cppcoreguidelines-avoid-non-const-global-variables) | ||
bool inited = false; | ||
bool initialised = false; | ||
#ifndef NO_MULTITHREADING | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. same here about adding a comment There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. done |
||
|
||
// The multitables initialisation procedure is not thread-sage, so we need to make sure only 1 thread gets to initialize | ||
// them. | ||
std::mutex multi_table_mutex; | ||
#endif | ||
void init_multi_tables() | ||
{ | ||
#ifndef NO_MULTITHREADING | ||
std::unique_lock<std::mutex> lock(multi_table_mutex); | ||
#endif | ||
if (initialised) { | ||
return; | ||
} | ||
MULTI_TABLES[MultiTableId::SHA256_CH_INPUT] = sha256_tables::get_choose_input_table(MultiTableId::SHA256_CH_INPUT); | ||
MULTI_TABLES[MultiTableId::SHA256_MAJ_INPUT] = | ||
sha256_tables::get_majority_input_table(MultiTableId::SHA256_MAJ_INPUT); | ||
|
@@ -96,14 +107,14 @@ void init_multi_tables() | |
keccak_tables::Rho<8, i>::get_rho_output_table(MultiTableId::KECCAK_NORMALIZE_AND_ROTATE); | ||
}); | ||
MULTI_TABLES[MultiTableId::HONK_DUMMY_MULTI] = dummy_tables::get_honk_dummy_multitable(); | ||
initialised = true; | ||
} | ||
} // namespace | ||
|
||
const MultiTable& create_table(const MultiTableId id) | ||
{ | ||
if (!inited) { | ||
if (!initialised) { | ||
init_multi_tables(); | ||
inited = true; | ||
initialised = true; | ||
} | ||
return MULTI_TABLES[id]; | ||
} | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
can you please add a comment explaining what this is for?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Added