Skip to content

Commit

Permalink
Sigma fixes (#777)
Browse files Browse the repository at this point in the history
* Sigma fixes
* Tests fix
  • Loading branch information
levonpetrosyan93 authored and a-bezrukov committed Dec 2, 2019
1 parent 2a1dad7 commit af20f12
Show file tree
Hide file tree
Showing 52 changed files with 413 additions and 139 deletions.
2 changes: 1 addition & 1 deletion configure.ac
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ AC_PREREQ([2.60])
define(_CLIENT_VERSION_MAJOR, 0)
define(_CLIENT_VERSION_MINOR, 13)
define(_CLIENT_VERSION_REVISION, 8)
define(_CLIENT_VERSION_BUILD, 5)
define(_CLIENT_VERSION_BUILD, 8)
define(_CLIENT_VERSION_IS_RELEASE, true)
define(_COPYRIGHT_YEAR, 2019)
define(_COPYRIGHT_HOLDERS,[The %s developers])
Expand Down
2 changes: 1 addition & 1 deletion qa/rpc-tests/exodus_sendspend.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ class ExodusSendSpendTest(ExodusTestFramework):
def run_test(self):
super().run_test()

sigma_starting_block = 500
sigma_starting_block = 550

self.nodes[0].generatetoaddress(sigma_starting_block - self.nodes[0].getblockcount(), self.addrs[0])
self.sync_all()
Expand Down
2 changes: 1 addition & 1 deletion qa/rpc-tests/exodus_sigma_reindex.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ class ExodusSigmaReindexTest(ExodusTestFramework):
def run_test(self):
super().run_test()

sigma_start_block = 500
sigma_start_block = 550
self.nodes[0].generate(sigma_start_block - self.nodes[0].getblockcount())

# generate mints to spend
Expand Down
4 changes: 2 additions & 2 deletions qa/rpc-tests/exodus_sigma_reorg.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ class ExodusSigmaReorgTest(ExodusTestFramework):
def run_test(self):
super().run_test()

sigma_start_block = 500
sigma_start_block = 550
self.nodes[0].generate(sigma_start_block - self.nodes[0].getblockcount())

# generate mints to spend
Expand Down Expand Up @@ -75,4 +75,4 @@ def run_test(self):
assert_equal(balance, self.nodes[0].exodus_getbalance(self.addrs[0], sigma_property)['balance'])

if __name__ == '__main__':
ExodusSigmaReorgTest().main()
ExodusSigmaReorgTest().main()
2 changes: 1 addition & 1 deletion qa/rpc-tests/sigma_meetspend.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ def run_test(self):
# Decimal formating: 6 digits for balance will be enought 000.000
getcontext().prec = 6

self.nodes[0].generate(400)
self.nodes[0].generate(500)
self.sync_all()

start_bal = self.nodes[0].getbalance()
Expand Down
5 changes: 2 additions & 3 deletions qa/rpc-tests/sigma_mintspend.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,15 +19,14 @@ def setup_nodes(self):
def run_test(self):
# Decimal formating: 6 digits for balance will be enought 000.000
getcontext().prec = 6
self.nodes[0].generate(400)
self.nodes[0].generate(551)
self.sync_all()

# old denomination
# TODO should be changed after RPC will be updated
denoms = [0.1, 0.5, 1, 10, 100]

start_bal = self.nodes[0].getbalance()
assert start_bal == 14918.000, 'Unexpected start balance: {}'.format(start_bal)

mint_trans = list()
for denom in denoms:
Expand Down Expand Up @@ -146,4 +145,4 @@ def run_test(self):


if __name__ == '__main__':
SigmaMintSpendTest().main()
SigmaMintSpendTest().main()
6 changes: 6 additions & 0 deletions src/chainparams.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -253,6 +253,8 @@ class CMainParams : public CChainParams {

// Sigma related values.
consensus.nSigmaStartBlock = ZC_SIGMA_STARTING_BLOCK;
consensus.nSigmaPaddingBlock = ZC_SIGMA_PADDING_BLOCK;
consensus.nDisableUnpaddedSigmaBlock = ZC_SIGMA_DISABLE_UNPADDED_BLOCK;
consensus.nOldSigmaBanBlock = ZC_OLD_SIGMA_BAN_BLOCK;
consensus.nZerocoinV2MintMempoolGracefulPeriod = ZC_V2_MINT_GRACEFUL_MEMPOOL_PERIOD;
consensus.nZerocoinV2MintGracefulPeriod = ZC_V2_MINT_GRACEFUL_PERIOD;
Expand Down Expand Up @@ -441,6 +443,8 @@ class CTestNetParams : public CChainParams {

// Sigma related values.
consensus.nSigmaStartBlock = ZC_SIGMA_TESTNET_STARTING_BLOCK;
consensus.nSigmaPaddingBlock = ZC_SIGMA_TESTNET_PADDING_BLOCK;
consensus.nDisableUnpaddedSigmaBlock = ZC_SIGMA_TESTNET_DISABLE_UNPADDED_BLOCK;
consensus.nOldSigmaBanBlock = 70416;
consensus.nZerocoinV2MintMempoolGracefulPeriod = ZC_V2_MINT_TESTNET_GRACEFUL_MEMPOOL_PERIOD;
consensus.nZerocoinV2MintGracefulPeriod = ZC_V2_MINT_TESTNET_GRACEFUL_PERIOD;
Expand Down Expand Up @@ -595,6 +599,8 @@ class CRegTestParams : public CChainParams {

// Sigma related values.
consensus.nSigmaStartBlock = 400;
consensus.nSigmaPaddingBlock = 550;
consensus.nDisableUnpaddedSigmaBlock = 510;
consensus.nOldSigmaBanBlock = 450;
consensus.nZerocoinV2MintMempoolGracefulPeriod = 2;
consensus.nZerocoinV2MintGracefulPeriod = 5;
Expand Down
2 changes: 1 addition & 1 deletion src/clientversion.h
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
#define CLIENT_VERSION_MAJOR 0
#define CLIENT_VERSION_MINOR 13
#define CLIENT_VERSION_REVISION 8
#define CLIENT_VERSION_BUILD 5
#define CLIENT_VERSION_BUILD 8

//! Set to true for release, false for prerelease or test build
#define CLIENT_VERSION_IS_RELEASE true
Expand Down
4 changes: 4 additions & 0 deletions src/consensus/params.h
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,10 @@ struct Params {
// The block number after which sigma are accepted.
int nSigmaStartBlock;

int nSigmaPaddingBlock;

int nDisableUnpaddedSigmaBlock;

// The block number after which old sigma clients are banned.
int nOldSigmaBanBlock;

Expand Down
5 changes: 4 additions & 1 deletion src/exodus/rpctx.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1711,7 +1711,10 @@ UniValue exodus_sendspend(const UniValue& params, bool fHelp)
std::vector<unsigned char> payload;

try {
auto spend = wallet->CreateSigmaSpend(propertyId, denomination);

bool fPadding = chainActive.Height() >= ::Params().GetConsensus().nSigmaPaddingBlock;

auto spend = wallet->CreateSigmaSpend(propertyId, denomination, fPadding);
mint = spend.mint;

payload = CreatePayload_SimpleSpend(
Expand Down
5 changes: 3 additions & 2 deletions src/exodus/sigma.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,8 @@ bool VerifySigmaSpend(
SigmaDenomination denomination,
SigmaMintGroup group,
size_t groupSize,
const SigmaProof& proof)
const SigmaProof& proof,
bool fPadding)
{
std::vector<SigmaPublicKey> anonimitySet; // Don't preallocate the vector due to it will allow attacker to crash all client.

Expand All @@ -30,7 +31,7 @@ bool VerifySigmaSpend(
return false;
}

return proof.Verify(anonimitySet.begin(), anonimitySet.end());
return proof.Verify(anonimitySet.begin(), anonimitySet.end(), fPadding);
}

} // namespace exodus
3 changes: 2 additions & 1 deletion src/exodus/sigma.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,8 @@ bool VerifySigmaSpend(
SigmaDenomination denomination,
SigmaMintGroup group,
size_t groupSize,
const SigmaProof& proof);
const SigmaProof& proof,
bool fPadding);

} // namespace exodus

Expand Down
12 changes: 6 additions & 6 deletions src/exodus/sigmaprimitives.h
Original file line number Diff line number Diff line change
Expand Up @@ -113,10 +113,10 @@ class SigmaProof
explicit SigmaProof(const SigmaParams& params);

template<typename PublicKey>
SigmaProof(const SigmaParams& params, const SigmaPrivateKey& key, PublicKey first, PublicKey last) :
SigmaProof(const SigmaParams& params, const SigmaPrivateKey& key, PublicKey first, PublicKey last, bool fPadding) :
SigmaProof(params)
{
Generate(key, first, last);
Generate(key, first, last, fPadding);
}

public:
Expand All @@ -125,7 +125,7 @@ class SigmaProof

public:
template<typename PublicKey>
bool Verify(PublicKey first, PublicKey last) const
bool Verify(PublicKey first, PublicKey last, bool fPadding) const
{
// Create commitment set.
auto gs = (params.g * serial).inverse();
Expand All @@ -145,12 +145,12 @@ class SigmaProof
params.m
);

return verifier.verify(commits, proof);
return verifier.verify(commits, proof, fPadding);
}

public:
template<typename PublicKey>
void Generate(const SigmaPrivateKey& priv, PublicKey first, PublicKey last)
void Generate(const SigmaPrivateKey& priv, PublicKey first, PublicKey last, bool fPadding)
{
if (!priv.IsValid()) {
throw std::invalid_argument("Private key is not valid");
Expand Down Expand Up @@ -186,7 +186,7 @@ class SigmaProof
params.m
);

prover.proof(commits, *index, priv.randomness, proof);
prover.proof(commits, *index, priv.randomness, fPadding, proof);
serial = priv.serial;
}

Expand Down
2 changes: 1 addition & 1 deletion src/exodus/test/create_payload_tests.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -560,7 +560,7 @@ BOOST_AUTO_TEST_CASE(payload_create_simple_spend)
key1.Generate();
key2.Generate();
anonimitySet = { SigmaPublicKey(key1, params), SigmaPublicKey(key2, params) };
spend.Generate(key1, anonimitySet.begin(), anonimitySet.end());
spend.Generate(key1, anonimitySet.begin(), anonimitySet.end(), false);
buffer << spend;

std::vector<unsigned char> payload;
Expand Down
16 changes: 8 additions & 8 deletions src/exodus/test/sigma_tests.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ BOOST_FIXTURE_TEST_CASE(verify_spend, SigmaDatabaseFixture)
anonimitySet.push_back(mint);
}

proof.Generate(key, anonimitySet.begin(), anonimitySet.end());
proof.Generate(key, anonimitySet.begin(), anonimitySet.end(), false);

// Generate spendable group.
for (unsigned i = 0; i < sigmaDb->groupSize; i++) {
Expand All @@ -91,13 +91,13 @@ BOOST_FIXTURE_TEST_CASE(verify_spend, SigmaDatabaseFixture)
sigmaDb->RecordMint(3, 0, mint, block);
}

BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 0, 0, anonimitySet.size(), proof), true);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 0, 0, anonimitySet.size() - 1, proof), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 0, 0, anonimitySet.size() + 1, proof), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 0, 0, sigmaDb->groupSize + 1, proof), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 1, 0, sigmaDb->groupSize, proof), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(4, 0, 0, sigmaDb->groupSize, proof), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 0, 1, sigmaDb->groupSize, proof), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 0, 0, anonimitySet.size(), proof, false), true);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 0, 0, anonimitySet.size() - 1, proof, false), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 0, 0, anonimitySet.size() + 1, proof, false), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 0, 0, sigmaDb->groupSize + 1, proof, false), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 1, 0, sigmaDb->groupSize, proof, false), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(4, 0, 0, sigmaDb->groupSize, proof, false), false);
BOOST_CHECK_EQUAL(VerifySigmaSpend(3, 0, 1, sigmaDb->groupSize, proof, false), false);
}

BOOST_AUTO_TEST_SUITE_END()
Expand Down
14 changes: 7 additions & 7 deletions src/exodus/test/sigmaprimitives_tests.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -107,10 +107,10 @@ BOOST_AUTO_TEST_CASE(proof)
SigmaPublicKey(key3, params)
});

proof.Generate(key2, pubs.begin(), pubs.end());
proof.Generate(key2, pubs.begin(), pubs.end(), false);

BOOST_CHECK_EQUAL(proof.Verify(pubs.begin(), pubs.end()), true);
BOOST_CHECK_EQUAL(proof.Verify(pubs.begin(), pubs.end() - 1), false);
BOOST_CHECK_EQUAL(proof.Verify(pubs.begin(), pubs.end(), false), true);
BOOST_CHECK_EQUAL(proof.Verify(pubs.begin(), pubs.end() - 1, false), false);
}

BOOST_AUTO_TEST_CASE(spend_with_large_anonimity_group)
Expand All @@ -129,11 +129,11 @@ BOOST_AUTO_TEST_CASE(spend_with_large_anonimity_group)
}

SigmaProof validProof(params), invalidProof(params);
validProof.Generate(key, pubs.begin() + 1, pubs.end()); // prove with 2 ^ 14 coins
invalidProof.Generate(key, pubs.begin(), pubs.end()); // prove with 2 ^ 14 + 1 coins
validProof.Generate(key, pubs.begin() + 1, pubs.end(), false); // prove with 2 ^ 14 coins
invalidProof.Generate(key, pubs.begin(), pubs.end(), false); // prove with 2 ^ 14 + 1 coins

BOOST_CHECK_EQUAL(validProof.Verify(pubs.begin() + 1, pubs.end()), true);
BOOST_CHECK_EQUAL(invalidProof.Verify(pubs.begin(), pubs.end()), false);
BOOST_CHECK_EQUAL(validProof.Verify(pubs.begin() + 1, pubs.end(), false), true);
BOOST_CHECK_EQUAL(invalidProof.Verify(pubs.begin(), pubs.end(), false), false);
}

BOOST_AUTO_TEST_SUITE_END()
Expand Down
14 changes: 7 additions & 7 deletions src/exodus/test/wallet_tests.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -124,22 +124,22 @@ BOOST_AUTO_TEST_CASE(sigma_mint_create_multi)
BOOST_AUTO_TEST_CASE(sigma_spend_create_no_spendable_mint)
{
// No any mints.
BOOST_CHECK_THROW(wallet->CreateSigmaSpend(3, 0), InsufficientFunds);
BOOST_CHECK_THROW(wallet->CreateSigmaSpend(3, 0, false), InsufficientFunds);

// Different denomination and property type.
auto mintId = wallet->CreateSigmaMint(3, 0);

BOOST_CHECK_THROW(wallet->CreateSigmaSpend(3, 1), InsufficientFunds);
BOOST_CHECK_THROW(wallet->CreateSigmaSpend(4, 0), InsufficientFunds);
BOOST_CHECK_THROW(wallet->CreateSigmaSpend(3, 1, false), InsufficientFunds);
BOOST_CHECK_THROW(wallet->CreateSigmaSpend(4, 0, false), InsufficientFunds);

// Pending mint.
BOOST_CHECK_THROW(wallet->CreateSigmaSpend(3, 0), InsufficientFunds);
BOOST_CHECK_THROW(wallet->CreateSigmaSpend(3, 0, false), InsufficientFunds);

// Already spent.
sigmaDb->RecordMint(3, 0, mintId.pubKey, 100);
wallet->SetSigmaMintUsedTransaction(mintId, uint256S("890e968f9b65dbacd576100c9b1c446f06471ed27df845ab7a24931cb640b388"));

BOOST_CHECK_THROW(wallet->CreateSigmaSpend(3, 0), InsufficientFunds);
BOOST_CHECK_THROW(wallet->CreateSigmaSpend(3, 0, false), InsufficientFunds);
}

BOOST_AUTO_TEST_CASE(sigma_spend_create_with_spendable_mints)
Expand All @@ -153,7 +153,7 @@ BOOST_AUTO_TEST_CASE(sigma_spend_create_with_spendable_mints)
sigmaDb->RecordMint(3, 0, mintid.pubKey, 100 + i);
}

auto spend = wallet->CreateSigmaSpend(3, 0);
auto spend = wallet->CreateSigmaSpend(3, 0, false);

BOOST_CHECK_EQUAL(spend.mint, expectedMintId);
BOOST_CHECK_EQUAL(spend.group, 0);
Expand All @@ -165,7 +165,7 @@ BOOST_AUTO_TEST_CASE(sigma_spend_create_not_enough_anonimity)
auto mintId = wallet->CreateSigmaMint(3, 0);
sigmaDb->RecordMint(3, 0, mintId.pubKey, 100);

BOOST_CHECK_EXCEPTION(wallet->CreateSigmaSpend(3, 0), WalletError, [] (const WalletError& e) {
BOOST_CHECK_EXCEPTION(wallet->CreateSigmaSpend(3, 0, false), WalletError, [] (const WalletError& e) {
return e.what() == std::string("Amount of coins in anonimity set is not enough to spend");
});
}
Expand Down
2 changes: 1 addition & 1 deletion src/exodus/test/walletmodels_tests.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -335,7 +335,7 @@ BOOST_AUTO_TEST_CASE(sigma_spend_init)
SigmaMint mint(3, 0, Hash160({0x00}), Hash160({0x01}));

std::vector<SigmaPublicKey> anonimitySet = { pub1, pub2 };
SigmaProof proof(params, key1, anonimitySet.begin(), anonimitySet.end());
SigmaProof proof(params, key1, anonimitySet.begin(), anonimitySet.end(), false);
SigmaSpend spend(id, 1, 100, proof);

BOOST_CHECK_EQUAL(spend.mint, id);
Expand Down
4 changes: 3 additions & 1 deletion src/exodus/txprocessor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -158,12 +158,14 @@ int TxProcessor::ProcessSimpleSpend(const CMPTransaction& tx)
auto group = tx.getGroup();
auto groupSize = tx.getGroupSize();

bool const fPadding = block >= ::Params().GetConsensus().nSigmaPaddingBlock;

assert(spend);

// check serial in database
uint256 spendTx;
if (sigmaDb->HasSpendSerial(property, denomination, spend->serial, spendTx)
|| !VerifySigmaSpend(property, denomination, group, groupSize, *spend)) {
|| !VerifySigmaSpend(property, denomination, group, groupSize, *spend, fPadding)) {
PrintToLog("%s(): rejected: spend is invalid\n", __func__);
return PKT_ERROR_SIGMA - 907;
}
Expand Down
6 changes: 3 additions & 3 deletions src/exodus/wallet.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,7 @@ void Wallet::ClearAllChainState()
mintWallet.ClearMintsChainState();
}

SigmaSpend Wallet::CreateSigmaSpend(PropertyId property, SigmaDenomination denomination)
SigmaSpend Wallet::CreateSigmaSpend(PropertyId property, SigmaDenomination denomination, bool fPadding)
{
LOCK(cs_main);

Expand All @@ -102,9 +102,9 @@ SigmaSpend Wallet::CreateSigmaSpend(PropertyId property, SigmaDenomination denom

// Create spend.
auto key = GetKey(mint.get());
SigmaProof proof(DefaultSigmaParams, key, anonimitySet.begin(), anonimitySet.end());
SigmaProof proof(DefaultSigmaParams, key, anonimitySet.begin(), anonimitySet.end(), fPadding);

if (!VerifySigmaSpend(mint->property, mint->denomination, mint->chainState.group, anonimitySet.size(), proof)) {
if (!VerifySigmaSpend(mint->property, mint->denomination, mint->chainState.group, anonimitySet.size(), proof, fPadding)) {
throw WalletError(_("Failed to create spendable spend"));
}

Expand Down
2 changes: 1 addition & 1 deletion src/exodus/wallet.h
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ class Wallet

void ClearAllChainState();

SigmaSpend CreateSigmaSpend(PropertyId property, SigmaDenomination denomination);
SigmaSpend CreateSigmaSpend(PropertyId property, SigmaDenomination denomination, bool fPadding);
void DeleteUnconfirmedSigmaMint(SigmaMintId const &id);

public:
Expand Down
Loading

0 comments on commit af20f12

Please sign in to comment.