#include #include #include #include #include "dpf/launch.hpp" #include "dpf/run_log.hpp" // Two-party open. Every run choice is a flag: // // c++ -std=c++17 -march=native -pthread -I include -I thirdparty \ // examples/protocol/two_party_exchange.cpp -lsctp // ./a.out # in-process async memory // ./a.out --transport=mux --lanes=1 # TCP mux on localhost // ./a.out --transport=parallel --window=65536 // // For separate processes, see party_node.cpp. int main(int argc, char ** argv) { try { auto cfg = dpf::app::run_config::from_env(); for (const auto & extra : cfg.apply_args(argc, argv)) throw std::invalid_argument("unknown argument " + extra); dpf::app::start_logging(cfg); dpf::protocol::composer c0(0); dpf::protocol::composer c1(1); auto x0 = c0.input(dpf::protocol::domain::a, 8); auto x1 = c1.input(dpf::protocol::domain::a, 8); auto o0 = c0.exchange(x0); (void)c1.exchange(x1); auto p0 = c0.schedule(); auto p1 = c1.schedule(); // One 8-byte input per instance; every instance opens to 42. dpf::app::party_values v0(p0.nodes().size()), v1(p1.nodes().size()); v0[x0.id].assign(8 * cfg.instances, 0); v1[x1.id].assign(8 * cfg.instances, 0); for (std::size_t i = 0; i < cfg.instances; ++i) { const std::uint64_t a = 11 + i, b = 31 - i; std::memcpy(v0[x0.id].data() + 8 * i, &a, 8); std::memcpy(v1[x1.id].data() + 8 * i, &b, 8); } const auto r = dpf::run_two_party(p0, p1, v0, v1, {}, cfg); bool all = true; std::uint64_t open = 0; for (std::size_t i = 0; i < cfg.instances; ++i) { std::memcpy(&open, v0[o0.id].data() + 8 * i, 8); all = all && open == 42; } std::cout << "two_party_exchange " << (all ? 42 : open) << " " << cfg.summary() << " wire_out=" << r.wire[0].bytes_out << "\n"; return all ? 0 : 1; } catch (const std::exception & e) { std::cerr << "two_party_exchange: " << e.what() << "\n"; return 1; } }