diff --git a/src/avalanche/proof.h b/src/avalanche/proof.h --- a/src/avalanche/proof.h +++ b/src/avalanche/proof.h @@ -39,6 +39,11 @@ using StakeId = uint256; +struct StakeCommitment : public uint256 { + explicit StakeCommitment() : uint256() {} + explicit StakeCommitment(const uint256 &b) : uint256(b) {} +}; + class Stake { COutPoint utxo; @@ -69,7 +74,7 @@ bool isCoinbase() const { return height & 1; } const CPubKey &getPubkey() const { return pubkey; } - uint256 getHash(const ProofId &proofid) const; + uint256 getHash(const StakeCommitment &commitment) const; const StakeId &getId() const { return stakeid; } }; @@ -88,7 +93,7 @@ const Stake &getStake() const { return stake; } const SchnorrSig &getSignature() const { return sig; } - bool verify(const ProofId &proofid) const; + bool verify(const StakeCommitment &commitment) const; }; class Proof { @@ -138,6 +143,9 @@ const ProofId &getId() const { return proofid; } const LimitedProofId &getLimitedId() const { return limitedProofId; } + const StakeCommitment getStakeCommitment() const { + return StakeCommitment(proofid); + } uint32_t getScore() const; bool verify(ProofValidationState &state) const; diff --git a/src/avalanche/proof.cpp b/src/avalanche/proof.cpp --- a/src/avalanche/proof.cpp +++ b/src/avalanche/proof.cpp @@ -24,15 +24,15 @@ stakeid = StakeId(ss.GetHash()); } -uint256 Stake::getHash(const ProofId &proofid) const { +uint256 Stake::getHash(const StakeCommitment &commitment) const { CHashWriter ss(SER_GETHASH, 0); - ss << proofid; + ss << commitment; ss << *this; return ss.GetHash(); } -bool SignedStake::verify(const ProofId &proofid) const { - return stake.getPubkey().VerifySchnorr(stake.getHash(proofid), sig); +bool SignedStake::verify(const StakeCommitment &commitment) const { + return stake.getPubkey().VerifySchnorr(stake.getHash(commitment), sig); } bool Proof::FromHex(Proof &proof, const std::string &hexProof, @@ -121,7 +121,7 @@ "duplicated-stake"); } - if (!ss.verify(proofid)) { + if (!ss.verify(getStakeCommitment())) { return state.Invalid( ProofValidationResult::INVALID_STAKE_SIGNATURE, "invalid-stake-signature", diff --git a/src/avalanche/proofbuilder.h b/src/avalanche/proofbuilder.h --- a/src/avalanche/proofbuilder.h +++ b/src/avalanche/proofbuilder.h @@ -27,7 +27,7 @@ StakeSigner(Stake stake_, CKey key_) : stake(std::move(stake_)), key(std::move(key_)) {} - SignedStake sign(const ProofId &proofid); + SignedStake sign(const StakeCommitment &commitment); }; struct StakeSignerComparator { diff --git a/src/avalanche/proofbuilder.cpp b/src/avalanche/proofbuilder.cpp --- a/src/avalanche/proofbuilder.cpp +++ b/src/avalanche/proofbuilder.cpp @@ -8,8 +8,8 @@ namespace avalanche { -SignedStake ProofBuilder::StakeSigner::sign(const ProofId &proofid) { - const uint256 h = stake.getHash(proofid); +SignedStake ProofBuilder::StakeSigner::sign(const StakeCommitment &commitment) { + const uint256 h = stake.getHash(commitment); SchnorrSig sig; if (!key.SignSchnorr(h, sig)) { @@ -34,13 +34,14 @@ Proof ProofBuilder::build() { const ProofId proofid = getProofId(); + const StakeCommitment commitment(proofid); std::vector signedStakes; signedStakes.reserve(stakes.size()); while (!stakes.empty()) { auto handle = stakes.extract(stakes.begin()); - signedStakes.push_back(handle.value().sign(proofid)); + signedStakes.push_back(handle.value().sign(commitment)); } return Proof(sequence, expirationTime, masterKey.GetPubKey(), diff --git a/src/avalanche/test/util.cpp b/src/avalanche/test/util.cpp --- a/src/avalanche/test/util.cpp +++ b/src/avalanche/test/util.cpp @@ -66,6 +66,7 @@ Proof TestProofBuilder::buildWithReversedOrderStakes(ProofBuilder &pb) { const ProofId proofid = TestProofBuilder::getReverseOrderProofId(pb); + const StakeCommitment commitment(proofid); std::vector signedStakes; signedStakes.reserve(pb.stakes.size()); @@ -74,7 +75,7 @@ // We need a forward iterator, so pb.stakes.rbegin() is not an // option. auto handle = pb.stakes.extract(std::prev(pb.stakes.end())); - signedStakes.push_back(handle.value().sign(proofid)); + signedStakes.push_back(handle.value().sign(commitment)); } return Proof(pb.sequence, pb.expirationTime, pb.masterKey.GetPubKey(), @@ -101,13 +102,14 @@ Proof TestProofBuilder::buildDuplicatedStakes(ProofBuilder &pb) { const ProofId proofid = TestProofBuilder::getDuplicatedStakeProofId(pb); + const StakeCommitment commitment(proofid); std::vector signedStakes; signedStakes.reserve(2 * pb.stakes.size()); while (!pb.stakes.empty()) { auto handle = pb.stakes.extract(pb.stakes.begin()); - SignedStake signedStake = handle.value().sign(proofid); + SignedStake signedStake = handle.value().sign(commitment); signedStakes.push_back(signedStake); signedStakes.push_back(signedStake); }