mirror of
https://github.com/ElementsProject/elements.git
synced 2026-08-18 13:17:55 +02:00
Refactor block_proof to support dynafed
This commit is contained in:
parent
0402da670a
commit
fa1f497a24
6 changed files with 46 additions and 27 deletions
|
|
@ -19,21 +19,18 @@ bool CheckChallenge(const CBlockHeader& block, const CBlockIndex& indexLast, con
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ResetChallenge(CBlockHeader& block, const CBlockIndex& indexLast, const Consensus::Params& params)
|
static bool CheckProofGeneric(const CBlockHeader& block, const uint32_t max_block_signature_size, const CScript& challenge, const CScript& scriptSig, const CScriptWitness& witness)
|
||||||
{
|
{
|
||||||
block.proof.challenge = indexLast.proof.challenge;
|
// scriptSig or witness will be nonempty, but not both, so just compare both limits
|
||||||
}
|
if (scriptSig.size() > max_block_signature_size) {
|
||||||
|
|
||||||
static bool CheckProofGeneric(const CBlockHeader& block, const Consensus::Params& params, const CScript& challenge)
|
|
||||||
{
|
|
||||||
if (block.GetHash() == params.hashGenesisBlock)
|
|
||||||
return true;
|
|
||||||
|
|
||||||
if (block.proof.solution.size() > params.max_block_signature_size) {
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Some anti-DoS flags, though consensus.max_block_signature_size caps the possible
|
if (witness.GetSerializedSize() > max_block_signature_size) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Some anti-DoS flags, though max_block_signature_size caps the possible
|
||||||
// danger in malleation of the block witness data.
|
// danger in malleation of the block witness data.
|
||||||
unsigned int proof_flags = SCRIPT_VERIFY_P2SH // For cleanstack evalution under segwit flag
|
unsigned int proof_flags = SCRIPT_VERIFY_P2SH // For cleanstack evalution under segwit flag
|
||||||
| SCRIPT_VERIFY_STRICTENC // Minimally-sized DER sigs
|
| SCRIPT_VERIFY_STRICTENC // Minimally-sized DER sigs
|
||||||
|
|
@ -42,15 +39,20 @@ static bool CheckProofGeneric(const CBlockHeader& block, const Consensus::Params
|
||||||
| SCRIPT_VERIFY_MINIMALDATA // Pushes are minimally-sized
|
| SCRIPT_VERIFY_MINIMALDATA // Pushes are minimally-sized
|
||||||
| SCRIPT_VERIFY_SIGPUSHONLY // Witness is push-only
|
| SCRIPT_VERIFY_SIGPUSHONLY // Witness is push-only
|
||||||
| SCRIPT_VERIFY_LOW_S // Stop easiest signature fiddling
|
| SCRIPT_VERIFY_LOW_S // Stop easiest signature fiddling
|
||||||
| SCRIPT_VERIFY_WITNESS // Required for cleanstack eval in VerifyScript
|
| SCRIPT_VERIFY_WITNESS // Witness and to enforce cleanstack
|
||||||
| SCRIPT_NO_SIGHASH_BYTE; // non-Check(Multi)Sig signatures will not have sighash byte
|
| SCRIPT_NO_SIGHASH_BYTE; // non-Check(Multi)Sig signatures will not have sighash byte
|
||||||
return GenericVerifyScript(block.proof.solution, challenge, proof_flags, block);
|
return GenericVerifyScript(scriptSig, witness, challenge, proof_flags, block);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool CheckProof(const CBlockHeader& block, const Consensus::Params& params)
|
bool CheckProof(const CBlockHeader& block, const Consensus::Params& params)
|
||||||
{
|
{
|
||||||
if (g_signed_blocks) {
|
if (g_signed_blocks) {
|
||||||
return CheckProofGeneric(block, params, params.signblockscript);
|
const DynaFedParams& d_params = block.m_dyna_params;
|
||||||
|
if (d_params.IsNull()) {
|
||||||
|
return CheckProofGeneric(block, params.max_block_signature_size, params.signblockscript, block.proof.solution, CScriptWitness());
|
||||||
|
} else {
|
||||||
|
return CheckProofGeneric(block, d_params.m_current.m_sbs_wit_limit, d_params.m_current.m_signblockscript, CScript(), block.m_signblock_witness);
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
return CheckProofOfWork(block.GetHash(), block.nBits, params);
|
return CheckProofOfWork(block.GetHash(), block.nBits, params);
|
||||||
}
|
}
|
||||||
|
|
@ -58,10 +60,15 @@ bool CheckProof(const CBlockHeader& block, const Consensus::Params& params)
|
||||||
|
|
||||||
bool CheckProofSignedParent(const CBlockHeader& block, const Consensus::Params& params)
|
bool CheckProofSignedParent(const CBlockHeader& block, const Consensus::Params& params)
|
||||||
{
|
{
|
||||||
return CheckProofGeneric(block, params, params.parent_chain_signblockscript);
|
const DynaFedParams& d_params = block.m_dyna_params;
|
||||||
}
|
if (d_params.IsNull()) {
|
||||||
|
return CheckProofGeneric(block, params.max_block_signature_size, params.parent_chain_signblockscript, block.proof.solution, CScriptWitness());
|
||||||
void ResetProof(CBlockHeader& block)
|
} else {
|
||||||
{
|
// Dynamic federations means we cannot validate the signer set
|
||||||
block.proof.solution.clear();
|
// at least without tracking the parent chain more directly.
|
||||||
|
// Note that we do not even serialize dynamic federation block witness data
|
||||||
|
// currently for merkle proofs which is the only context in which
|
||||||
|
// this function is currently used.
|
||||||
|
return true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -20,8 +20,6 @@ class CScript;
|
||||||
/** Check on header proof, depending on chain type, PoW or signed **/
|
/** Check on header proof, depending on chain type, PoW or signed **/
|
||||||
bool CheckProof(const CBlockHeader& block, const Consensus::Params&);
|
bool CheckProof(const CBlockHeader& block, const Consensus::Params&);
|
||||||
bool CheckProofSignedParent(const CBlockHeader& block, const Consensus::Params&);
|
bool CheckProofSignedParent(const CBlockHeader& block, const Consensus::Params&);
|
||||||
void ResetProof(CBlockHeader& block);
|
|
||||||
bool CheckChallenge(const CBlockHeader& block, const CBlockIndex& indexLast, const Consensus::Params&);
|
bool CheckChallenge(const CBlockHeader& block, const CBlockIndex& indexLast, const Consensus::Params&);
|
||||||
void ResetChallenge(CBlockHeader& block, const CBlockIndex& indexLast, const Consensus::Params&);
|
|
||||||
|
|
||||||
#endif // BITCOIN_BLOCK_PROOF_H
|
#endif // BITCOIN_BLOCK_PROOF_H
|
||||||
|
|
|
||||||
|
|
@ -25,13 +25,21 @@
|
||||||
#include <util/system.h>
|
#include <util/system.h>
|
||||||
#include <validationinterface.h>
|
#include <validationinterface.h>
|
||||||
|
|
||||||
// ELEMENTS
|
|
||||||
#include <block_proof.h> // ResetProof, ResetChallenge
|
|
||||||
|
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <queue>
|
#include <queue>
|
||||||
#include <utility>
|
#include <utility>
|
||||||
|
|
||||||
|
void ResetChallenge(CBlockHeader& block, const CBlockIndex& indexLast, const Consensus::Params& params)
|
||||||
|
{
|
||||||
|
block.proof.challenge = indexLast.proof.challenge;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ResetProof(CBlockHeader& block)
|
||||||
|
{
|
||||||
|
block.proof.solution.clear();
|
||||||
|
}
|
||||||
|
|
||||||
int64_t UpdateTime(CBlockHeader* pblock, const Consensus::Params& consensusParams, const CBlockIndex* pindexPrev)
|
int64_t UpdateTime(CBlockHeader* pblock, const Consensus::Params& consensusParams, const CBlockIndex* pindexPrev)
|
||||||
{
|
{
|
||||||
int64_t nOldTime = pblock->nTime;
|
int64_t nOldTime = pblock->nTime;
|
||||||
|
|
@ -161,7 +169,6 @@ std::unique_ptr<CBlockTemplate> BlockAssembler::CreateNewBlock(const CScript& sc
|
||||||
// Pad block weight by block proof fields (including upper-bound of signature)
|
// Pad block weight by block proof fields (including upper-bound of signature)
|
||||||
nBlockWeight += chainparams.GetConsensus().signblockscript.size() * WITNESS_SCALE_FACTOR;
|
nBlockWeight += chainparams.GetConsensus().signblockscript.size() * WITNESS_SCALE_FACTOR;
|
||||||
nBlockWeight += chainparams.GetConsensus().max_block_signature_size * WITNESS_SCALE_FACTOR;
|
nBlockWeight += chainparams.GetConsensus().max_block_signature_size * WITNESS_SCALE_FACTOR;
|
||||||
// Reset block proof
|
|
||||||
ResetProof(*pblock);
|
ResetProof(*pblock);
|
||||||
ResetChallenge(*pblock, *pindexPrev, chainparams.GetConsensus());
|
ResetChallenge(*pblock, *pindexPrev, chainparams.GetConsensus());
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -45,9 +45,9 @@ public:
|
||||||
};
|
};
|
||||||
|
|
||||||
template<typename T>
|
template<typename T>
|
||||||
bool GenericVerifyScript(const CScript& scriptSig, const CScript& scriptPubKey, unsigned int flags, const T& data)
|
bool GenericVerifyScript(const CScript& scriptSig, const CScriptWitness& witness, const CScript& scriptPubKey, unsigned int flags, const T& data)
|
||||||
{
|
{
|
||||||
return VerifyScript(scriptSig, scriptPubKey, NULL, flags, SimpleSignatureChecker(SerializeHash(data)));
|
return VerifyScript(scriptSig, scriptPubKey, &witness, flags, SimpleSignatureChecker(SerializeHash(data)));
|
||||||
}
|
}
|
||||||
|
|
||||||
template<typename T>
|
template<typename T>
|
||||||
|
|
|
||||||
|
|
@ -335,6 +335,11 @@ std::string CScriptWitness::ToString() const
|
||||||
return ret + ")";
|
return ret + ")";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint32_t CScriptWitness::GetSerializedSize() const
|
||||||
|
{
|
||||||
|
return ::GetSerializeSize(stack, 0);
|
||||||
|
}
|
||||||
|
|
||||||
bool CScript::HasValidOps() const
|
bool CScript::HasValidOps() const
|
||||||
{
|
{
|
||||||
CScript::const_iterator it = begin();
|
CScript::const_iterator it = begin();
|
||||||
|
|
|
||||||
|
|
@ -603,6 +603,8 @@ struct CScriptWitness
|
||||||
void SetNull() { stack.clear(); stack.shrink_to_fit(); }
|
void SetNull() { stack.clear(); stack.shrink_to_fit(); }
|
||||||
|
|
||||||
std::string ToString() const;
|
std::string ToString() const;
|
||||||
|
|
||||||
|
uint32_t GetSerializedSize() const;
|
||||||
};
|
};
|
||||||
|
|
||||||
class CReserveScript
|
class CReserveScript
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue