Unverified Commit a4dbedba authored by Oleh Nikolaiev's avatar Oleh Nikolaiev Committed by GitHub

Merge branch 'develop' into readme-updates

parents 5e4870ba 61b4ac93
......@@ -46,6 +46,7 @@
#include "LevelDB.h"
#include "ServerInit.h"
#include "BLSCrypto.h"
#include "CryptoTools.h"
string *FqToString(libff::alt_bn128_Fq *_fq) {
......@@ -65,71 +66,6 @@ string *FqToString(libff::alt_bn128_Fq *_fq) {
return new string(arr);
}
int char2int(char _input) {
if (_input >= '0' && _input <= '9')
return _input - '0';
if (_input >= 'A' && _input <= 'F')
return _input - 'A' + 10;
if (_input >= 'a' && _input <= 'f')
return _input - 'a' + 10;
return -1;
}
vector<char> carray2Hex(const unsigned char *d, uint64_t _len) {
CHECK_STATE(d);
vector<char> _hexArray( 2 * _len + 1);
char hexval[16] = {'0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'a', 'b', 'c', 'd', 'e', 'f'};
for (uint64_t j = 0; j < _len; j++) {
_hexArray[j * 2] = hexval[((d[j] >> 4) & 0xF)];
_hexArray[j * 2 + 1] = hexval[(d[j]) & 0x0F];
}
_hexArray[_len * 2] = 0;
return _hexArray;
}
bool hex2carray(const char *_hex, uint64_t *_bin_len,
uint8_t *_bin, uint64_t _max_length) {
CHECK_STATE(_hex);
CHECK_STATE(_bin);
CHECK_STATE(_bin_len)
uint64_t len = strnlen(_hex, 2 * _max_length + 1);
CHECK_STATE(len != 2 * _max_length + 1);
CHECK_STATE(len <= 2 * _max_length);
if (len == 0 && len % 2 == 1)
return false;
*_bin_len = len / 2;
for (uint64_t i = 0; i < len / 2; i++) {
int high = char2int((char) _hex[i * 2]);
int low = char2int((char) _hex[i * 2 + 1]);
if (high < 0 || low < 0) {
return false;
}
_bin[i] = (unsigned char) (high * 16 + low);
}
return true;
}
bool sign_aes(const char *_encryptedKeyHex, const char *_hashHex, size_t _t, size_t _n, char *_sig) {
CHECK_STATE(_encryptedKeyHex);
......@@ -182,13 +118,11 @@ bool sign_aes(const char *_encryptedKeyHex, const char *_hashHex, size_t _t, siz
int errStatus = 0;
sgx_status_t status = SGX_SUCCESS;
status = trustedBlsSignMessage(eid, &errStatus, errMsg.data(), encryptedKey,
sz, xStrArg, yStrArg, signature);
HANDLE_TRUSTED_FUNCTION_ERROR(status, errStatus, errMsg.data());
string hint = BLSutils::ConvertToString(hash_with_hint.first.Y) + ":" + hash_with_hint.second;
......
......@@ -14,7 +14,7 @@
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file BLSCrypto.h
@author Stan Kladko
......@@ -37,13 +37,6 @@
EXTERNC bool bls_sign(const char* encryptedKeyHex, const char* hashHex, size_t t, size_t n, char* _sig);
EXTERNC int char2int(char _input);
EXTERNC std::vector<char> carray2Hex(const unsigned char *d, uint64_t _len);
EXTERNC bool hex2carray(const char * _hex, uint64_t *_bin_len,
uint8_t* _bin, uint64_t _max_length );
std::string encryptBLSKeyShare2Hex(int *errStatus, char *err_string, const char *_key);
#endif //SGXWALLET_BLSCRYPTO_H
......@@ -32,6 +32,7 @@
#include "sgxwallet.h"
#include "BLSCrypto.h"
#include "CryptoTools.h"
#include "ServerInit.h"
#include "SEKManager.h"
#include "BLSPrivateKeyShareSGX.h"
......@@ -122,13 +123,10 @@ string BLSPrivateKeyShareSGX::signWithHelperSGXstr(
BOOST_THROW_EXCEPTION(runtime_error("Null yStr"));
}
vector<char> errMsg(BUF_LEN, 0);
SAFE_CHAR_BUF(xStrArg, BUF_LEN)SAFE_CHAR_BUF(yStrArg, BUF_LEN)SAFE_CHAR_BUF(signature, BUF_LEN);
strncpy(xStrArg, xStr->c_str(), BUF_LEN);
strncpy(yStrArg, yStr->c_str(), BUF_LEN);
......
/*
Copyright (C) 2021-Present SKALE Labs
This file is part of sgxwallet.
sgxwallet is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published
by the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
sgxwallet is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file CryptoTools.cpp
@author Oleh Nikolaiev
@date 2021
*/
#include <vector>
#include "common.h"
#include "CryptoTools.h"
using std::vector;
int char2int(char _input) {
if (_input >= '0' && _input <= '9')
return _input - '0';
if (_input >= 'A' && _input <= 'F')
return _input - 'A' + 10;
if (_input >= 'a' && _input <= 'f')
return _input - 'a' + 10;
return -1;
}
vector<char> carray2Hex(const unsigned char *d, uint64_t _len) {
CHECK_STATE(d);
vector<char> _hexArray( 2 * _len + 1);
char hexval[16] = {'0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'a', 'b', 'c', 'd', 'e', 'f'};
for (uint64_t j = 0; j < _len; j++) {
_hexArray[j * 2] = hexval[((d[j] >> 4) & 0xF)];
_hexArray[j * 2 + 1] = hexval[(d[j]) & 0x0F];
}
_hexArray[_len * 2] = 0;
return _hexArray;
}
bool hex2carray(const char *_hex, uint64_t *_bin_len,
uint8_t *_bin, uint64_t _max_length) {
CHECK_STATE(_hex);
CHECK_STATE(_bin);
CHECK_STATE(_bin_len)
uint64_t len = strnlen(_hex, 2 * _max_length + 1);
CHECK_STATE(len != 2 * _max_length + 1);
CHECK_STATE(len <= 2 * _max_length);
if (len % 2 == 1)
return false;
*_bin_len = len / 2;
for (uint64_t i = 0; i < len / 2; i++) {
int high = char2int((char) _hex[i * 2]);
int low = char2int((char) _hex[i * 2 + 1]);
if (high < 0 || low < 0) {
return false;
}
_bin[i] = (unsigned char) (high * 16 + low);
}
return true;
}
\ No newline at end of file
/*
Copyright (C) 2021-Present SKALE Labs
This file is part of sgxwallet.
sgxwallet is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published
by the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
sgxwallet is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file CryptoTools.h
@author Oleh Nikolaiev
@date 2021
*/
#ifndef SGXWALLET_CRYPTOTOOLS_H
#define SGXWALLET_CRYPTOTOOLS_H
#ifdef __cplusplus
#define EXTERNC extern "C"
#else
#define EXTERNC
#endif
#include "stddef.h"
#include "stdint.h"
#include <string>
#include <vector>
EXTERNC int char2int(char _input);
EXTERNC std::vector<char> carray2Hex(const unsigned char *d, uint64_t _len);
EXTERNC bool hex2carray(const char * _hex, uint64_t *_bin_len,
uint8_t* _bin, uint64_t _max_length );
#endif // SGXWALLET_CRYPTOTOOLS_H
......@@ -32,7 +32,7 @@
#include "SGXException.h"
#include "SGXWalletServer.hpp"
#include "BLSCrypto.h"
#include "CryptoTools.h"
#include "SEKManager.h"
#include "DKGCrypto.h"
......@@ -448,7 +448,10 @@ bool createBLSShareV2(const string &blsKeyName, const char *s_shares, const char
vector<char> errMsg(BUF_LEN, 0);
int errStatus = 0;
uint64_t decKeyLen;SAFE_UINT8_BUF(encr_bls_key, BUF_LEN);SAFE_UINT8_BUF(encr_key, BUF_LEN);
uint64_t decKeyLen;
SAFE_UINT8_BUF(encr_bls_key, BUF_LEN)
SAFE_UINT8_BUF(encr_key, BUF_LEN)
if (!hex2carray(encryptedKeyHex, &decKeyLen, encr_key, BUF_LEN)) {
throw SGXException(CREATE_BLS_SHARE_INVALID_KEY_HEX, string(__FUNCTION__) + ":Invalid encryptedKeyHex");
}
......
......@@ -36,7 +36,7 @@
#include "secure_enclave/Verify.h"
#include "BLSCrypto.h"
#include "CryptoTools.h"
#include "SEKManager.h"
#include "ECDSACrypto.h"
......@@ -59,9 +59,11 @@ vector <string> genECDSAKey() {
sgx_status_t status = SGX_SUCCESS;
status = trustedGenerateEcdsaKey(eid, &errStatus,
errMsg.data(), encr_pr_key.data(), &enc_len,
pub_key_x.data(), pub_key_y.data());
int exportable = 0;
status = trustedGenerateEcdsaKey(eid, &errStatus, errMsg.data(),
&exportable, encr_pr_key.data(), &enc_len,
pub_key_x.data(), pub_key_y.data());
HANDLE_TRUSTED_FUNCTION_ERROR(status, errStatus,errMsg.data());
......
......@@ -72,8 +72,8 @@ bin_PROGRAMS = sgxwallet testw sgx_util
COMMON_SRC = SGXException.cpp ExitHandler.cpp zmq_src/ZMQClient.cpp zmq_src/RspMessage.cpp zmq_src/ReqMessage.cpp \
zmq_src/ZMQMessage.cpp zmq_src/ZMQServer.cpp \
InvalidStateException.cpp Exception.cpp InvalidArgumentException.cpp Log.cpp \
SGXWalletServer.cpp SGXRegistrationServer.cpp CSRManagerServer.cpp BLSCrypto.cpp \
InvalidStateException.cpp Exception.cpp InvalidArgumentException.cpp Log.cpp TECrypto.cpp \
SGXWalletServer.cpp SGXRegistrationServer.cpp CSRManagerServer.cpp BLSCrypto.cpp CryptoTools.cpp \
DKGCrypto.cpp ServerInit.cpp BLSPrivateKeyShareSGX.cpp LevelDB.cpp ServerDataChecker.cpp SEKManager.cpp \
third_party/intel/sgx_stub.c third_party/intel/sgx_detect_linux.c third_party/intel/create_enclave.c \
third_party/intel/oc_alloc.c ECDSAImpl.c TestUtils.cpp sgxwallet.c SGXInfoServer.cpp ECDSACrypto.cpp
......
......@@ -14,7 +14,7 @@
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file SEKManager.cpp
@author Stan Kladko
......@@ -33,7 +33,7 @@
#include "sgxwallet.h"
#include "SGXException.h"
#include "BLSCrypto.h"
#include "CryptoTools.h"
#include "LevelDB.h"
#include "ServerDataChecker.h"
......
......@@ -38,8 +38,9 @@
#include "SGXException.h"
#include "LevelDB.h"
#include "BLSCrypto.h"
#include "ECDSACrypto.h"
#include "DKGCrypto.h"
#include "ECDSACrypto.h"
#include "TECrypto.h"
#include "SGXWalletServer.h"
#include "SGXWalletServer.hpp"
......@@ -984,6 +985,30 @@ SGXWalletServer::createBLSPrivateKeyV2Impl(const string &_blsKeyName, const stri
RETURN_SUCCESS(result);
}
Json::Value SGXWalletServer::getDecryptionShareImpl(const std::string& blsKeyName, const std::string& publicDecryptionValue) {
spdlog::info("Entering {}", __FUNCTION__);
INIT_RESULT(result)
try {
if (!checkName(blsKeyName, "BLS_KEY")) {
throw SGXException(BLS_SIGN_INVALID_KS_NAME, string(__FUNCTION__) + ":Invalid BLSKey name");
}
if ( publicDecryptionValue.length() < 7 || publicDecryptionValue.length() > 78 * 4 ) {
throw SGXException(INVALID_DECRYPTION_VALUE_FORMAT, string(__FUNCTION__) + ":Invalid publicDecryptionValue format");
}
shared_ptr<string> encryptedKeyHex_ptr = readFromDb(blsKeyName);
vector<string> decryptionValueVector = calculateDecryptionShare(encryptedKeyHex_ptr->c_str(), publicDecryptionValue);
for (uint8_t i = 0; i < 4; ++i) {
result["decryptionShare"][i] = decryptionValueVector.at(i);
}
} HANDLE_SGX_EXCEPTION(result)
RETURN_SUCCESS(result)
}
Json::Value SGXWalletServer::generateDKGPoly(const string &_polyName, int _t) {
return generateDKGPolyImpl(_polyName, _t);
}
......@@ -1084,11 +1109,14 @@ SGXWalletServer::createBLSPrivateKeyV2(const string &blsKeyName, const string &e
return createBLSPrivateKeyV2Impl(blsKeyName, ethKeyName, polyName, SecretShare, t, n);
}
Json::Value SGXWalletServer::getDecryptionShare(const std::string& blsKeyName, const std::string& publicDecryptionValue) {
return getDecryptionShareImpl(blsKeyName, publicDecryptionValue);
}
shared_ptr <string> SGXWalletServer::readFromDb(const string &name, const string &prefix) {
auto dataStr = checkDataFromDb(prefix + name);
if (dataStr == nullptr) {
throw SGXException(KEY_SHARE_DOES_NOT_EXIST, string(__FUNCTION__) + ":Data with this name does not exist: "
+ prefix + name);
}
......@@ -1112,9 +1140,9 @@ void SGXWalletServer::writeKeyShare(const string &_keyShareName, const string &_
}
void SGXWalletServer::writeDataToDB(const string &name, const string &value) {
if (LevelDB::getLevelDb()->readString(name) != nullptr) {
throw SGXException(KEY_NAME_ALREADY_EXISTS, string(__FUNCTION__) + ":Name already exists" + name);
}
LevelDB::getLevelDb()->writeString(name, value);
}
......@@ -14,7 +14,7 @@
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file SGXWalletServer.h
@author Stan Kladko
......
......@@ -113,6 +113,8 @@ public:
virtual Json::Value createBLSPrivateKeyV2(const std::string& blsKeyName, const std::string& ethKeyName, const std::string& polyName, const std::string & SecretShare, int t, int n);
virtual Json::Value getDecryptionShare(const std::string& blsKeyName, const std::string& publicDecryptionValue);
static shared_ptr<string> readFromDb(const string &name, const string &prefix = "");
static shared_ptr <string> checkDataFromDb(const string &name, const string &prefix = "");
......@@ -171,6 +173,8 @@ public:
static Json::Value createBLSPrivateKeyV2Impl(const std::string& blsKeyName, const std::string& ethKeyName, const std::string& polyName, const std::string & SecretShare, int t, int n);
static Json::Value getDecryptionShareImpl(const std::string& KeyName, const std::string& publicDecryptionValue);
static void printDB();
static void initHttpServer();
......
/*
Copyright (C) 2021-Present SKALE Labs
This file is part of sgxwallet.
sgxwallet is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published
by the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
sgxwallet is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file TECrypto.cpp
@author Oleh Nikolaiev
@date 2021
*/
#include <memory>
#include "leveldb/db.h"
#include <jsonrpccpp/server/connectors/httpserver.h>
#include "threshold_encryption/threshold_encryption.h"
#include "sgxwallet_common.h"
#include "sgxwallet.h"
#include "SGXException.h"
#include "third_party/spdlog/spdlog.h"
#include "common.h"
#include "SGXWalletServer.h"
#include "TECrypto.h"
#include "CryptoTools.h"
#include <bls/BLSutils.h>
vector<string> calculateDecryptionShare(const string& encryptedKeyShare,
const string& publicDecryptionValue) {
size_t sz = 0;
SAFE_UINT8_BUF(encryptedKey, BUF_LEN);
bool result = hex2carray(encryptedKeyShare.data(), &sz, encryptedKey, BUF_LEN);
if (!result) {
BOOST_THROW_EXCEPTION(invalid_argument("Invalid hex encrypted key"));
}
SAFE_CHAR_BUF(decryptionShare, BUF_LEN)
vector<char> errMsg(BUF_LEN, 0);
int errStatus = 0;
sgx_status_t status = SGX_SUCCESS;
status = trustedGetDecryptionShare(eid, &errStatus, errMsg.data(), encryptedKey,
publicDecryptionValue.data(), sz, decryptionShare);
HANDLE_TRUSTED_FUNCTION_ERROR(status, errStatus, errMsg.data());
auto splitted_share = BLSutils::SplitString(std::make_shared<std::string>(decryptionShare), ":");
return *splitted_share;
}
\ No newline at end of file
/*
Copyright (C) 2021-Present SKALE Labs
This file is part of sgxwallet.
sgxwallet is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published
by the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
sgxwallet is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file TECrypto.h
@author Oleh Nikolaiev
@date 2021
*/
#ifndef SGXWALLET_TECRYPTO_H
#define SGXWALLET_TECRYPTO_H
#ifdef __cplusplus
#define EXTERNC extern "C"
#else
#define EXTERNC
#endif
#include "stddef.h"
#include "stdint.h"
#include <string>
#include <vector>
std::vector<std::string> calculateDecryptionShare(const std::string& encryptedKeyShare,
const std::string& publicDecryptionValue);
#endif // SGXWALLET_TECRYPTO_H
......@@ -14,7 +14,7 @@
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file TestUtils.cpp
@author Stan Kladko
......@@ -37,6 +37,7 @@
#include "BLSCrypto.h"
#include "ServerInit.h"
#include "DKGCrypto.h"
#include "CryptoTools.h"
#include "SGXException.h"
#include "LevelDB.h"
#include "SGXWalletServer.hpp"
......
......@@ -14,7 +14,7 @@
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file BLSEnclave.cpp
@author Stan Kladko
......@@ -62,6 +62,8 @@ class AbstractStubServer : public jsonrpc::AbstractServer<AbstractStubServer>
this->bindAndAddMethod(jsonrpc::Procedure("getSecretShareV2", jsonrpc::PARAMS_BY_NAME, jsonrpc::JSON_OBJECT, "polyName",jsonrpc::JSON_STRING,"publicKeys",jsonrpc::JSON_ARRAY, "n",jsonrpc::JSON_INTEGER,"t",jsonrpc::JSON_INTEGER, NULL), &AbstractStubServer::getSecretShareV2I);
this->bindAndAddMethod(jsonrpc::Procedure("dkgVerificationV2", jsonrpc::PARAMS_BY_NAME, jsonrpc::JSON_OBJECT, "publicShares",jsonrpc::JSON_STRING, "ethKeyName",jsonrpc::JSON_STRING, "secretShare",jsonrpc::JSON_STRING,"t",jsonrpc::JSON_INTEGER, "n",jsonrpc::JSON_INTEGER, "index",jsonrpc::JSON_INTEGER, NULL), &AbstractStubServer::dkgVerificationV2I);
this->bindAndAddMethod(jsonrpc::Procedure("createBLSPrivateKeyV2", jsonrpc::PARAMS_BY_NAME, jsonrpc::JSON_OBJECT, "blsKeyName",jsonrpc::JSON_STRING, "ethKeyName",jsonrpc::JSON_STRING, "polyName", jsonrpc::JSON_STRING, "secretShare",jsonrpc::JSON_STRING,"t", jsonrpc::JSON_INTEGER,"n",jsonrpc::JSON_INTEGER, NULL), &AbstractStubServer::createBLSPrivateKeyV2I);
this->bindAndAddMethod(jsonrpc::Procedure("getDecryptionShare", jsonrpc::PARAMS_BY_NAME, jsonrpc::JSON_OBJECT, "blsKeyName",jsonrpc::JSON_STRING,"publicDecryptionValue",jsonrpc::JSON_STRING, NULL), &AbstractStubServer::getDecryptionShareI);
}
inline virtual void importBLSKeyShareI(const Json::Value &request, Json::Value &response)
......@@ -161,6 +163,11 @@ class AbstractStubServer : public jsonrpc::AbstractServer<AbstractStubServer>
response = this->createBLSPrivateKeyV2(request["blsKeyName"].asString(), request["ethKeyName"].asString(), request["polyName"].asString(),request["secretShare"].asString(),request["t"].asInt(), request["n"].asInt());
}
inline virtual void getDecryptionShareI(const Json::Value &request, Json::Value &response)
{
response = this->getDecryptionShare(request["blsKeyName"].asString(), request["publicDecryptionValue"].asString());
}
virtual Json::Value importBLSKeyShare(const std::string& keyShare, const std::string& keyShareName) = 0;
virtual Json::Value blsSignMessageHash(const std::string& keyShareName, const std::string& messageHash, int t, int n ) = 0;
virtual Json::Value importECDSAKey(const std::string& keyShare, const std::string& keyShareName) = 0;
......@@ -186,6 +193,8 @@ class AbstractStubServer : public jsonrpc::AbstractServer<AbstractStubServer>
virtual Json::Value getSecretShareV2(const std::string& polyName, const Json::Value& publicKeys, int t, int n) = 0;
virtual Json::Value dkgVerificationV2( const std::string& publicShares, const std::string& ethKeyName, const std::string& SecretShare, int t, int n, int index) = 0;
virtual Json::Value createBLSPrivateKeyV2(const std::string& blsKeyName, const std::string& ethKeyName, const std::string& polyName, const std::string & SecretShare, int t, int n) = 0;
virtual Json::Value getDecryptionShare(const std::string& KeyName, const std::string& publicDecryptionValue) = 0;
};
#endif //JSONRPC_CPP_STUB_ABSTRACTSTUBSERVER_H_
......@@ -98,8 +98,6 @@ inline int getValue() { //Note: this value is in KB!
return result;
}
#define CHECK_STATE(_EXPRESSION_) \
if (!(_EXPRESSION_)) { \
auto __msg__ = std::string("State check failed::") + #_EXPRESSION_ + " " + std::string(__FILE__) + ":" + std::to_string(__LINE__); \
......@@ -136,8 +134,6 @@ BOOST_THROW_EXCEPTION(runtime_error(__ERR_STRING__)); \
// Copy from libconsensus
inline string exec( const char* cmd ) {
CHECK_STATE( cmd );
std::array< char, 128 > buffer;
......@@ -162,5 +158,4 @@ extern uint64_t initTime;
#define WRITE_LOCK(__X__) std::unique_lock<std::shared_timed_mutex> __LOCK__(__X__);
#endif //SGXWALLET_COMMON_H
......@@ -2,6 +2,25 @@
# Building SGX wallet from source
## Build and install Intel SGX SDK
We are currently using SGX SDK version 2.13.
Below is a sequence of commands that builds SDK and installs it into /opt/intel directory.
```bash
git clone -b sgx_2.13 --depth 1 https://github.com/intel/linux-sgx
cd linux-sgx
make preparation
sudo make sdk_install_pkg_no_mitigation
cd /opt/intel
sudo sh -c 'echo yes | /linux-sgx/linux/installer/bin/sgx_linux_x64_sdk_*.bin
sudo make psw_install_pkg
sudo cp /linux-sgx/linux/installer/bin/sgx_linux_x64_psw*.bin .
sudo ./sgx_linux_x64_psw*.bin --no-start-aesm
```
## Clone this repository and its submodules
`git clone --recurse-submodules https://github.com/skalenetwork/sgxwallet.git`
......@@ -23,7 +42,7 @@ cd scripts; ./build_deps.py; cd ..
## Set SGX environment variables
```bash
source sgx-sdk-build/sgxsdk/environment
source /opt/intel/sgxsdk/environment
```
## Configure and build sgxwallet
......@@ -40,6 +59,7 @@ make
Note: to run in simulation mode, add --enable-sgx-simulation flag when you run configure.
```bash
./autoconf.bash
./configure --enable-sgx-simulation
make
```
......
......@@ -66,6 +66,7 @@ If operating with a firewall, please make sure these ports are open so clients a
- \-n Launch SGXWalletServer using http (not https)
- \-b Restore from back up (you will need to enter backup key)
- \-y Do not ask user to acknowledge receipt of backup key
- \-e Check whether one who is trying to access the key is the same user who created it (Ownership is checked via SSL certificate for now. Deleting old SSL certificates and trying to access the keys created before will cause the error!)
- \-T Generate test keys
### Healthcheck
......
......@@ -14,7 +14,7 @@
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file DKGUtils.h
@author Stan Kladko
......@@ -45,14 +45,12 @@ EXTERNC void calc_secret_shares(const char* decrypted_coeffs, char * secret_shar
EXTERNC int calc_secret_share(const char* decrypted_coeffs, char * s_share,
unsigned _t, unsigned _n, unsigned ind);
EXTERNC int calc_public_shares(const char* decrypted_coeffs, char * public_shares,
unsigned _t);
EXTERNC int calc_public_shares(const char* decrypted_coeffs, char * public_shares, unsigned _t);
EXTERNC int Verification ( char * public_shares, mpz_t decr_secret_share, int _t, int ind);
EXTERNC int calc_bls_public_key(char* skey, char* pub_key);
EXTERNC int calc_secret_shareG2(const char* s_share, char * s_shareG2);
#endif
......@@ -84,7 +84,7 @@ CLEANFILES+= secure_enclave_t.c secure_enclave_t.h
secure_enclave_SOURCES = secure_enclave_t.c secure_enclave_t.h \
secure_enclave.c \
Curves.c NumberTheory.c Point.c Signature.c DHDkg.c AESUtils.c \
DKGUtils.cpp EnclaveCommon.cpp DomainParameters.cpp ../third_party/SCIPR/libff/algebra/curves/alt_bn128/alt_bn128_init.cpp \
DKGUtils.cpp TEUtils.cpp EnclaveCommon.cpp DomainParameters.cpp ../third_party/SCIPR/libff/algebra/curves/alt_bn128/alt_bn128_init.cpp \
../third_party/SCIPR/libff/algebra/curves/alt_bn128/alt_bn128_g2.cpp \
../third_party/SCIPR/libff/algebra/curves/alt_bn128/alt_bn128_g1.cpp $(ENCLAVE_KEY) $(ENCLAVE_CONFIG)
......@@ -113,7 +113,7 @@ secure_enclave_LDADD = @SGX_ENCLAVE_LDADD@
## --startgroup and --endgroup flags. (This would be where you'd add
## SGXSSL libraries, and your trusted c++ library
SGX_EXTRA_TLIBS=-lsgx_tgmp -lsgx_tservice -lsgx_urts -lsgx_tcxx
SGX_EXTRA_TLIBS=-lsgx_tgmp -lsgx_tservice -lsgx_urts -lsgx_tcxx
......
This diff is collapsed.
/*
Copyright (C) 2021-Present SKALE Labs
This file is part of sgxwallet.
sgxwallet is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published
by the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
sgxwallet is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file TEUtils.cpp
@author Oleh Nikolaiev
@date 2021
*/
#ifndef SGXWALLET_DKGUTILS_H
#define SGXWALLET_DKGUTILS_H
#ifdef __cplusplus
#define EXTERNC extern "C"
#else
#define EXTERNC
#endif
#ifdef USER_SPACE
#include <gmp.h>
#else
#include <../tgmp-build/include/sgx_tgmp.h>
#endif
#include <cstdio>
#include <stdio.h>
#include <string>
#include <vector>
#include <../SCIPR/libff/algebra/curves/alt_bn128/alt_bn128_pp.hpp>
#include <../SCIPR/libff/algebra/fields/fp.hpp>
#include <../SCIPR/libff/algebra/curves/alt_bn128/alt_bn128_g2.hpp>
#include "EnclaveConstants.h"
#include "EnclaveCommon.h"
#include "TEUtils.h"
template<class T>
std::string fieldElementToString(const T &field_elem, int base = 10) {
std::string ret;
mpz_t t;
mpz_init(t);
try {
field_elem.as_bigint().to_mpz(t);
SAFE_CHAR_BUF(arr, BUF_LEN);
char *tmp = mpz_get_str(arr, base, t);
ret = std::string(tmp);
goto clean;
} catch (std::exception &e) {
LOG_ERROR(e.what());
goto clean;
} catch (...) {
LOG_ERROR("Unknown throwable");
goto clean;
}
clean:
mpz_clear(t);
return ret;
}
std::string ConvertG2ElementToString(const libff::alt_bn128_G2 &elem, int base = 10, const std::string &delim = ":") {
std::string result = "";
try {
result += fieldElementToString(elem.X.c0);
result += delim;
result += fieldElementToString(elem.X.c1);
result += delim;
result += fieldElementToString(elem.Y.c0);
result += delim;
result += fieldElementToString(elem.Y.c1);
return result;
} catch (std::exception &e) {
LOG_ERROR(e.what());
return result;
} catch (...) {
LOG_ERROR("Unknown throwable");
return result;
}
return result;
}
std::vector <libff::alt_bn128_Fq> SplitStringToFq(const char *coords, const char symbol) {
std::vector <libff::alt_bn128_Fq > result;
std::string str(coords);
std::string delim;
CHECK_ARG_CLEAN(coords);
try {
delim.push_back(symbol);
size_t prev = 0, pos = 0;
do {
pos = str.find(delim, prev);
if (pos == std::string::npos) pos = str.length();
std::string token = str.substr(prev, pos - prev);
if (!token.empty()) {
libff::alt_bn128_Fq coeff(token.c_str());
result.push_back(coeff);
}
prev = pos + delim.length();
} while (pos < str.length() && prev < str.length());
return result;
} catch (std::exception &e) {
LOG_ERROR(e.what());
return result;
} catch (...) {
LOG_ERROR("Unknown throwable");
return result;
}
clean:
return result;
}
EXTERNC int getDecryptionShare(char* skey_hex, char* decryptionValue, char* decryption_share) {
mpz_t skey;
mpz_init(skey);
int ret = 1;
CHECK_ARG_CLEAN(skey_hex);
CHECK_ARG_CLEAN(decryptionValue);
CHECK_ARG_CLEAN(decryption_share);
try {
if (mpz_set_str(skey, skey_hex, 16) == -1) {
mpz_clear(skey);
return 1;
}
char skey_dec[mpz_sizeinbase(skey, 10) + 2];
mpz_get_str(skey_dec, 10, skey);
libff::alt_bn128_Fr bls_skey(skey_dec);
auto splitted_decryption_value = SplitStringToFq(decryptionValue, ':');
libff::alt_bn128_G2 decryption_value;
decryption_value.Z = libff::alt_bn128_Fq2::one();
decryption_value.X.c0 = splitted_decryption_value[0];
decryption_value.X.c1 = splitted_decryption_value[1];
decryption_value.Y.c0 = splitted_decryption_value[2];
decryption_value.Y.c1 = splitted_decryption_value[3];
if ( !decryption_value.is_well_formed() ) {
mpz_clear(skey);
return 1;
}
libff::alt_bn128_G2 decryption_share_point = bls_skey * decryption_value;
decryption_share_point.to_affine_coordinates();
std::string result = ConvertG2ElementToString(decryption_share_point);
strncpy(decryption_share, result.c_str(), result.length());
mpz_clear(skey);
return 0;
} catch (std::exception &e) {
LOG_ERROR(e.what());
return 1;
} catch (...) {
LOG_ERROR("Unknown throwable");
return 1;
}
clean:
mpz_clear(skey);
return ret;
}
#endif
/*
Copyright (C) 2021-Present SKALE Labs
This file is part of sgxwallet.
sgxwallet is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published
by the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
sgxwallet is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file TEUtils.h
@author Oleh Nikolaiev
@date 2021
*/
#ifndef SGXWALLET_DKGUTILS_H
#define SGXWALLET_DKGUTILS_H
#ifdef __cplusplus
#define EXTERNC extern "C"
#else
#define EXTERNC
#endif
#ifdef USER_SPACE
#include <gmp.h>
#else
#include <../tgmp-build/include/sgx_tgmp.h>
#endif
EXTERNC int getDecryptionShare(char* secret, char* decryptionValue, char* decryption_share);
#endif
......@@ -54,6 +54,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include "Curves.h"
#include "DHDkg.h"
#include "AESUtils.h"
#include "TEUtils.h"
#include "EnclaveConstants.h"
#include "EnclaveCommon.h"
......@@ -357,7 +358,7 @@ void trustedSetSEKBackup(int *errStatus, char *errString,
LOG_INFO("SGX call completed");
}
void trustedGenerateEcdsaKey(int *errStatus, char *errString,
void trustedGenerateEcdsaKey(int *errStatus, char *errString, int *is_exportable,
uint8_t *encryptedPrivateKey, uint64_t *enc_len, char *pub_key_x, char *pub_key_y) {
LOG_INFO(__FUNCTION__);
INIT_ERROR_STATE
......@@ -408,8 +409,15 @@ void trustedGenerateEcdsaKey(int *errStatus, char *errString,
strncpy(skey_str + n_zeroes, arr_skey_str, 65 - n_zeroes);
snprintf(errString, BUF_LEN, "skey len is %d\n", (int) strlen(skey_str));
int status = AES_encrypt((char *) skey_str, encryptedPrivateKey, BUF_LEN,
int status = -1;
if ( *is_exportable ) {
status = AES_encrypt((char *) skey_str, encryptedPrivateKey, BUF_LEN,
ECDSA, EXPORTABLE, enc_len);
} else {
status = AES_encrypt((char *) skey_str, encryptedPrivateKey, BUF_LEN,
ECDSA, NON_EXPORTABLE, enc_len);
}
CHECK_STATUS("ecdsa private key encryption failed");
uint8_t type = 0;
......@@ -453,7 +461,6 @@ void trustedGetPublicEcdsaKey(int *errStatus, char *errString,
CHECK_STATUS2("AES_decrypt failed with status %d");
skey[enc_len - SGX_AESGCM_MAC_SIZE - SGX_AESGCM_IV_SIZE] = '\0';
strncpy(errString, skey, 1024);
status = mpz_set_str(privateKeyMpz, skey, ECDSA_SKEY_BASE);
......@@ -609,8 +616,13 @@ void trustedDecryptKey(int *errStatus, char *errString, uint8_t *encryptedPrivat
&type, &exportable);
if (exportable != EXPORTABLE) {
while (*key != '\0') {
*key++ = '0';
}
*errStatus = -11;
snprintf(errString, BUF_LEN, "Key is not exportable");
LOG_ERROR(errString);
goto clean;
}
if (status != 0) {
......@@ -855,7 +867,9 @@ void trustedGetEncryptedSecretShare(int *errStatus, char *errString,
SAFE_CHAR_BUF(pub_key_x, BUF_LEN);SAFE_CHAR_BUF(pub_key_y, BUF_LEN);
trustedGenerateEcdsaKey(&status, errString, encrypted_skey, &enc_len, pub_key_x, pub_key_y);
int is_exportable = 1;
trustedGenerateEcdsaKey(&status, errString, &is_exportable, encrypted_skey, &enc_len, pub_key_x, pub_key_y);
CHECK_STATUS("trustedGenerateEcdsaKey failed");
......@@ -929,7 +943,9 @@ void trustedGetEncryptedSecretShareV2(int *errStatus, char *errString,
SAFE_CHAR_BUF(pub_key_x, BUF_LEN);
SAFE_CHAR_BUF(pub_key_y, BUF_LEN);
trustedGenerateEcdsaKey(&status, errString, encrypted_skey, &enc_len, pub_key_x, pub_key_y);
int is_exportable = 1;
trustedGenerateEcdsaKey(&status, errString, &is_exportable, encrypted_skey, &enc_len, pub_key_x, pub_key_y);
CHECK_STATUS("trustedGenerateEcdsaKey failed");
......@@ -1363,3 +1379,35 @@ trustedGetBlsPubKey(int *errStatus, char *errString, uint8_t *encryptedPrivateKe
clean:
;
}
void trustedGetDecryptionShare( int *errStatus, char* errString, uint8_t* encryptedPrivateKey,
const char* public_decryption_value, uint64_t key_len,
char* decryption_share ) {
LOG_DEBUG(__FUNCTION__);
INIT_ERROR_STATE
CHECK_STATE(decryption_share);
CHECK_STATE(encryptedPrivateKey);
SAFE_CHAR_BUF(skey_hex, BUF_LEN);
uint8_t type = 0;
uint8_t exportable = 0;
int status = AES_decrypt(encryptedPrivateKey, key_len, skey_hex, BUF_LEN,
&type, &exportable);
CHECK_STATUS2("AES decrypt failed %d");
skey_hex[ECDSA_SKEY_LEN - 1] = 0;
status = getDecryptionShare(skey_hex, public_decryption_value, decryption_share);
CHECK_STATUS("could not calculate decryption share");
SET_SUCCESS
clean:
;
}
......@@ -35,6 +35,7 @@ enclave {
public void trustedGenerateEcdsaKey (
[out] int *errStatus,
[out, count = SMALL_BUF_SIZE] char* err_string,
[in, count = 1] int *is_exportable,
[out, count = SMALL_BUF_SIZE] uint8_t* encrypted_key,
[out] uint64_t *enc_len,
[out, count = SMALL_BUF_SIZE] char * pub_key_x,
......@@ -174,10 +175,18 @@ enclave {
public void trustedGetBlsPubKey(
[out]int *errStatus,
[out, count = SMALL_BUF_SIZE] char* err_string,
[out, count = SMALL_BUF_SIZE] char* err_string,
[in, count = SMALL_BUF_SIZE] uint8_t* encrypted_key,
uint64_t key_len,
[out, count = 320] char* bls_pub_key);
public void trustedGetDecryptionShare(
[out]int *errStatus,
[out, count = SMALL_BUF_SIZE] char* err_string,
[in, count = SMALL_BUF_SIZE] uint8_t* encrypted_key,
[in, count = 320] const char* public_decryption_value,
uint64_t key_len,
[out, count = 320] char* decrption_share);
};
untrusted {
......
......@@ -101,7 +101,7 @@ int main(int argc, char *argv[]) {
bool checkClientCertOption = true;
bool autoSignClientCertOption = false;
bool generateTestKeys = false;
bool checkKeyOwnership = true;
bool checkKeyOwnership = false;
std::signal(SIGABRT, SGXWallet::signalHandler);
......
......@@ -184,6 +184,7 @@ extern bool autoconfirm;
#define SGX_SERVER_FAILED_TO_START -111
#define CORRUPT_DATABASE -112
#define INVALID_SEK -113
#define INVALID_DECRYPTION_VALUE_FORMAT -114
#define SGX_ENCLAVE_ERROR -666
......
......@@ -214,6 +214,19 @@ class StubClient : public jsonrpc::Client
throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString());
}
Json::Value getDecryptionShare(const std::string& blsKeyName, const std::string& publicDecryptionValue)
{
Json::Value p;
p["blsKeyName"] = blsKeyName;
p["publicDecryptionValue"] = publicDecryptionValue;
Json::Value result = this->CallMethod("getDecryptionShare",p);
if (result.isObject())
return result;
else
throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString());
}
Json::Value calculateAllBLSPublicKeys(const Json::Value& publicShares, int t, int n)
{
Json::Value p;
......
......@@ -14,7 +14,7 @@
GNU Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
along with sgxwallet. If not, see <https://www.gnu.org/licenses/>.
@file testw.cpp
@author Stan Kladko
......@@ -37,6 +37,7 @@
#include <sgx_tcrypto.h>
#include "BLSCrypto.h"
#include "CryptoTools.h"
#include "ServerInit.h"
#include "DKGCrypto.h"
#include "SGXException.h"
......@@ -73,7 +74,7 @@ public:
TestFixture() {
TestUtils::resetDB();
setOptions(L_INFO, false, true);
initAll(L_INFO, false, false, true, false, false);
initAll(L_INFO, false, false, true, false, true);
}
~TestFixture() {
......@@ -114,7 +115,7 @@ class TestFixtureNoResetFromBackup {
public:
TestFixtureNoResetFromBackup() {
setFullOptions(L_INFO, false, true, true);
initAll(L_INFO, false, false, true, false, false);
initAll(L_INFO, false, false, true, false, true);
}
~TestFixtureNoResetFromBackup() {
......@@ -128,7 +129,7 @@ class TestFixtureNoReset {
public:
TestFixtureNoReset() {
setOptions(L_INFO, false, true);
initAll(L_INFO, false, false, true, false, false);
initAll(L_INFO, false, false, true, false, true);
}
~TestFixtureNoReset() {
......@@ -145,8 +146,9 @@ TEST_CASE_METHOD(TestFixture, "ECDSA AES keygen and signature test", "[ecdsa-aes
vector<char> pubKeyY(BUF_LEN, 0);
uint64_t encLen = 0;
int exportable = 0;
PRINT_SRC_LINE
auto status = trustedGenerateEcdsaKey(eid, &errStatus, errMsg.data(), encrPrivKey.data(), &encLen,
auto status = trustedGenerateEcdsaKey(eid, &errStatus, errMsg.data(), &exportable, encrPrivKey.data(), &encLen,
pubKeyX.data(),
pubKeyY.data());
REQUIRE(status == SGX_SUCCESS);
......@@ -176,8 +178,9 @@ TEST_CASE_METHOD(TestFixture, "ECDSA AES key gen", "[ecdsa-aes-key-gen]") {
vector<char> pubKeyX(BUF_LEN, 0);
vector<char> pubKeyY(BUF_LEN, 0);
uint64_t encLen = 0;
int exportable = 0;
PRINT_SRC_LINE
auto status = trustedGenerateEcdsaKey(eid, &errStatus, errMsg.data(), encrPrivKey.data(), &encLen,
auto status = trustedGenerateEcdsaKey(eid, &errStatus, errMsg.data(), &exportable, encrPrivKey.data(), &encLen,
pubKeyX.data(),
pubKeyY.data());
......@@ -193,9 +196,10 @@ TEST_CASE_METHOD(TestFixture, "ECDSA AES get public key", "[ecdsa-aes-get-pub-ke
vector<char> pubKeyY(BUF_LEN, 0);
uint64_t encLen = 0;
int exportable = 0;
PRINT_SRC_LINE
auto status = trustedGenerateEcdsaKey(eid, &errStatus, errMsg.data(), encPrivKey.data(), &encLen, pubKeyX.data(),
auto status = trustedGenerateEcdsaKey(eid, &errStatus, errMsg.data(), &exportable, encPrivKey.data(), &encLen, pubKeyX.data(),
pubKeyY.data());
REQUIRE(status == SGX_SUCCESS);
......@@ -1119,6 +1123,56 @@ TEST_CASE_METHOD(TestFixture, "AES encrypt/decrypt", "[aes-encrypt-decrypt]") {
sleep(3);
}
TEST_CASE_METHOD(TestFixture, "Exportable / non-exportable keys", "[exportable-nonexportable-keys]") {
int errStatus = 0;
vector<char> errMsg(BUF_LEN, 0);
vector <uint8_t> encPrivKey(BUF_LEN, 0);
vector<char> pubKeyX(BUF_LEN, 0);
vector<char> pubKeyY(BUF_LEN, 0);
uint64_t encLen = 0;
int exportable = 0;
auto status = trustedGenerateEcdsaKey(eid, &errStatus, errMsg.data(), &exportable, encPrivKey.data(), &encLen, pubKeyX.data(),
pubKeyY.data());
vector<char> decrypted_key(BUF_LEN, 0);
status = trustedDecryptKey(eid, &errStatus, errMsg.data(), encPrivKey.data(), encLen, decrypted_key.data());
REQUIRE( errStatus == -11 );
exportable = 1;
encPrivKey.clear();
errMsg.clear();
pubKeyX.clear();
pubKeyY.clear();
status = trustedGenerateEcdsaKey(eid, &errStatus, errMsg.data(), &exportable, encPrivKey.data(), &encLen, pubKeyX.data(),
pubKeyY.data());
decrypted_key.clear();
status = trustedDecryptKey(eid, &errStatus, errMsg.data(), encPrivKey.data(), encLen, decrypted_key.data());
REQUIRE( errStatus == 0 );
REQUIRE( status == SGX_SUCCESS );
string key = SAMPLE_AES_KEY;
vector <uint8_t> encrypted_key(BUF_LEN, 0);
status = trustedEncryptKey(eid, &errStatus, errMsg.data(), key.c_str(), encrypted_key.data(), &encLen);
REQUIRE(status == 0);
REQUIRE(errStatus == 0);
vector<char> decr_key(BUF_LEN, 0);
PRINT_SRC_LINE
status = trustedDecryptKey(eid, &errStatus, errMsg.data(), encrypted_key.data(), encLen, decr_key.data());
REQUIRE(status == 0);
REQUIRE(key.compare(decr_key.data()) == 0);
REQUIRE(errStatus == 0);
sleep(3);
}
TEST_CASE_METHOD(TestFixture, "Many threads ecdsa dkg v2 bls", "[many-threads-crypto-v2]") {
vector <thread> threads;
int num_threads = 4;
......@@ -1182,8 +1236,65 @@ TEST_CASE_METHOD(TestFixtureNoReset, "Second run", "[second-run]") {
}
}
TEST_CASE_METHOD(TestFixtureZMQSign, "ZMQ-ecdsa", "[zmq-ecdsa]") {
TEST_CASE_METHOD(TestFixture, "Test decryption share for threshold encryption", "[te-decryption-share]") {
HttpClient client(RPC_ENDPOINT);
StubClient c(client, JSONRPC_CLIENT_V2);
std::string key_str = "0xe632f7fde2c90a073ec43eaa90dca7b82476bf28815450a11191484934b9c3f";
std::string name = "BLS_KEY:SCHAIN_ID:123456789:NODE_ID:0:DKG_ID:0";
c.importBLSKeyShare(key_str, name);
// the same key writtn in decimal
libff::alt_bn128_Fr key = libff::alt_bn128_Fr(
"6507625568967977077291849236396320012317305261598035438182864059942098934847");
libff::alt_bn128_G2 decryption_value = libff::alt_bn128_G2::random_element();
decryption_value.to_affine_coordinates();
auto decrytion_value_str = convertG2ToString( decryption_value, ':' );
auto decryption_share = c.getDecryptionShare( name, decrytion_value_str )["decryptionShare"];
libff::alt_bn128_G2 share;
share.Z = libff::alt_bn128_Fq2::one();
share.X.c0 = libff::alt_bn128_Fq( decryption_share[0].asCString() );
share.X.c1 = libff::alt_bn128_Fq( decryption_share[1].asCString() );
share.Y.c0 = libff::alt_bn128_Fq( decryption_share[2].asCString() );
share.Y.c1 = libff::alt_bn128_Fq( decryption_share[3].asCString() );
REQUIRE( share == key * decryption_value );
}
TEST_CASE_METHOD(TestFixture, "Test decryption share for threshold encryption via zmq", "[te-decryption-share-zmq]") {
auto client = make_shared<ZMQClient>(ZMQ_IP, ZMQ_PORT, true, "./sgx_data/cert_data/rootCA.pem",
"./sgx_data/cert_data/rootCA.key");
std::string key_str = "0xe632f7fde2c90a073ec43eaa90dca7b82476bf28815450a11191484934b9c3f";
std::string name = "BLS_KEY:SCHAIN_ID:123456789:NODE_ID:0:DKG_ID:0";
client->importBLSKeyShare(key_str, name);
// the same key writtn in decimal
libff::alt_bn128_Fr key = libff::alt_bn128_Fr(
"6507625568967977077291849236396320012317305261598035438182864059942098934847");
libff::alt_bn128_G2 decryption_value = libff::alt_bn128_G2::random_element();
decryption_value.to_affine_coordinates();
auto decrytion_value_str = convertG2ToString( decryption_value, ':' );
auto decryption_share = client->getDecryptionShare( name, decrytion_value_str );
libff::alt_bn128_G2 share;
share.Z = libff::alt_bn128_Fq2::one();
share.X.c0 = libff::alt_bn128_Fq( decryption_share[0].asCString() );
share.X.c1 = libff::alt_bn128_Fq( decryption_share[1].asCString() );
share.Y.c0 = libff::alt_bn128_Fq( decryption_share[2].asCString() );
share.Y.c1 = libff::alt_bn128_Fq( decryption_share[3].asCString() );
REQUIRE( share == key * decryption_value );
}
TEST_CASE_METHOD(TestFixtureZMQSign, "ZMQ-ecdsa", "[zmq-ecdsa]") {
HttpClient htp(RPC_ENDPOINT);
StubClient c(htp, JSONRPC_CLIENT_V2);
......
......@@ -55,14 +55,16 @@ testList = [ "[zmq-ecdsa]",
"[dkg-api-v2]",
"[dkg-api-v2-zmq]",
"[dkg-bls]",
"[dkgzmqbls]",
"[dkg-bls-v2]",
"[dkg-poly-exists]",
"[dkg-poly-exists-zmq]",
"[dkg-aes-pub-shares]",
"[aes-encrypt-decrypt]",
"[exportable-nonexportable-keys]",
"[aes-dkg-v2]",
"[aes-dkg-v2-zmq]"
"[aes-dkg-v2-zmq]",
"[te-decryption-share]",
"[te-decryption-share-zmq]"
]
......
......@@ -26,12 +26,14 @@
#include "ReqMessage.h"
#include "third_party/spdlog/spdlog.h"
Json::Value ECDSASignReqMessage::process() {
auto base = getInt64Rapid("base");
auto keyName = getStringRapid("keyName");
auto hash = getStringRapid("messageHash");
if (checkKeyOwnership && !isKeyByOwner(keyName, getStringRapid("cert"))) {
spdlog::error("Cert {} try to access key {} which does not belong to it", getStringRapid("cert"), keyName);
throw std::invalid_argument("Only owner of the key can access it");
}
auto result = SGXWalletServer::ecdsaSignMessageHashImpl(base, keyName, hash);
......@@ -45,6 +47,7 @@ Json::Value BLSSignReqMessage::process() {
auto t = getInt64Rapid("t");
auto n = getInt64Rapid("n");
if (checkKeyOwnership && !isKeyByOwner(keyName, getStringRapid("cert"))) {
spdlog::error("Cert {} try to access key {} which does not belong to it", getStringRapid("cert"), keyName);
throw std::invalid_argument("Only owner of the key can access it");
}
auto result = SGXWalletServer::blsSignMessageHashImpl(keyName, hash, t, n);
......@@ -57,6 +60,7 @@ Json::Value importBLSReqMessage::process() {
auto keyShare = getStringRapid("keyShare");
auto result = SGXWalletServer::importBLSKeyShareImpl(keyShare, keyName);
if (checkKeyOwnership && result["status"] == 0) {
spdlog::info("Cert {} creates key {}", getStringRapid("cert"), keyName);
auto cert = getStringRapid("cert");
addKeyByOwner(keyName, cert);
}
......@@ -70,6 +74,7 @@ Json::Value importECDSAReqMessage::process() {
auto result = SGXWalletServer::importECDSAKeyImpl(key, keyName);
if (checkKeyOwnership && result["status"] == 0) {
auto cert = getStringRapid("cert");
spdlog::info("Cert {} creates key {}", cert, keyName);
addKeyByOwner(keyName, cert);
}
result["type"] = ZMQMessage::IMPORT_ECDSA_RSP;
......@@ -81,6 +86,7 @@ Json::Value generateECDSAReqMessage::process() {
string keyName = result["keyName"].asString();
if (checkKeyOwnership && result["status"] == 0) {
auto cert = getStringRapid("cert");
spdlog::info("Cert {} creates key {}", cert, keyName);
addKeyByOwner(keyName, cert);
}
result["type"] = ZMQMessage::GENERATE_ECDSA_RSP;
......@@ -90,6 +96,7 @@ Json::Value generateECDSAReqMessage::process() {
Json::Value getPublicECDSAReqMessage::process() {
auto keyName = getStringRapid("keyName");
if (checkKeyOwnership && !isKeyByOwner(keyName, getStringRapid("cert"))) {
spdlog::error("Cert {} try to access key {} which does not belong to it", getStringRapid("cert"), keyName);
throw std::invalid_argument("Only owner of the key can access it");
}
auto result = SGXWalletServer::getPublicECDSAKeyImpl(keyName);
......@@ -103,6 +110,7 @@ Json::Value generateDKGPolyReqMessage::process() {
auto result = SGXWalletServer::generateDKGPolyImpl(polyName, t);
if (checkKeyOwnership && result["status"] == 0) {
auto cert = getStringRapid("cert");
spdlog::info("Cert {} creates key {}", cert, polyName);
addKeyByOwner(polyName, cert);
}
result["type"] = ZMQMessage::GENERATE_DKG_POLY_RSP;
......@@ -112,6 +120,7 @@ Json::Value generateDKGPolyReqMessage::process() {
Json::Value getVerificationVectorReqMessage::process() {
auto polyName = getStringRapid("polyName");
if (checkKeyOwnership && !isKeyByOwner(polyName, getStringRapid("cert"))) {
spdlog::error("Cert {} try to access key {} which does not belong to it", getStringRapid("cert"), polyName);
throw std::invalid_argument("Only owner of the key can access it");
}
auto t = getInt64Rapid("t");
......@@ -126,6 +135,7 @@ Json::Value getSecretShareReqMessage::process() {
auto n = getInt64Rapid("n");
auto pubKeys = getJsonValueRapid("publicKeys");
if (checkKeyOwnership && !isKeyByOwner(polyName, getStringRapid("cert"))) {
spdlog::error("Cert {} try to access key {} which does not belong to it", getStringRapid("cert"), polyName);
throw std::invalid_argument("Only owner of the key can access it");
}
auto result = SGXWalletServer::getSecretShareV2Impl(polyName, pubKeys, t, n);
......@@ -141,6 +151,7 @@ Json::Value dkgVerificationReqMessage::process() {
auto pubShares = getStringRapid("publicShares");
auto secretShare = getStringRapid("secretShare");
if (checkKeyOwnership && !isKeyByOwner(ethKeyName, getStringRapid("cert"))) {
spdlog::error("Cert {} try to access key {} which does not belong to it", getStringRapid("cert"), ethKeyName);
throw std::invalid_argument("Only owner of the key can access it");
}
auto result = SGXWalletServer::dkgVerificationV2Impl(pubShares, ethKeyName, secretShare, t, n, idx);
......@@ -156,11 +167,14 @@ Json::Value createBLSPrivateKeyReqMessage::process() {
auto t = getInt64Rapid("t");
auto n = getInt64Rapid("n");
if (checkKeyOwnership && (!isKeyByOwner(ethKeyName, getStringRapid("cert")) || !isKeyByOwner(polyName, getStringRapid("cert")))) {
spdlog::error("Cert {} try to access keys {} {} which do not belong to it", getStringRapid("cert"), ethKeyName ,polyName);
throw std::invalid_argument("Only owner of the key can access it");
}
auto result = SGXWalletServer::createBLSPrivateKeyV2Impl(blsKeyName, ethKeyName, polyName, secretShare, t, n);
if (checkKeyOwnership && result["status"] == 0) {
addKeyByOwner(blsKeyName, getStringRapid("cert"));
auto cert = getStringRapid("cert");
spdlog::info("Cert {} creates key {}", cert, blsKeyName);
addKeyByOwner(blsKeyName, cert);
}
result["type"] = ZMQMessage::CREATE_BLS_PRIVATE_RSP;
return result;
......@@ -169,6 +183,7 @@ Json::Value createBLSPrivateKeyReqMessage::process() {
Json::Value getBLSPublicReqMessage::process() {
auto blsKeyName = getStringRapid("blsKeyName");
if (checkKeyOwnership && !isKeyByOwner(blsKeyName, getStringRapid("cert"))) {
spdlog::error("Cert {} try to access key {} which does not belong to it", getStringRapid("cert"), blsKeyName);
throw std::invalid_argument("Only owner of the key can access it");
}
auto result = SGXWalletServer::getBLSPublicKeyShareImpl(blsKeyName);
......@@ -191,6 +206,7 @@ Json::Value complaintResponseReqMessage::process() {
auto n = getInt64Rapid("n");
auto idx = getInt64Rapid("ind");
if (checkKeyOwnership && !isKeyByOwner(polyName, getStringRapid("cert"))) {
spdlog::error("Cert {} try to access key {} which does not belong to it", getStringRapid("cert"), polyName);
throw std::invalid_argument("Only owner of the key can access it");
}
auto result = SGXWalletServer::complaintResponseImpl(polyName, t, n, idx);
......@@ -227,9 +243,21 @@ Json::Value getServerVersionReqMessage::process() {
Json::Value deleteBLSKeyReqMessage::process() {
auto blsKeyName = getStringRapid("blsKeyName");
if (checkKeyOwnership && !isKeyByOwner(blsKeyName, getStringRapid("cert"))) {
spdlog::error("Cert {} try to access key {} which does not belong to it", getStringRapid("cert"), blsKeyName);
throw std::invalid_argument("Only owner of the key can access it");
}
auto result = SGXWalletServer::deleteBlsKeyImpl(blsKeyName);
result["type"] = ZMQMessage::DELETE_BLS_KEY_RSP;
return result;
}
Json::Value GetDecryptionShareReqMessage::process() {
auto blsKeyName = getStringRapid("blsKeyName");
auto publicDecryptionValue = getStringRapid("publicDecryptionValue");
if (checkKeyOwnership && !isKeyByOwner(blsKeyName, getStringRapid("cert"))) {
throw std::invalid_argument("Only owner of the key can access it");
}
auto result = SGXWalletServer::getDecryptionShareImpl(blsKeyName, publicDecryptionValue);
result["type"] = ZMQMessage::GET_DECRYPTION_SHARE_RSP;
return result;
}
......@@ -178,4 +178,11 @@ public:
virtual Json::Value process();
};
class GetDecryptionShareReqMessage : public ZMQMessage {
public:
GetDecryptionShareReqMessage(shared_ptr<rapidjson::Document>& _d) : ZMQMessage(_d) {};
virtual Json::Value process();
};
#endif //SGXWALLET_REQMESSAGE_H
......@@ -110,3 +110,7 @@ Json::Value getServerVersionRspMessage::process() {
Json::Value deleteBLSKeyRspMessage::process() {
assert(false);
}
Json::Value GetDecryptionShareRspMessage::process() {
assert(false);
}
......@@ -248,4 +248,16 @@ public:
};
class GetDecryptionShareRspMessage : public ZMQMessage {
public:
GetDecryptionShareRspMessage(shared_ptr<rapidjson::Document>& _d) : ZMQMessage(_d) {};
virtual Json::Value process();
Json::Value getShare() {
return getJsonValueRapid("decryptionShare");
}
};
#endif //SGXWALLET_RSPMESSAGE_H
......@@ -32,7 +32,7 @@
#include "sgxwallet_common.h"
#include "common.h"
#include "BLSCrypto.h"
#include "CryptoTools.h"
#include "ReqMessage.h"
#include "RspMessage.h"
#include "ZMQClient.h"
......@@ -496,6 +496,17 @@ bool ZMQClient::deleteBLSKey(const string& blsKeyName) {
return result->isSuccessful();
}
Json::Value ZMQClient::getDecryptionShare(const string& blsKeyName, const string& publicDecryptionValue) {
Json::Value p;
p["type"] = ZMQMessage::GET_DECRYPTION_SHARE_REQ;
p["blsKeyName"] = blsKeyName;
p["publicDecryptionValue"] = publicDecryptionValue;
auto result = dynamic_pointer_cast<GetDecryptionShareRspMessage>(doRequestReply(p));
CHECK_STATE(result);
CHECK_STATE(result->getStatus() == 0);
return result->getShare();
}
uint64_t ZMQClient::getProcessID() {
return syscall(__NR_gettid);
}
......@@ -122,6 +122,8 @@ public:
string getServerVersion();
bool deleteBLSKey(const string& blsKeyName);
Json::Value getDecryptionShare(const string& blsKeyName, const string& publicDecryptionValue);
};
......
......@@ -227,6 +227,9 @@ shared_ptr <ZMQMessage> ZMQMessage::buildRequest(string &_type, shared_ptr <rapi
case ENUM_DELETE_BLS_KEY_REQ:
ret = make_shared<deleteBLSKeyReqMessage>(_d);
break;
case ENUM_GET_DECRYPTION_SHARE_REQ:
ret = make_shared<GetDecryptionShareReqMessage>(_d);
break;
default:
break;
}
......@@ -308,6 +311,9 @@ shared_ptr <ZMQMessage> ZMQMessage::buildResponse(string &_type, shared_ptr <rap
case ENUM_DELETE_BLS_KEY_RSP:
ret = make_shared<deleteBLSKeyRspMessage>(_d);
break;
case ENUM_GET_DECRYPTION_SHARE_RSP:
ret = make_shared<GetDecryptionShareRspMessage>(_d);
break;
default:
break;
}
......@@ -320,12 +326,12 @@ shared_ptr <ZMQMessage> ZMQMessage::buildResponse(string &_type, shared_ptr <rap
std::map<string, string> ZMQMessage::keysByOwners;
bool ZMQMessage::isKeyByOwner(const string& keyName, const string& cert) {
auto value = LevelDB::getLevelDb()->readString(keyName);
auto value = LevelDB::getLevelDb()->readString(keyName + ":OWNER");
return value && *value == cert;
}
void ZMQMessage::addKeyByOwner(const string& keyName, const string& cert) {
SGXWalletServer::writeDataToDB(keyName, cert);
SGXWalletServer::writeDataToDB(keyName + ":OWNER", cert);
}
cache::lru_cache<string, pair < EVP_PKEY * , X509 *>> ZMQMessage::verifiedCerts(256);
......@@ -336,7 +342,8 @@ const std::map<string, int> ZMQMessage::requests{
{GET_VV_REQ, 7}, {GET_SECRET_SHARE_REQ, 8}, {DKG_VERIFY_REQ, 9},
{CREATE_BLS_PRIVATE_REQ, 10}, {GET_BLS_PUBLIC_REQ, 11}, {GET_ALL_BLS_PUBLIC_REQ, 12},
{COMPLAINT_RESPONSE_REQ, 13}, {MULT_G2_REQ, 14}, {IS_POLY_EXISTS_REQ, 15},
{GET_SERVER_STATUS_REQ, 16}, {GET_SERVER_VERSION_REQ, 17}, {DELETE_BLS_KEY_REQ, 18}
{GET_SERVER_STATUS_REQ, 16}, {GET_SERVER_VERSION_REQ, 17}, {DELETE_BLS_KEY_REQ, 18},
{GET_DECRYPTION_SHARE_REQ, 19}
};
const std::map<string, int> ZMQMessage::responses {
......@@ -345,5 +352,6 @@ const std::map<string, int> ZMQMessage::responses {
{GET_VV_RSP, 7}, {GET_SECRET_SHARE_RSP, 8}, {DKG_VERIFY_RSP, 9},
{CREATE_BLS_PRIVATE_RSP, 10}, {GET_BLS_PUBLIC_RSP, 11}, {GET_ALL_BLS_PUBLIC_RSP, 12},
{COMPLAINT_RESPONSE_RSP, 13}, {MULT_G2_RSP, 14}, {IS_POLY_EXISTS_RSP, 15},
{GET_SERVER_STATUS_RSP, 16}, {GET_SERVER_VERSION_RSP, 17}, {DELETE_BLS_KEY_RSP, 18}
{GET_SERVER_STATUS_RSP, 16}, {GET_SERVER_VERSION_RSP, 17}, {DELETE_BLS_KEY_RSP, 18},
{GET_DECRYPTION_SHARE_RSP, 19}
};
......@@ -100,6 +100,8 @@ public:
static constexpr const char *GET_SERVER_VERSION_RSP = "getServerVersionRsp";
static constexpr const char *DELETE_BLS_KEY_REQ = "deleteBLSKeyReq";
static constexpr const char *DELETE_BLS_KEY_RSP = "deleteBLSKeyRsp";
static constexpr const char *GET_DECRYPTION_SHARE_REQ = "getDecryptionShareReq";
static constexpr const char *GET_DECRYPTION_SHARE_RSP = "getDecryptionShareRsp";
static const std::map<string, int> requests;
static const std::map<string, int> responses;
......@@ -107,11 +109,11 @@ public:
enum Requests { ENUM_BLS_SIGN_REQ, ENUM_ECDSA_SIGN_REQ, ENUM_IMPORT_BLS_REQ, ENUM_IMPORT_ECDSA_REQ, ENUM_GENERATE_ECDSA_REQ, ENUM_GET_PUBLIC_ECDSA_REQ,
ENUM_GENERATE_DKG_POLY_REQ, ENUM_GET_VV_REQ, ENUM_GET_SECRET_SHARE_REQ, ENUM_DKG_VERIFY_REQ, ENUM_CREATE_BLS_PRIVATE_REQ,
ENUM_GET_BLS_PUBLIC_REQ, ENUM_GET_ALL_BLS_PUBLIC_REQ, ENUM_COMPLAINT_RESPONSE_REQ, ENUM_MULT_G2_REQ, ENUM_IS_POLY_EXISTS_REQ,
ENUM_GET_SERVER_STATUS_REQ, ENUM_GET_SERVER_VERSION_REQ, ENUM_DELETE_BLS_KEY_REQ };
ENUM_GET_SERVER_STATUS_REQ, ENUM_GET_SERVER_VERSION_REQ, ENUM_DELETE_BLS_KEY_REQ, ENUM_GET_DECRYPTION_SHARE_REQ };
enum Responses { ENUM_BLS_SIGN_RSP, ENUM_ECDSA_SIGN_RSP, ENUM_IMPORT_BLS_RSP, ENUM_IMPORT_ECDSA_RSP, ENUM_GENERATE_ECDSA_RSP, ENUM_GET_PUBLIC_ECDSA_RSP,
ENUM_GENERATE_DKG_POLY_RSP, ENUM_GET_VV_RSP, ENUM_GET_SECRET_SHARE_RSP, ENUM_DKG_VERIFY_RSP, ENUM_CREATE_BLS_PRIVATE_RSP,
ENUM_GET_BLS_PUBLIC_RSP, ENUM_GET_ALL_BLS_PUBLIC_RSP, ENUM_COMPLAINT_RESPONSE_RSP, ENUM_MULT_G2_RSP, ENUM_IS_POLY_EXISTS_RSP,
ENUM_GET_SERVER_STATUS_RSP, ENUM_GET_SERVER_VERSION_RSP, ENUM_DELETE_BLS_KEY_RSP };
ENUM_GET_SERVER_STATUS_RSP, ENUM_GET_SERVER_VERSION_RSP, ENUM_DELETE_BLS_KEY_RSP, ENUM_GET_DECRYPTION_SHARE_RSP };
explicit ZMQMessage(shared_ptr<rapidjson::Document> &_d) : d(_d) {};
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment