diff --git a/CMakeLists.txt b/CMakeLists.txt index a03b222e..eab3b031 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -2,6 +2,7 @@ cmake_minimum_required(VERSION 3.10) project(ABY LANGUAGES CXX) option(ABY_BUILD_EXE "Build executables" OFF) +option(ABY_ENABLE_MATRIX "Enable logging for the MATRIX framework in examples applications" OFF) list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_LIST_DIR}/cmake") diff --git a/MATRIX/build.sh b/MATRIX/build.sh new file mode 100644 index 00000000..9481ea90 --- /dev/null +++ b/MATRIX/build.sh @@ -0,0 +1,9 @@ +#!/usr/bin/env bash + +# for custom, up-to-date CMake installed to ~/prefix +export PATH="$HOME/prefix/bin:$PATH" + +cd .. +mkdir -p build && cd build +cmake .. -DABY_BUILD_EXE=On -DABY_ENABLE_MATRIX=On +make -j`nproc` diff --git a/MATRIX/logs/dummylog b/MATRIX/logs/dummylog new file mode 100644 index 00000000..e69de29b diff --git a/README.md b/README.md index 76922336..34475eff 100644 --- a/README.md +++ b/README.md @@ -122,6 +122,9 @@ applications, you use the `ABY_BUILD_EXE` option: cmake .. -DABY_BUILD_EXE=On ``` +If also `-DABY_ENABLE_MATRIX=On` is given, then the examples output data for +the [MATRIX framework](https://github.com/cryptobiu/MATRIX) (if available). + ###### Build Options You can choose the build type, e.g. `Release` or `Debug` using diff --git a/src/abycore/MATRIX/MatrixMeasurement.h b/src/abycore/MATRIX/MatrixMeasurement.h new file mode 100644 index 00000000..1c8cab93 --- /dev/null +++ b/src/abycore/MATRIX/MatrixMeasurement.h @@ -0,0 +1,110 @@ +// +// Created by liork on 8/22/18. +// + +#ifndef ABY_MATRIXMEASUREMENT_H +#define ABY_MATRIXMEASUREMENT_H + +#include +#include +#include +#include +#include + + +using namespace std; +using namespace std::chrono; + +class MatrixMeasurement +{ +private: + string getcwdStr() const + { + char buff[256]; + auto res = getcwd(buff, 255); + assert(res != NULL); + return std::string(buff); + } + + size_t getTaskIdx(string name) const + { + auto it = std::find(m_tasksNames.begin(), m_tasksNames.end(), name); + auto idx = distance(m_tasksNames.begin(), it); + return idx; + } + + size_t numberOfIterations; + vector m_tasksNames; + vector> m_cpuStartTimes; + vector> m_cpuEndTimes; + string m_arguments = ""; + +public: + MatrixMeasurement(size_t argc, char* argv[], vector tasksNames, size_t numberOfIterations): + numberOfIterations(numberOfIterations), + m_tasksNames(tasksNames), + m_cpuStartTimes(vector>(tasksNames.size(), vector(numberOfIterations))), + m_cpuEndTimes(vector>(tasksNames.size(), vector(numberOfIterations))) + { + + for(size_t idx = 0; idx < argc; ++idx) + { + string s(argv[idx]); + if (idx < argc - 1) + m_arguments += s + "*"; + else + m_arguments += s; + } + + } + + auto get_ms_since_epoch() const + { + //Cast the time point to ms, then get its duration, then get the duration's count. + auto now = system_clock::now(); + return time_point_cast(now).time_since_epoch().count(); + } + + void startSubTask(string taskName, size_t currentIterationNumber) + { + auto taskIdx = getTaskIdx(taskName); + m_cpuStartTimes[taskIdx][currentIterationNumber] = get_ms_since_epoch(); + } + + void endSubTask(string taskName, size_t currentIterationNumber) + { + auto taskIdx = getTaskIdx(taskName); + m_cpuEndTimes[taskIdx][currentIterationNumber] = get_ms_since_epoch(); + } + + void write_log() const + { + string logFileName = getcwdStr() + "/../../MATRIX/logs/" + m_arguments + ".log"; + ofstream logFile(logFileName); + if (!logFile.is_open()) + { + cerr << "MatrixMeasurement: Could not open log file '" + << logFileName + << "'\n"; + return; + } + //write to file + for (size_t task_idx = 0; task_idx < m_tasksNames.size(); ++task_idx) + { + logFile << m_tasksNames[task_idx] + ":"; + cout << "taskName : " << m_tasksNames[task_idx] << endl; + for (size_t iteration = 0; iteration < numberOfIterations; ++iteration) + { + cout << "value : " << m_cpuEndTimes[task_idx][iteration] << endl; + logFile << to_string(m_cpuEndTimes[task_idx][iteration] + - m_cpuStartTimes[task_idx][iteration]) + << ","; + } + + logFile << "\n"; + } + logFile.close(); + } +}; + +#endif //ABY_MATRIXMEASUREMENT_H diff --git a/src/examples/innerproduct/CMakeLists.txt b/src/examples/innerproduct/CMakeLists.txt index be90b660..419fb7d7 100644 --- a/src/examples/innerproduct/CMakeLists.txt +++ b/src/examples/innerproduct/CMakeLists.txt @@ -1,3 +1,6 @@ add_executable(innerproduct_test innerproduct_test.cpp common/innerproduct.cpp) target_link_libraries(innerproduct_test ABY::aby ENCRYPTO_utils::encrypto_utils) +if(ABY_ENABLE_MATRIX) + target_compile_definitions(innerproduct_test PRIVATE ABY_ENABLE_MATRIX) +endif() diff --git a/src/examples/innerproduct/common/innerproduct.cpp b/src/examples/innerproduct/common/innerproduct.cpp index 4930fba6..2cefdf0c 100644 --- a/src/examples/innerproduct/common/innerproduct.cpp +++ b/src/examples/innerproduct/common/innerproduct.cpp @@ -17,12 +17,29 @@ */ #include "innerproduct.h" -#include "../../../abycore/sharing/sharing.h" +#include +#include int32_t test_inner_product_circuit(e_role role, const std::string& address, uint16_t port, seclvl seclvl, uint32_t nvals, uint32_t bitlen, uint32_t nthreads, e_mt_gen_alg mt_alg, e_sharing sharing, uint32_t num) { + /** + Step 0: Init logger. + */ + char * argv[4]; + argv[0] = (char*)"innerproduct"; + argv[1] = (char*)malloc(16); + sprintf(argv[1], "%d", role); + argv[2] = (char*)malloc(16); + sprintf(argv[2], "%d", bitlen); + argv[3] = (char*)malloc(16); + sprintf(argv[3], "%d", seclvl.symbits); + + vector subTaskNames{"BuildInnerProductCircuit", "ExecCircuit"}; + + MatrixMeasurement log(4, argv, subTaskNames, 1); + /** Step 1: Create the ABYParty object which defines the basis of all the operations which are happening. Operations performed are on the @@ -31,6 +48,7 @@ int32_t test_inner_product_circuit(e_role role, const std::string& address, uint ABYParty* party = new ABYParty(role, address, port, seclvl, bitlen, nthreads, mt_alg); + /** Step 2: Get to know all the sharing types available in the program. */ @@ -92,8 +110,10 @@ int32_t test_inner_product_circuit(e_role role, const std::string& address, uint problem by passing the shared objects and circuit object. Don't forget to type cast the circuit object to type of share */ + log.startSubTask("BuildInnerProductCircuit", 0); s_out = BuildInnerProductCircuit(s_x_vec, s_y_vec, num, (ArithmeticCircuit*) circ); + log.endSubTask("BuildInnerProductCircuit", 0); /** Step 8: Output the value of s_out (the computation result) to both parties @@ -104,7 +124,13 @@ int32_t test_inner_product_circuit(e_role role, const std::string& address, uint Step 9: Executing the circuit using the ABYParty object evaluate the problem. */ + log.startSubTask("ExecCircuit", 0); party->ExecCircuit(); + log.endSubTask("ExecCircuit", 0); + +#ifdef ABY_ENABLE_MATRIX + log.write_log(); +#endif /** Step 10: Type caste the plaintext output to 16 bit unsigned integer. diff --git a/src/examples/innerproduct/common/innerproduct.h b/src/examples/innerproduct/common/innerproduct.h index bea627b1..68847dae 100644 --- a/src/examples/innerproduct/common/innerproduct.h +++ b/src/examples/innerproduct/common/innerproduct.h @@ -19,10 +19,10 @@ #ifndef __INNERPRODUCT_H_ #define __INNERPRODUCT_H_ -#include "../../../abycore/circuit/booleancircuits.h" -#include "../../../abycore/circuit/arithmeticcircuits.h" -#include "../../../abycore/circuit/circuit.h" -#include "../../../abycore/aby/abyparty.h" +#include +#include +#include +#include #include #include diff --git a/src/examples/innerproduct/innerproduct_test.cpp b/src/examples/innerproduct/innerproduct_test.cpp index 6fe93a35..1df5edd2 100644 --- a/src/examples/innerproduct/innerproduct_test.cpp +++ b/src/examples/innerproduct/innerproduct_test.cpp @@ -20,7 +20,7 @@ #include #include //ABY Party class -#include "../../abycore/aby/abyparty.h" +#include #include "common/innerproduct.h" diff --git a/src/examples/innerproduct/run_matrix.sh b/src/examples/innerproduct/run_matrix.sh new file mode 100755 index 00000000..6d78a4aa --- /dev/null +++ b/src/examples/innerproduct/run_matrix.sh @@ -0,0 +1,27 @@ +#!/usr/bin/env bash + +set -euo pipefail + +# read the arguments without party id + +argc=$# +argv=($@) +values="" + +for (( j=1; j