Repository navigation
dash-spv: support Dash Core's devnet LLMQ routing overrides (-llmqchainlocks / -llmqinstantsenddip0024 / -llmqplatform) #785
Description
Background
PR #784 adds -llmqdevnetparams=<size>:<threshold> support, which faithfully mirrors Dash Core's flag of the same name. In Dash Core, that flag only adjusts the size/threshold of LLMQ_DEVNET (type 101) — confirmed in chainparams.cpp:
auto params = std::ranges::find_if(consensus.llmqs, [](const auto& llmq){
return llmq.type == Consensus::LLMQType::LLMQ_DEVNET;}); // only 101LLMQ_DEVNET_DIP0024 (105) and LLMQ_DEVNET_PLATFORM (107) keep their hardcoded defaults regardless of that flag.
The gap
Dash Core ships three companion flags that small devnets routinely rely on (declared in chainparams.cpp):
-llmqchainlocks=<quorum name> (default: llmq_devnet)
-llmqinstantsenddip0024=<quorum name> (default: llmq_devnet_dip0024)
-llmqplatform=<quorum name> (default: llmq_devnet_platform)
These don't change a quorum's size — they change which LLMQ type fulfills each role. The typical small-devnet recipe is to shrink LLMQ_DEVNET (via -llmqdevnetparams) to fit the masternode count, then reroute ChainLocks / InstantSend DIP24 / Platform onto it, because the default 105/107 quorums (8 and 12 members) can't form on a small MN set.
In rust-dashcore today, the routing is hardcoded in dash/src/sml/llmq_type/network.rs:
fn is_llmq_type(&self) -> LLMQType { ... Network::Devnet => LlmqtypeDevnet, ... }
fn isd_llmq_type(&self) -> LLMQType { ... Network::Devnet => LlmqtypeDevnetDIP0024, ... }
fn chain_locks_type(&self) -> LLMQType { ... Network::Devnet => LlmqtypeDevnet, ... }
fn platform_type(&self) -> LLMQType { ... Network::Devnet => LlmqtypeDevnetPlatform, ... }Consequence: an SPV client talking to a devnet started with, say, -llmqinstantsenddip0024=llmq_devnet will keep hunting for LlmqtypeDevnetDIP0024 quorums, find none, and silently fail to verify InstantSend locks. Same story for rerouted ChainLocks / Platform.
Proposed solution
Allow per-instance overrides of the four NetworkLLMQExt lookups on devnet, surfaced through ClientConfig and the CLI.
ClientConfig (dash-spv)
pub struct ClientConfig {
// ...
pub llmq_devnet_params: Option<LlmqDevnetParams>, // already in PR #784
pub llmq_chainlocks_type: Option<LLMQType>, // new
pub llmq_instantsend_dip0024_type: Option<LLMQType>, // new
pub llmq_platform_type: Option<LLMQType>, // new
// (and a builder method for each — Devnet-only validation, same as llmq_devnet_params)
}CLI (dash-spv binary)
--llmq-chainlocks=<quorum-name>
--llmq-instantsend-dip0024=<quorum-name>
--llmq-platform=<quorum-name>
Mirroring Dash Core's flag names. Quorum name strings should accept llmq_devnet, llmq_devnet_dip0024, llmq_devnet_platform at minimum (the set of LLMQ types valid on devnet).
Routing change
NetworkLLMQExt currently takes &self (a Network). The cleanest way to thread overrides through is to either:
- Option A — add a
NetworkLLMQContext { network: Network, overrides: DevnetRouting }and have callers use that instead ofNetwork. Clean, but touches many call sites. - Option B — apply the same
OnceLockglobal-override pattern PR feat: devnet support fordash-spv#784 introduced forLLMQ_DEVNETparams:set_devnet_chainlocks_type(t),set_devnet_isd_type(t),set_devnet_platform_type(t). Smaller diff, idempotent contract is already established. Tradeoff: same process-global limitation as the existing override.
Option B is consistent with what's already there and probably the right pragmatic call.
Out of scope
- Changes to mainnet/testnet/regtest routing — these flags are devnet-only in Dash Core.
- Per-quorum size overrides beyond
LLMQ_DEVNET— Dash Core itself doesn't expose those.
Acceptance criteria
- CLI accepts the three flags; rejected on non-devnet networks
-
ClientConfigcarries the overrides through to startup -
chain_locks_type/isd_llmq_type/platform_typereturn the overridden values when set -
enabled_llmq_typesincludes the overridden types - Unit tests cover override-set / override-unset / cross-network rejection
- Existing PR feat: devnet support for
dash-spv#784 test (test_llmq_devnet_override_lifecycle) stays green
References
- Dash Core flag declarations:
chainparams.cpparg registration (search for-llmqchainlocks,-llmqinstantsenddip0024,-llmqplatform) - PR feat: devnet support for
dash-spv#784 — initial-llmqdevnetparamssupport - Original observation by @QuantumExplorer on feat: devnet support for
dash-spv#784
Activity