aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDennis Brentjes <d.brentjes@gmail.com>2016-12-14 15:51:43 +0100
committerDennis Brentjes <d.brentjes@gmail.com>2016-12-15 09:45:30 +0100
commitb42cb376c32ef4182d3e7f405f50dde2641e85b0 (patch)
treeb16ce5f2e6f8e6bd7cfb942fbca3d6a6e3f43bb2
parentad74ce8412eea2c554b048e379b9ca145d9694c6 (diff)
downloadcmix-b42cb376c32ef4182d3e7f405f50dde2641e85b0.tar.gz
cmix-b42cb376c32ef4182d3e7f405f50dde2641e85b0.tar.bz2
cmix-b42cb376c32ef4182d3e7f405f50dde2641e85b0.zip
Reworks the protocol to be tag attack resistant.
-rw-r--r--libcmix-common/cmixprotofunctor.hpp2
-rw-r--r--libcmix-protobuf/cmix.proto23
-rw-r--r--libcmix/cmix.c122
-rw-r--r--libcmix/cmix.h69
-rw-r--r--node/node.cpp24
-rw-r--r--node/node.hpp4
-rw-r--r--node/node_node.cpp217
7 files changed, 363 insertions, 98 deletions
diff --git a/libcmix-common/cmixprotofunctor.hpp b/libcmix-common/cmixprotofunctor.hpp
index 17793ec..85fe35b 100644
--- a/libcmix-common/cmixprotofunctor.hpp
+++ b/libcmix-common/cmixprotofunctor.hpp
@@ -66,8 +66,10 @@ struct CMixProtoFunctor {
PrePre, prepre,
PreMix, premix,
PrePost, prepost,
+ Commitments, commitments,
RealPre, realpre,
RealMix, realmix,
+ RealPost, realpost,
Payload, payload,
Performance, performance
)
diff --git a/libcmix-protobuf/cmix.proto b/libcmix-protobuf/cmix.proto
index 2af20bc..07e8721 100644
--- a/libcmix-protobuf/cmix.proto
+++ b/libcmix-protobuf/cmix.proto
@@ -50,6 +50,14 @@ message PreMix {
message PrePost {
repeated bytes r_EPiRS = 1;
repeated bytes m_EPiRS = 2;
+ repeated bytes decryption_commitments = 3;
+ bytes ciphertext_commitment = 4;
+}
+
+message Commitments {
+ repeated bytes m_EPiRS = 1;
+ repeated bytes decryption_commitments = 2;
+ bytes ciphertext_commitment = 3;
}
message RealPre {
@@ -61,6 +69,11 @@ message RealMix {
repeated bytes m = 2;
}
+message RealPost {
+ bytes PiMRS_commitment = 1;
+ repeated bytes m_epirs = 2;
+}
+
message Payload {
bytes payload = 1;
}
@@ -86,9 +99,11 @@ message CMixMessage {
PrePre prepre = 9;
PreMix premix = 10;
PrePost prepost = 11;
- RealPre realpre = 12;
- RealMix realmix = 13;
- Payload payload = 14;
- Performance performance = 15;
+ Commitments commitments = 12;
+ RealPre realpre = 13;
+ RealMix realmix = 14;
+ RealPost realpost = 15;
+ Payload payload = 16;
+ Performance performance = 17;
}
}
diff --git a/libcmix/cmix.c b/libcmix/cmix.c
index 0255f42..a4fba6f 100644
--- a/libcmix/cmix.c
+++ b/libcmix/cmix.c
@@ -14,7 +14,9 @@ struct CMixContext initialize_cmix_context(struct Api api) {
.r = NULL,
.s = NULL,
.permutation = NULL,
- .pirs = NULL,
+ .decryption_shares = NULL,
+ .EPiRS = NULL,
+ .PiMRS = NULL
};
}
@@ -22,8 +24,10 @@ enum cmix_error alloc_mix(struct CMixContext* ctx) {
ctx->r = (GroupElement*) calloc(ctx->nr_participants, sizeof(GroupElement));
ctx->s = (GroupElement*) calloc(ctx->nr_participants, sizeof(GroupElement));
ctx->permutation = (unsigned int*) calloc(ctx->nr_participants, sizeof(unsigned int));
- ctx->pirs = (GroupElement*) calloc(ctx->nr_participants, sizeof(GroupElement));
- if(!ctx->r || !ctx->s || !ctx->permutation || !ctx->pirs) {
+ ctx->decryption_shares = (GroupElement*) calloc(ctx->nr_participants, sizeof(GroupElement));
+ ctx->EPiRS = (GroupElement*) calloc(ctx->nr_participants, sizeof(GroupElement));
+ ctx->PiMRS = (GroupElement*) calloc(ctx->nr_participants, sizeof(GroupElement));
+ if(!ctx->r || !ctx->s || !ctx->permutation || !ctx->decryption_shares || !ctx->EPiRS || !ctx->PiMRS ) {
return out_of_memory;
}
return no_error;
@@ -33,7 +37,9 @@ void release_mix(struct CMixContext* ctx) {
for(size_t i = 0; i < ctx->nr_participants; ++i) {
ctx->api.free_group_element(ctx->r[i]);
ctx->api.free_group_element(ctx->s[i]);
- ctx->api.free_group_element(ctx->pirs[i]);
+ ctx->api.free_group_element(ctx->decryption_shares[i]);
+ ctx->api.free_group_element(ctx->EPiRS[i]);
+ ctx->api.free_group_element(ctx->PiMRS[i]);
}
free(ctx->r);
ctx->r = NULL;
@@ -44,8 +50,14 @@ void release_mix(struct CMixContext* ctx) {
free(ctx->permutation);
ctx->permutation = NULL;
- free(ctx->pirs);
- ctx->pirs = NULL;
+ free(ctx->decryption_shares);
+ ctx->decryption_shares = NULL;
+
+ free(ctx->EPiRS);
+ ctx->EPiRS = NULL;
+
+ free(ctx->PiMRS);
+ ctx->PiMRS = NULL;
ctx->nr_participants = 0;
}
@@ -186,7 +198,7 @@ enum cmix_error encrypt_r_and_multiply(struct CMixContext const* ctx, char** ran
element_to_buffer(ctx, random_buffer[i], new_random_element);
element_to_buffer(ctx, message_buffer[i], new_message_element);
-
+
ctx->api.free_group_element(enc_random_element);
ctx->api.free_group_element(enc_message_element);
ctx->api.free_group_element(other_random_element);
@@ -228,21 +240,22 @@ enum cmix_error permute_and_multiply_encrypted_s(struct CMixContext const* ctx,
return no_error;
}
-enum cmix_error permute_and_multiply_s(struct CMixContext const* ctx, char** out_buffer, char const** message) {
+enum cmix_error permute_and_multiply_s(struct CMixContext* ctx, char** out_buffer, char const** message) {
size_t el_size = get_group_element_array_size(ctx);
for(size_t i = 0; i < ctx->nr_participants; ++i) {
unsigned int new_pos = ctx->permutation[i];
GroupElement message_el = ctx->api.array_to_element(message[i], el_size, false);
- GroupElement mult = ctx->api.multiply(message_el, ctx->s[new_pos], false);
+ ctx->PiMRS[new_pos] = ctx->api.multiply(message_el, ctx->s[new_pos], false);
- element_to_buffer(ctx, out_buffer[new_pos], mult);
+ element_to_buffer(ctx, out_buffer[new_pos], ctx->PiMRS[new_pos]);
ctx->api.free_group_element(message_el);
- ctx->api.free_group_element(mult);
}
+
+
return no_error;
}
@@ -298,7 +311,8 @@ enum cmix_error key_exchange_initiator(struct CMixContext const* ctx, GroupEleme
return no_error;
}
-enum cmix_error post_process(struct CMixContext* ctx, char** r_out, char** m_out, const char** r_epirs, const char** m_epirs) {
+/*
+enum cmix_error precomputation_post_process_unsafe(struct CMixContext* ctx, char** r_out, char** m_out, const char** r_epirs, const char** m_epirs) {
for(size_t i = 0; i < ctx->nr_participants; ++i) {
GroupElement x = ctx->api.array_to_element(r_epirs[i], get_group_element_array_size(ctx), true);
GroupElement D = ctx->api.get_decryption_share(x, ctx->keypair.sec);
@@ -318,6 +332,37 @@ enum cmix_error post_process(struct CMixContext* ctx, char** r_out, char** m_out
return no_error;
}
+*/
+
+size_t get_commitment_length(struct CMixContext const* ctx) {
+ return 1;
+}
+
+enum cmix_error precomputation_post_process(struct CMixContext* ctx, char* commitment, const char** r_epirs, const char** m_epirs) {
+ size_t len = get_group_element_array_size(ctx);
+
+ for(size_t i = 0; i < ctx->nr_participants; ++i) {
+ GroupElement x = ctx->api.array_to_element(r_epirs[i], get_group_element_array_size(ctx), true);
+ ctx->decryption_shares[i] = ctx->api.get_decryption_share(x, ctx->keypair.sec);
+
+ ctx->EPiRS[i] = ctx->api.array_to_element(m_epirs[i], len, true);
+
+ ctx->api.free_group_element(x);
+ }
+
+ //ToDo: actually calculate commitment.
+
+ memset(commitment, 0, get_commitment_length(ctx));
+
+ return no_error;
+}
+
+enum cmix_error commit_precomputation_ciphertext(struct CMixContext* ctx, char* commitment, const char** m_epirs) {
+ //ToDo: actually calculate commitment.
+ memset(commitment, 0, get_commitment_length(ctx));
+
+ return no_error;
+}
enum cmix_error blind_message(struct CMixContext const* ctx, char* m_out, char const* message, GroupElement const* keys, size_t const nr_nodes) {
size_t len = get_group_element_array_size(ctx);
@@ -363,19 +408,48 @@ enum cmix_error swap_k_for_r(struct CMixContext const* ctx, char** out_buffer, c
return no_error;
}
-enum cmix_error remove_r_and_s(struct CMixContext const* ctx, char* out_buffer, char const* message, size_t index) {
- size_t len = get_group_element_array_size(ctx);
-
- GroupElement mes = ctx->api.array_to_element(message, len, false);
- GroupElement inv_pirs = ctx->api.invert(ctx->pirs[index]);
-
- GroupElement mult = ctx->api.multiply(mes, inv_pirs, false);
-
- element_to_buffer(ctx, out_buffer, mult);
+
+enum cmix_error get_epirs(struct CMixContext const* ctx, char** out_buffer) {
+ for(size_t i = 0; i < ctx->nr_participants; ++i) {
+ element_to_buffer(ctx, out_buffer[i], ctx->EPiRS[i]);
+ }
+ return no_error;
+}
+
+enum cmix_error get_pimrs_commitment(struct CMixContext const* ctx, char* out_buffer, const char** pimrss) {
+ (void) pimrss;
+ memset(out_buffer, '\0', get_commitment_length(ctx));
+ return no_error;
+}
+
+enum cmix_error decrypt_epirs(struct CMixContext const* ctx, char** out_buffer, const char** epirs) {
+ for(size_t i = 0; i < ctx->nr_participants; ++i) {
+ GroupElement msg = ctx->api.array_to_element(epirs[i], get_group_element_array_size(ctx), true);
+ GroupElement pirs = ctx->api.multiply(ctx->decryption_shares[i], msg, true);
+ element_to_buffer(ctx, out_buffer[i], pirs);
+
+ ctx->api.free_group_element(msg);
+ ctx->api.free_group_element(pirs);
+ }
- ctx->api.free_group_element(mes);
- ctx->api.free_group_element(inv_pirs);
- ctx->api.free_group_element(mult);
+ return no_error;
+}
+
+enum cmix_error remove_pirs(struct CMixContext const* ctx, char** out_buffer, const char** pirs) {
+ size_t len = get_group_element_array_size(ctx);
+
+ for(size_t i = 0; i < ctx->nr_participants; ++i) {
+ GroupElement g_pirs = ctx->api.array_to_element(pirs[i], len, false);
+ GroupElement inv_pirs = ctx->api.invert(g_pirs);
+
+ GroupElement mult = ctx->api.multiply(ctx->PiMRS[i], inv_pirs, false);
+
+ element_to_buffer(ctx, out_buffer[i], mult);
+
+ ctx->api.free_group_element(g_pirs);
+ ctx->api.free_group_element(inv_pirs);
+ ctx->api.free_group_element(mult);
+ }
return no_error;
}
diff --git a/libcmix/cmix.h b/libcmix/cmix.h
index 06fd939..5c6a4c1 100644
--- a/libcmix/cmix.h
+++ b/libcmix/cmix.h
@@ -49,7 +49,9 @@ struct CMixContext {
GroupElement* r; ///< An array of random values (R in the paper).
GroupElement* s; ///< An array of random values (S in the paper).
unsigned int* permutation; ///< a permutation (π in the paper (called Pi in source)).
- GroupElement* pirs; ///< an array containing π(R) * S
+ GroupElement* decryption_shares; ///< The decryption share for each slot.
+ GroupElement* EPiRS; ///< stores teh current π(R) * S for this node. Only usfull for the last node.
+ GroupElement* PiMRS; ///< stores the current π(M * R) * S for this node. Only usefull for the last node.
};
/*!
@@ -240,16 +242,30 @@ enum cmix_error encrypt_r_and_multiply(struct CMixContext const* ctx, char** ran
enum cmix_error permute_and_multiply_encrypted_s(struct CMixContext const* ctx, char** random_buffer, char** message_buffer, char const** random_element, char const** message_element);
/*!
- * \brief post_process decrypts Pi(R) * S and stores it in the context.
+ * \brief get_commitment_length
+ * \param ctx
+ * \return
+ */
+size_t get_commitment_length(struct CMixContext const* ctx);
+
+/*!
+ * \brief precomputation_post_process Calculates it's decryption shares and it's commitment to them.
* \note The stored pirs only has meaning for the last node, but just storing it for the last node just adds unneeded complexity.
* \param ctx The relevant context.
- * \param r_out The output buffer for the random components.
- * \param m_out The output buffer for the message components.
+ * \param commitment a buffer of size get_commitment_length() to store the commitment.
* \param r_epirs The input buffer for the random components.
- * \param m_epirs The input buffer for the message components.
* \return A cmix_error
*/
-enum cmix_error post_process(struct CMixContext* ctx, char** r_out, char** m_out, char const** r_epirs, char const** m_epirs);
+enum cmix_error precomputation_post_process(struct CMixContext* ctx, char* commitment, const char** r_epirs, const char** m_epirs);
+
+/*!
+ * \brief commit_precomputation_ciphertext
+ * \param ctx
+ * \param commitment
+ * \param m_epirs
+ * \return
+ */
+enum cmix_error commit_precomputation_ciphertext(struct CMixContext* ctx, char* commitment, const char** m_epirs);
/*!
* \brief swap_k_for_r multiplies with K^-1 and multiplies with R
@@ -268,17 +284,42 @@ enum cmix_error swap_k_for_r(struct CMixContext const* ctx, char** out_buffer, c
* \param message The input buffer.
* \return A cmix_error
*/
-enum cmix_error permute_and_multiply_s(struct CMixContext const* ctx, char** out_buffer, char const** message);
+enum cmix_error permute_and_multiply_s(struct CMixContext* ctx, char** out_buffer, char const** message);
/*!
- * \brief remove_r_and_s multiply with (Pi(R) * S)^-1
- * \param ctx The relevant context.
- * \param out_buffer The ouput buffer,
- * \param message The input buffer
- * \param index message process message x (take the x'th Pi(R) * S)
- * \return A cmix_error
+ * \brief get_epirs
+ * \param ctx
+ * \param out_buffer
+ * \return
+ */
+enum cmix_error get_epirs(struct CMixContext const* ctx, char** out_buffer);
+
+/*!
+ * \brief get_pimrs_commitment
+ * \param ctx
+ * \param out_buffer
+ * \param pimrss
+ * \return
+ */
+enum cmix_error get_pimrs_commitment(struct CMixContext const* ctx, char* out_buffer, const char** pimrss);
+
+/*!
+ * \brief decrypt_epirs
+ * \param ctx
+ * \param out_buffer
+ * \param epirs
+ * \return
+ */
+enum cmix_error decrypt_epirs(struct CMixContext const* ctx, char** out_buffer, const char** epirs);
+
+/*!
+ * \brief remove_pirs
+ * \param ctx
+ * \param out_buffer
+ * \param pirs
+ * \return
*/
-enum cmix_error remove_r_and_s(struct CMixContext const* ctx, char* out_buffer, char const* message, size_t index);
+enum cmix_error remove_pirs(struct CMixContext const* ctx, char** out_buffer, const char** pirs);
/*!
* \brief split_message Splits a message in its destination and payload components.
diff --git a/node/node.cpp b/node/node.cpp
index dc0d1c0..2407138 100644
--- a/node/node.cpp
+++ b/node/node.cpp
@@ -148,7 +148,7 @@ void Node::start_precomputation() {
}
BOOST_LOG_TRIVIAL(trace) << "Starting precomputation for " << messages.size() << " clients.";
- index_map.clear();
+ participants.clear();
if(messages.size() < network_settings.minimum_nr_messages) {
start_timer_delayed_mix();
@@ -159,9 +159,8 @@ void Node::start_precomputation() {
exit(-1);
}
- unsigned int i = 0;
for(auto&& pair : messages) {
- index_map[pair.first] = i++;
+ participants.push_back(pair.first);
}
if(initialize_mix_randomness(&cmix_ctx) != no_error) {
@@ -170,7 +169,7 @@ void Node::start_precomputation() {
std::stringstream ss;
ss << "permutation:";
- for(auto i = 0; i < cmix_ctx.nr_participants; ++i) {
+ for(auto i = 0u; i < cmix_ctx.nr_participants; ++i) {
ss << " " << cmix_ctx.permutation[i];
}
BOOST_LOG_TRIVIAL(trace) << ss.str();
@@ -228,13 +227,12 @@ void Node::start_realtime_phase() {
size_t len = get_group_element_array_size(&cmix_ctx);
- std::vector<char*> ms(index_map.size(), nullptr);
- std::vector<char const*> msv(index_map.size(), nullptr);
- std::vector<GroupElement> keys(index_map.size(), nullptr);
- auto it = index_map.begin();
- for(size_t i = 0; i < index_map.size(); ++i) {
- auto handle = it->first;
- auto index = it->second;
+ std::vector<char*> ms(participants.size(), nullptr);
+ std::vector<char const*> msv(participants.size(), nullptr);
+ std::vector<GroupElement> keys(participants.size(), nullptr);
+ auto it = participants.begin();
+ for(size_t i = 0; i < participants.size(); ++i) {
+ auto handle = *it;
std::string* m = realpre.add_m();
m->resize(len);
@@ -270,8 +268,8 @@ void Node::start_realtime_phase() {
next_node.async_send(realpre);
- for(auto&& pair : index_map) {
- messages.at(pair.first).pop();
+ for(auto&& handle : participants) {
+ messages.at(handle).pop();
}
}
diff --git a/node/node.hpp b/node/node.hpp
index 1aad503..d9e16d4 100644
--- a/node/node.hpp
+++ b/node/node.hpp
@@ -104,7 +104,7 @@ class Node
CMixContext cmix_ctx;
- std::map<std::string, unsigned int> index_map;
+ std::vector<std::string> participants;
bool shutting_down;
@@ -123,8 +123,10 @@ class Node
void handle_node_prepre(cmix_proto::PrePre const& prepre);
void handle_node_premix(cmix_proto::PreMix const& premix);
void handle_node_prepost(cmix_proto::PrePost const& prepost);
+ void handle_node_commitments(cmix_proto::Commitments const& commitments);
void handle_node_realpre(cmix_proto::RealPre const& realpre);
void handle_node_realmix(cmix_proto::RealMix const& realmix);
+ void handle_node_realpost(cmix_proto::RealPost const& realpost);
void handle_node_message(cmix_proto::CMixMessage message);
void handle_client_keyexchange(ClientConnections::key_type handle, cmix_proto::KeyExchange const& ke);
diff --git a/node/node_node.cpp b/node/node_node.cpp
index a0e04fa..56e883d 100644
--- a/node/node_node.cpp
+++ b/node/node_node.cpp
@@ -80,33 +80,49 @@ void fill_precomputation_mix_message(CMixContext const& ctx, cmix_proto::PreMix&
}
template <typename T>
-void fill_precomputation_post_message(CMixContext& ctx, cmix_proto::PrePost& prepost, T const& rs, T const& ms) {
- size_t len = get_group_element_array_size(&ctx);
-
- std::vector<char*> r_epirs(ms.size(), nullptr);
- std::vector<char*> m_epirs(ms.size(), nullptr);
+void fill_precomputation_post_message(CMixContext& ctx, cmix_proto::PrePost& prepost, T const& rs, T const& ms, T const& cs = T{}) {
+
std::vector<char const*> rsv(ms.size(), nullptr);
std::vector<char const*> msv(ms.size(), nullptr);
- for(auto i = 0; i < ms.size(); ++i) {
- std::string* r = prepost.add_r_epirs();
- r->resize(len);
- r_epirs[size_t(i)] = &(*r)[0];
-
- std::string* m = prepost.add_m_epirs();
- m->resize(len);
- m_epirs[i] = &(*m)[0];
-
+ for(auto i = 0; i < ms.size(); ++i) {
rsv[i] = rs.Get(i).data();
msv[i] = ms.Get(i).data();
}
- post_process(
+ std::string* decryption_commitment = prepost.add_decryption_commitments();
+ decryption_commitment->resize(get_commitment_length(&ctx));
+
+ precomputation_post_process(
&ctx,
- r_epirs.data(),
- m_epirs.data(),
+ &(*decryption_commitment)[0],
rsv.data(),
msv.data()
);
+
+ *prepost.mutable_r_epirs() = rs;
+ *prepost.mutable_m_epirs() = ms;
+ *prepost.mutable_decryption_commitments() = cs;
+}
+
+template <typename T>
+void fill_commitments_message(CMixContext& ctx, cmix_proto::Commitments& commits, T const& ms, T const& cs) {
+
+ std::vector<char const*> msv(ms.size(), nullptr);
+ for(auto i = 0; i < ms.size(); ++i) {
+ msv[i] = ms.Get(i).data();
+ }
+
+ std::vector<char> commitment(get_commitment_length(&ctx), '\0');
+
+ commit_precomputation_ciphertext(
+ &ctx,
+ commitment.data(),
+ msv.data()
+ );
+
+ *commits.mutable_m_epirs() = ms;
+ *commits.mutable_decryption_commitments() = cs;
+ commits.set_ciphertext_commitment(commitment.data(), commitment.size());
}
template <typename T>
@@ -157,6 +173,55 @@ void fill_realtime_mix_message(CMixContext& ctx, cmix_proto::RealMix& realmix, T
);
}
+void fill_realtime_post_message(CMixContext& ctx, cmix_proto::RealPost& realpost, cmix_proto::RealMix const& realmix) {
+
+ size_t len = get_group_element_array_size(&ctx);
+ std::vector<char*> mv(ctx.nr_participants, nullptr);
+ for(int i = 0; i < ctx.nr_participants; ++i) {
+ std::string* m = realpost.add_m_epirs();
+ m->resize(len);
+ mv[i] = &(*m)[0];
+ }
+
+ get_epirs(
+ &ctx,
+ mv.data()
+ );
+
+ std::string* m = realpost.mutable_pimrs_commitment();
+ m->resize(get_commitment_length(&ctx));
+
+ std::vector<const char*> mvs(ctx.nr_participants, nullptr);
+ for(int i = 0; i < ctx.nr_participants; ++i) {
+ mvs[i] = realmix.m(i).data();
+ }
+
+ get_pimrs_commitment(
+ &ctx,
+ &(*m)[0],
+ mvs.data()
+ );
+}
+
+void fill_realtime_post_message(CMixContext& ctx, cmix_proto::RealPost& n_realpost, cmix_proto::RealPost const& realpost) {
+ size_t len = get_group_element_array_size(&ctx);
+ std::vector<char*> mv(ctx.nr_participants, nullptr);
+ std::vector<char const*> mvs(ctx.nr_participants, nullptr);
+ for(size_t i = 0; i < ctx.nr_participants; ++i) {
+ std::string* m = n_realpost.add_m_epirs();
+ m->resize(len);
+ mv[i] = &(*m)[0];
+
+ mvs[i] = realpost.m_epirs(i).data();
+ }
+
+ decrypt_epirs(
+ &ctx,
+ mv.data(),
+ mvs.data()
+ );
+}
+
void Node::handle_node_initialization(const cmix_proto::Initialization& init)
{
if(network_settings.is_first) {
@@ -252,21 +317,39 @@ void Node::handle_node_premix(cmix_proto::PreMix const& premix) {
}
void Node::handle_node_prepost(cmix_proto::PrePost const& prepost) {
- if(network_settings.is_first) {
- start_realtime_phase();
+ if(performance) {
+ performance->send("pre_post_start");
+ }
+
+ if(network_settings.is_last) {
+ ArenaMessage<cmix_proto::PrePost> arena;
+ auto& n_prepost = arena.get();
+ fill_precomputation_post_message(cmix_ctx, n_prepost, prepost.r_epirs(), prepost.m_epirs(), prepost.decryption_commitments());
+
+ ArenaMessage<cmix_proto::Commitments> arena2;
+ auto& commits = arena2.get();
+ fill_commitments_message(cmix_ctx, commits, n_prepost.m_epirs(), n_prepost.decryption_commitments());
+ next_node.async_send(commits);
} else {
- if(performance) {
- performance->send("pre_post_start");
- }
-
ArenaMessage<cmix_proto::PrePost> arena;
auto& n_prepost = arena.get();
- fill_precomputation_post_message(cmix_ctx, n_prepost, prepost.r_epirs(), prepost.m_epirs());
+ fill_precomputation_post_message(cmix_ctx, n_prepost, prepost.r_epirs(), prepost.m_epirs(), prepost.decryption_commitments());
next_node.async_send(n_prepost);
-
- if(performance) {
- performance->send("pre_post_end");
- }
+ }
+ if(performance) {
+ performance->send("pre_post_end");
+ }
+}
+
+void Node::handle_node_commitments(cmix_proto::Commitments const& comm) {
+
+ //Do your commitments check/storage.
+
+ if(!network_settings.is_first && !network_settings.is_last) {
+ next_node.async_send(comm);
+ }
+ if(network_settings.is_first) {
+ next_node.async_send(comm, [this]{start_realtime_phase();});
}
}
@@ -312,23 +395,64 @@ void Node::handle_node_realmix(cmix_proto::RealMix const& realmix) {
auto& n_realmix = arena.get();
fill_realtime_mix_message(cmix_ctx, n_realmix, realmix.m());
+ ArenaMessage<cmix_proto::RealPost> arena2;
+ auto& realpost = arena2.get();
+ fill_realtime_post_message(cmix_ctx, realpost, n_realmix);
+
+ next_node.async_send(realpost);
+
if(performance) {
performance->send("real_mix_end");
}
+ } else {
+ if(performance) {
+ performance->send("real_mix_start");
+ }
+
+ ArenaMessage<cmix_proto::RealMix> arena;
+ auto& n_realmix = arena.get();
+ fill_realtime_mix_message(cmix_ctx, n_realmix, realmix.m());
+ next_node.async_send(n_realmix);
+
+ if(performance) {
+ performance->send("real_mix_end");
+ }
+ }
+}
+
+void Node::handle_node_realpost(cmix_proto::RealPost const& realpost) {
+ if(network_settings.is_last) {
if(performance) {
performance->send("real_post_start");
}
+ ArenaMessage<cmix_proto::RealPost> arena;
+ auto& n_realpost = arena.get();
+ fill_realtime_post_message(cmix_ctx, n_realpost, realpost);
+
size_t len = get_group_element_array_size(&cmix_ctx);
- std::string str;
- str.resize(len);
+ std::vector<std::string> messages(cmix_ctx.nr_participants);
+ std::vector<const char*> pirs(cmix_ctx.nr_participants, nullptr);
+ std::vector<char*> msgs(cmix_ctx.nr_participants, nullptr);
+ for(size_t i = 0; i < cmix_ctx.nr_participants; ++i) {
+ messages[i].resize(len);
+ msgs[i] = &messages[i][0];
+
+ pirs[i] = n_realpost.m_epirs(i).data();
+ }
+
+ remove_pirs (
+ &cmix_ctx,
+ msgs.data(),
+ pirs.data()
+ );
- for(int i = 0; i < n_realmix.m_size(); i++) {
- remove_r_and_s(&cmix_ctx, &str[0], n_realmix.m(i).data(), i);
+
+ for(auto i = 0u; i < cmix_ctx.nr_participants; i++) {
{
std::stringstream ss;
- for(auto&& c : str) {
+ for(auto&& c : messages[i]) {
ss << "\\" << std::setw(3) << std::setfill('0') << std::oct << (unsigned int) c;
}
BOOST_LOG_TRIVIAL(trace) << ss.str();
@@ -340,7 +464,7 @@ void Node::handle_node_realmix(cmix_proto::RealMix const& realmix) {
char* payload;
size_t payload_len;
- split_message(&cmix_ctx, &dest, &dest_len, &payload, &payload_len, str.data());
+ split_message(&cmix_ctx, &dest, &dest_len, &payload, &payload_len, messages[i].data());
std::string dest_s = std::string(dest, dest_len);
@@ -355,19 +479,18 @@ void Node::handle_node_realmix(cmix_proto::RealMix const& realmix) {
if(performance) {
performance->send("real_post_end");
}
-
} else {
if(performance) {
- performance->send("real_mix_start");
+ performance->send("real_post_start");
}
-
- ArenaMessage<cmix_proto::RealMix> arena;
- auto& n_realmix = arena.get();
- fill_realtime_mix_message(cmix_ctx, n_realmix, realmix.m());
- next_node.async_send(n_realmix);
+
+ ArenaMessage<cmix_proto::RealPost> arena;
+ auto& n_realpost = arena.get();
+ fill_realtime_post_message(cmix_ctx, n_realpost, realpost);
+ next_node.async_send(n_realpost);
if(performance) {
- performance->send("real_mix_end");
+ performance->send("real_post_end");
}
}
}
@@ -409,6 +532,11 @@ void Node::handle_node_message(cmix_proto::CMixMessage message)
handle_node_prepost(message.prepost());
break;
}
+ case cmix_proto::CMixMessage::ContentsCase::kCommitments: {
+ BOOST_LOG_TRIVIAL(trace) << "Handling PrePost";
+ handle_node_commitments(message.commitments());
+ break;
+ }
case cmix_proto::CMixMessage::ContentsCase::kRealpre: {
BOOST_LOG_TRIVIAL(trace) << "Handling RealPre";
handle_node_realpre(message.realpre());
@@ -419,6 +547,11 @@ void Node::handle_node_message(cmix_proto::CMixMessage message)
handle_node_realmix(message.realmix());
break;
}
+ case cmix_proto::CMixMessage::ContentsCase::kRealpost: {
+ BOOST_LOG_TRIVIAL(trace) << "Handling RealPost";
+ handle_node_realpost(message.realpost());
+ break;
+ }
default: {
BOOST_LOG_TRIVIAL(error) << "handle_node_message: CMixMessage contains unknown contents.";
}