From 5eef742e0d8a04e06689d70d2c9fd38b67dfb879 Mon Sep 17 00:00:00 2001 From: Serban Iorga Date: Tue, 26 May 2026 10:10:03 +0300 Subject: [PATCH 01/10] Fix cumulus test runtime --- cumulus/test/runtime/src/lib.rs | 6 +++--- .../zombienet-sdk-tests/tests/functional/scheduling_v3.rs | 4 ++-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/cumulus/test/runtime/src/lib.rs b/cumulus/test/runtime/src/lib.rs index 458412423fee4..1a79ccb752518 100644 --- a/cumulus/test/runtime/src/lib.rs +++ b/cumulus/test/runtime/src/lib.rs @@ -170,12 +170,12 @@ pub const BLOCK_PROCESSING_VELOCITY: u32 = 3; )))] pub const BLOCK_PROCESSING_VELOCITY: u32 = 1; -#[cfg(feature = "async-backing")] -const UNINCLUDED_SEGMENT_CAPACITY: u32 = 3; - #[cfg(all(feature = "sync-backing", not(feature = "async-backing")))] const UNINCLUDED_SEGMENT_CAPACITY: u32 = 1; +#[cfg(feature = "async-backing")] +const UNINCLUDED_SEGMENT_CAPACITY: u32 = 3 + RELAY_PARENT_OFFSET; + /// We need `VELOCITY * 3`, because the block flow is the following: /// /// - Collator produces the block(s) on relay chain block `X` diff --git a/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs b/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs index 8f8d52c1265e4..fd4c3bdc3b30d 100644 --- a/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs +++ b/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs @@ -125,8 +125,8 @@ async fn scheduling_v2_and_v3_collator_with_v3_validators( // Verify both V3 and V2 candidates are backed in the same relay chain block window. let expected_v3_throughput = match para_chain { - "async-backing-v3" => 15..21, - "async-backing-v3-rpo" => 8..21, + "async-backing-v3" => 18..21, + "async-backing-v3-rpo" => 13..21, _ => unreachable!("unexpected para_chain"), }; assert_para_throughput_with( From cecd9ca5c927afa1b21974672716b1b11ea3443f Mon Sep 17 00:00:00 2001 From: Serban Iorga Date: Fri, 29 May 2026 12:08:44 +0300 Subject: [PATCH 02/10] cumulus test runtime: remove unneeded flavor --- cumulus/test/runtime/Cargo.toml | 2 +- cumulus/test/runtime/build.rs | 6 ------ cumulus/test/runtime/src/lib.rs | 6 +----- cumulus/test/service/src/chain_spec.rs | 10 ---------- cumulus/test/service/src/cli.rs | 6 +++--- .../zombienet-sdk/tests/zombie_ci/runtime_upgrade.rs | 2 +- polkadot/node/core/provisioner/src/tests.rs | 2 +- polkadot/runtime/parachains/src/inclusion/tests.rs | 2 +- .../tests/elastic_scaling/slot_based_3cores.rs | 4 ---- 9 files changed, 8 insertions(+), 32 deletions(-) diff --git a/cumulus/test/runtime/Cargo.toml b/cumulus/test/runtime/Cargo.toml index 7bbfca60d84de..4ff46d3e10965 100644 --- a/cumulus/test/runtime/Cargo.toml +++ b/cumulus/test/runtime/Cargo.toml @@ -103,7 +103,7 @@ std = [ "tracing/std", ] increment-spec-version = [] -# A runtime which expects to build behind the relay chain tip. +# A runtime that uses a relay parent offset of 2. relay-parent-offset = [] # A runtime with elastic-scaling configuration. elastic-scaling = [] diff --git a/cumulus/test/runtime/build.rs b/cumulus/test/runtime/build.rs index 68227838e3824..6e8790d16a257 100644 --- a/cumulus/test/runtime/build.rs +++ b/cumulus/test/runtime/build.rs @@ -28,12 +28,6 @@ fn main() { .set_file_name("wasm_binary_spec_version_incremented.rs") .build(); - WasmBuilder::init_with_defaults() - .enable_feature("elastic-scaling") - .import_memory() - .set_file_name("wasm_binary_elastic_scaling_mvp.rs") - .build(); - WasmBuilder::new() .with_current_project() .enable_feature("elastic-scaling") diff --git a/cumulus/test/runtime/src/lib.rs b/cumulus/test/runtime/src/lib.rs index 1a79ccb752518..8040a13de09c0 100644 --- a/cumulus/test/runtime/src/lib.rs +++ b/cumulus/test/runtime/src/lib.rs @@ -22,7 +22,7 @@ #[cfg(feature = "std")] include!(concat!(env!("OUT_DIR"), "/wasm_binary.rs")); -pub mod wasm_spec_version_incremented { +pub mod spec_version_incremented { #[cfg(feature = "std")] include!(concat!(env!("OUT_DIR"), "/wasm_binary_spec_version_incremented.rs")); } @@ -36,10 +36,6 @@ pub mod elastic_scaling_500ms { #[cfg(feature = "std")] include!(concat!(env!("OUT_DIR"), "/wasm_binary_elastic_scaling_500ms.rs")); } -pub mod elastic_scaling_mvp { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_elastic_scaling_mvp.rs")); -} pub mod elastic_scaling { #[cfg(feature = "std")] diff --git a/cumulus/test/service/src/chain_spec.rs b/cumulus/test/service/src/chain_spec.rs index 1c38dc2ebe4ea..d05401d22f715 100644 --- a/cumulus/test/service/src/chain_spec.rs +++ b/cumulus/test/service/src/chain_spec.rs @@ -115,16 +115,6 @@ pub fn get_elastic_scaling_500ms_chain_spec(id: Option) -> GenericChainS ) } -/// Get the chain spec for a specific parachain ID. -pub fn get_elastic_scaling_mvp_chain_spec(id: Option) -> GenericChainSpec { - get_chain_spec_with_extra_endowed( - id, - Default::default(), - cumulus_test_runtime::elastic_scaling_mvp::WASM_BINARY - .expect("WASM binary was not built, please build it!"), - ) -} - pub fn get_block_bundling_chain_spec(id: Option) -> GenericChainSpec { get_chain_spec_with_extra_endowed( id, diff --git a/cumulus/test/service/src/cli.rs b/cumulus/test/service/src/cli.rs index 7c293b3982f88..9269df83d962a 100644 --- a/cumulus/test/service/src/cli.rs +++ b/cumulus/test/service/src/cli.rs @@ -290,9 +290,9 @@ impl SubstrateCli for TestCollatorCli { }, "elastic-scaling-mvp" => { tracing::info!("Using elastic-scaling mvp chain spec."); - Box::new(cumulus_test_service::get_elastic_scaling_mvp_chain_spec(Some( - ParaId::from(2100), - ))) as Box<_> + Box::new(cumulus_test_service::get_elastic_scaling_chain_spec(Some(ParaId::from( + 2100, + )))) as Box<_> }, "elastic-scaling" => { tracing::info!("Using elastic-scaling chain spec."); diff --git a/cumulus/zombienet/zombienet-sdk/tests/zombie_ci/runtime_upgrade.rs b/cumulus/zombienet/zombienet-sdk/tests/zombie_ci/runtime_upgrade.rs index 24b18d2728bb8..ce82125caed7b 100644 --- a/cumulus/zombienet/zombienet-sdk/tests/zombie_ci/runtime_upgrade.rs +++ b/cumulus/zombienet/zombienet-sdk/tests/zombie_ci/runtime_upgrade.rs @@ -3,7 +3,7 @@ use crate::utils::initialize_network; use anyhow::anyhow; -use cumulus_test_runtime::wasm_spec_version_incremented::WASM_BINARY as WASM_RUNTIME_UPGRADE; +use cumulus_test_runtime::spec_version_incremented::WASM_BINARY as WASM_RUNTIME_UPGRADE; use cumulus_zombienet_sdk_helpers::{ assert_para_throughput, submit_sudo_runtime_upgrade, wait_for_pvf_prepare, wait_for_runtime_upgrade, diff --git a/polkadot/node/core/provisioner/src/tests.rs b/polkadot/node/core/provisioner/src/tests.rs index 92f9cebd4593c..761cb657ea3f7 100644 --- a/polkadot/node/core/provisioner/src/tests.rs +++ b/polkadot/node/core/provisioner/src/tests.rs @@ -902,7 +902,7 @@ mod select_candidates { } #[test] - fn multiple_cores_per_para_elastic_scaling_mvp() { + fn multiple_cores_per_para_elastic_scaling() { let mock_cores = mock_availability_cores_multiple_per_para(); // why those particular indices? see the comments on mock_availability_cores() diff --git a/polkadot/runtime/parachains/src/inclusion/tests.rs b/polkadot/runtime/parachains/src/inclusion/tests.rs index c191bee5cebf8..2890fe9b8f3b1 100644 --- a/polkadot/runtime/parachains/src/inclusion/tests.rs +++ b/polkadot/runtime/parachains/src/inclusion/tests.rs @@ -2082,7 +2082,7 @@ fn backing_works() { } #[test] -fn backing_works_with_elastic_scaling_mvp() { +fn backing_works_with_elastic_scaling() { let chain_a = ParaId::from(1_u32); let chain_b = ParaId::from(2_u32); let thread_a = ParaId::from(3_u32); diff --git a/polkadot/zombienet-sdk-tests/tests/elastic_scaling/slot_based_3cores.rs b/polkadot/zombienet-sdk-tests/tests/elastic_scaling/slot_based_3cores.rs index 02ab00091560c..aaa513dd72136 100644 --- a/polkadot/zombienet-sdk-tests/tests/elastic_scaling/slot_based_3cores.rs +++ b/polkadot/zombienet-sdk-tests/tests/elastic_scaling/slot_based_3cores.rs @@ -54,8 +54,6 @@ async fn slot_based_3cores_test() -> Result<(), anyhow::Error> { }) }) .with_parachain(|p| { - // Para 2100 uses the old elastic scaling mvp, which doesn't send the new UMP signal - // commitment for selecting the core index. p.with_id(2100) .with_default_command("test-parachain") .with_default_image(images.cumulus.as_str()) @@ -67,8 +65,6 @@ async fn slot_based_3cores_test() -> Result<(), anyhow::Error> { .with_collator(|n| n.with_name("collator-elastic-mvp")) }) .with_parachain(|p| { - // Para 2200 uses the new RFC103-enabled collator which sends the UMP signal commitment - // for selecting the core index p.with_id(2200) .with_default_command("test-parachain") .with_default_image(images.cumulus.as_str()) From f5d4e862ad43e83ae6b47a9680f1fc9acb19e9f8 Mon Sep 17 00:00:00 2001 From: Serban Iorga Date: Fri, 29 May 2026 18:20:34 +0300 Subject: [PATCH 03/10] cumulus test runtime: cleanup configs --- cumulus/test/runtime/Cargo.toml | 30 +++---- cumulus/test/runtime/build.rs | 75 +++++++--------- cumulus/test/runtime/src/lib.rs | 150 +++++++++++++++----------------- 3 files changed, 115 insertions(+), 140 deletions(-) diff --git a/cumulus/test/runtime/Cargo.toml b/cumulus/test/runtime/Cargo.toml index 4ff46d3e10965..64ebc8a8d862c 100644 --- a/cumulus/test/runtime/Cargo.toml +++ b/cumulus/test/runtime/Cargo.toml @@ -102,24 +102,18 @@ std = [ "substrate-wasm-builder", "tracing/std", ] + increment-spec-version = [] -# A runtime that uses a relay parent offset of 2. -relay-parent-offset = [] -# A runtime with elastic-scaling configuration. -elastic-scaling = [] -# A runtime with low slot duration of 500ms for low-latency testing with 12 cores. -elastic-scaling-500ms = [] -# A runtime with a slot duration of 6s but parameters that allow multiple blocks per slot. -elastic-scaling-multi-block-slot = [] -# A runtime that uses block-bundling. -block-bundling = [] -# A runtime with 12s slot duration which only authors one block per slot. + +12s-slot = [] +18s-slot = [] + sync-backing = [] -# A runtime with 6s slot duration which only authors one block per slot. -async-backing = [] -# A runtime that uses `CandidateDescriptorV3`. +velocity-3 = [] +velocity-6 = [] +velocity-12 = [] +fallback-target-block-rate = [] + +relay-parent-offset-2 = [] + v3-descriptor = [] -# An elastic scaling runtime with 12s slots. -elastic-scaling-12s-slot = [] -# A runtime with 18s slot duration with increased spec version for runtime upgrade testing. -slot-duration-18s = ["increment-spec-version"] diff --git a/cumulus/test/runtime/build.rs b/cumulus/test/runtime/build.rs index 6e8790d16a257..b8baa4cc1d898 100644 --- a/cumulus/test/runtime/build.rs +++ b/cumulus/test/runtime/build.rs @@ -18,69 +18,61 @@ fn main() { use substrate_wasm_builder::WasmBuilder; - WasmBuilder::init_with_defaults() - .enable_feature("async-backing") - .import_memory() - .build(); + // A runtime with 6s slot duration which only authors one block per slot. + WasmBuilder::init_with_defaults().build(); WasmBuilder::init_with_defaults() .enable_feature("increment-spec-version") .set_file_name("wasm_binary_spec_version_incremented.rs") .build(); - WasmBuilder::new() - .with_current_project() - .enable_feature("elastic-scaling") - .import_memory() + WasmBuilder::init_with_defaults() + .enable_feature("velocity-3") + .enable_feature("increment-spec-version") + .enable_feature("fallback-target-block-rate") .set_file_name("wasm_binary_elastic_scaling.rs") .build(); - WasmBuilder::new() - .with_current_project() - .enable_feature("elastic-scaling-500ms") - .import_memory() + // A runtime with low slot duration of 500ms for low-latency testing with 12 cores. + WasmBuilder::init_with_defaults() + .enable_feature("velocity-12") .set_file_name("wasm_binary_elastic_scaling_500ms.rs") .build(); - WasmBuilder::new() - .with_current_project() - .enable_feature("elastic-scaling-multi-block-slot") - .import_memory() + // A runtime with a slot duration of 6s but parameters that allow multiple blocks per slot. + WasmBuilder::init_with_defaults() + .enable_feature("velocity-6") .set_file_name("wasm_binary_elastic_scaling_multi_block_slot.rs") .build(); - WasmBuilder::new() - .with_current_project() - .enable_feature("relay-parent-offset") - .import_memory() + // A runtime that uses a relay parent offset of 2. + WasmBuilder::init_with_defaults() + .enable_feature("relay-parent-offset-2") .set_file_name("wasm_binary_relay_parent_offset.rs") .build(); - WasmBuilder::new() - .with_current_project() + WasmBuilder::init_with_defaults() .enable_feature("sync-backing") - .import_memory() + .enable_feature("12s-slot") .set_file_name("wasm_binary_sync_backing.rs") .build(); - WasmBuilder::new() - .with_current_project() - .enable_feature("elastic-scaling-12s-slot") - .enable_feature("elastic-scaling") - .import_memory() + // An elastic scaling runtime with 12s slots. + WasmBuilder::init_with_defaults() + .enable_feature("12s-slot") + .enable_feature("velocity-3") + .enable_feature("fallback-target-block-rate") + .enable_feature("increment-spec-version") .set_file_name("wasm_binary_elastic_scaling_12s_slot.rs") .build(); - WasmBuilder::new() - .with_current_project() - .enable_feature("block-bundling") - .import_memory() + // A runtime that uses block-bundling. + WasmBuilder::init_with_defaults() + .enable_feature("velocity-12") .set_file_name("wasm_binary_block_bundling.rs") .build(); - WasmBuilder::new() - .with_current_project() - .enable_feature("async-backing") + WasmBuilder::init_with_defaults() .enable_feature("v3-descriptor") .import_memory() .set_file_name("wasm_binary_async_backing_v3.rs") @@ -88,23 +80,20 @@ fn main() { WasmBuilder::new() .with_current_project() - .enable_feature("async-backing") .enable_feature("v3-descriptor") - .enable_feature("relay-parent-offset") - .import_memory() + .enable_feature("relay-parent-offset-2") .set_file_name("wasm_binary_async_backing_v3_rpo.rs") .build(); - WasmBuilder::new() - .with_current_project() - .enable_feature("elastic-scaling") + WasmBuilder::init_with_defaults() .enable_feature("v3-descriptor") - .import_memory() + .enable_feature("velocity-3") .set_file_name("wasm_binary_elastic_scaling_v3.rs") .build(); + // A runtime with 18s slot duration with increased spec version for runtime upgrade testing. WasmBuilder::init_with_defaults() - .enable_feature("slot-duration-18s") + .enable_feature("18s-slot") .enable_feature("increment-spec-version") .set_file_name("wasm_binary_slot_duration_18s.rs") .build(); diff --git a/cumulus/test/runtime/src/lib.rs b/cumulus/test/runtime/src/lib.rs index 8040a13de09c0..e32eb8e309986 100644 --- a/cumulus/test/runtime/src/lib.rs +++ b/cumulus/test/runtime/src/lib.rs @@ -145,59 +145,62 @@ impl_opaque_keys! { /// The para-id used in this runtime. pub const PARACHAIN_ID: u32 = 100; -#[cfg(any(feature = "elastic-scaling-500ms", feature = "block-bundling"))] -pub const BLOCK_PROCESSING_VELOCITY: u32 = 12; - -#[cfg(all(feature = "elastic-scaling-multi-block-slot", not(feature = "elastic-scaling-500ms")))] -pub const BLOCK_PROCESSING_VELOCITY: u32 = 6; - -#[cfg(all( - feature = "elastic-scaling", - not(feature = "elastic-scaling-500ms"), - not(feature = "elastic-scaling-multi-block-slot") -))] -pub const BLOCK_PROCESSING_VELOCITY: u32 = 3; - -#[cfg(not(any( - feature = "elastic-scaling", - feature = "elastic-scaling-500ms", - feature = "elastic-scaling-multi-block-slot", - feature = "block-bundling", -)))] -pub const BLOCK_PROCESSING_VELOCITY: u32 = 1; - -#[cfg(all(feature = "sync-backing", not(feature = "async-backing")))] -const UNINCLUDED_SEGMENT_CAPACITY: u32 = 1; - -#[cfg(feature = "async-backing")] -const UNINCLUDED_SEGMENT_CAPACITY: u32 = 3 + RELAY_PARENT_OFFSET; - -/// We need `VELOCITY * 3`, because the block flow is the following: -/// -/// - Collator produces the block(s) on relay chain block `X` -/// - In the mean time the relay chain is building block `X + 1` -/// - The collator sends the collation to the relay chain and it gets backed on chain in relay block -/// `X + 2` -/// - The collation then gets included on chain in relay block `X + 3` -/// - As we are building on `RELAY_PARENT_OFFSET` old relay parents, the included block from the -/// parachain is also `RELAY_PARENT_OFFSET` relay blocks older (one relay block may contains -/// multiple parachain blocks). -#[cfg(all(not(feature = "sync-backing"), not(feature = "async-backing")))] -const UNINCLUDED_SEGMENT_CAPACITY: u32 = BLOCK_PROCESSING_VELOCITY * (3 + RELAY_PARENT_OFFSET); - -#[cfg(feature = "slot-duration-18s")] -pub const SLOT_DURATION: u64 = 18000; -#[cfg(all( - any(feature = "sync-backing", feature = "elastic-scaling-12s-slot"), - not(feature = "slot-duration-18s") -))] -pub const SLOT_DURATION: u64 = 12000; -#[cfg(not(any( - feature = "sync-backing", - feature = "elastic-scaling-12s-slot", - feature = "slot-duration-18s" -)))] -pub const SLOT_DURATION: u64 = 6000; +const SCHEDULING_V3_ENABLED: bool = cfg!(feature = "v3-descriptor"); + +const fn relay_parent_offset() -> u32 { + if cfg!(feature = "relay-parent-offset-2") { + return 2; + } + + 0 +} + +const fn slot_duration() -> u64 { + if cfg!(feature = "18s-slot") { + return 18000; + } + + if cfg!(feature = "12s-slot") { + return 12000; + } + + 6000 +} + +const fn block_processing_velocity() -> u32 { + if cfg!(feature = "velocity-12") { + return 12; + } + + if cfg!(feature = "velocity-6") { + return 6; + } + + if cfg!(feature = "velocity-3") { + return 3; + } + + 1 +} + +const fn unincluded_segment_capacity() -> u32 { + if cfg!(feature = "sync-backing") { + return 1; + } + + // Without sync backing, the block flow is the following: + // + // - Collator produces the block(s) on relay chain block `X` + // - In the meantime the relay chain is building block `X + 1` + // - The collator sends the collation to the relay chain, and it gets backed on chain in relay + // block `X + 2` + // - The collation then gets included on chain in relay block `X + 3` + // - As we are building on `RELAY_PARENT_OFFSET` old relay parents, the included block from the + // parachain is also `RELAY_PARENT_OFFSET` relay blocks older (one relay block may contain + // multiple parachain blocks). + block_processing_velocity() * (3 + relay_parent_offset()) +} +const UNINCLUDED_SEGMENT_CAPACITY: u32 = unincluded_segment_capacity(); const RELAY_CHAIN_SLOT_DURATION_MILLIS: u32 = 6000; @@ -212,7 +215,7 @@ const RELAY_CHAIN_SLOT_DURATION_MILLIS: u32 = 6000; // details. Since macro kicks in early, it operates on AST. Thus you cannot use constants. // Macros are expanded top to bottom, meaning we also cannot use `cfg` here. -#[cfg(all(not(feature = "increment-spec-version"), not(feature = "elastic-scaling")))] +#[cfg(not(feature = "increment-spec-version"))] #[sp_version::runtime_version] pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("cumulus-test-parachain"), @@ -226,7 +229,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { system_version: 3, }; -#[cfg(any(feature = "increment-spec-version", feature = "elastic-scaling"))] +#[cfg(feature = "increment-spec-version")] #[sp_version::runtime_version] pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("cumulus-test-parachain"), @@ -243,7 +246,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { pub const EPOCH_DURATION_IN_BLOCKS: u32 = 10 * MINUTES; // These time units are defined in number of blocks. -pub const MINUTES: BlockNumber = 60_000 / (SLOT_DURATION as BlockNumber); +pub const MINUTES: BlockNumber = 60_000 / (slot_duration() as BlockNumber); pub const HOURS: BlockNumber = MINUTES * 60; pub const DAYS: BlockNumber = HOURS * 24; @@ -265,7 +268,7 @@ const NORMAL_DISPATCH_RATIO: Perbill = Perbill::from_percent(75); type MaximumBlockWeight = cumulus_pallet_parachain_system::block_weight::MaxParachainBlockWeight< Runtime, - ConstU32, + ConstU32<{ block_processing_velocity() }>, >; parameter_types! { @@ -319,7 +322,7 @@ impl frame_system::Config for Runtime { type MaxConsumers = frame_support::traits::ConstU32<16>; type PreInherents = cumulus_pallet_parachain_system::block_weight::DynamicMaxBlockWeightHooks< Runtime, - ConstU32, + ConstU32<{ block_processing_velocity() }>, >; type SingleBlockMigrations = SingleBlockMigrations; } @@ -404,14 +407,6 @@ impl pallet_glutton::Config for Runtime { type WeightInfo = pallet_glutton::weights::SubstrateWeight; } -#[cfg(feature = "relay-parent-offset")] -const RELAY_PARENT_OFFSET: u32 = 2; - -#[cfg(not(feature = "relay-parent-offset"))] -const RELAY_PARENT_OFFSET: u32 = 0; - -const SCHEDULING_V3_ENABLED: bool = cfg!(feature = "v3-descriptor"); - /// Scheduling-info verifier used by `cumulus-test-runtime`. /// /// Accepts any signature; `V3_SCHEDULING_ENABLED` is gated on the `v3-descriptor` cargo @@ -433,7 +428,7 @@ impl VerifySchedulingSignature for NoVerification { type ConsensusHook = cumulus_pallet_aura_ext::FixedVelocityConsensusHook< Runtime, RELAY_CHAIN_SLOT_DURATION_MILLIS, - BLOCK_PROCESSING_VELOCITY, + { block_processing_velocity() }, UNINCLUDED_SEGMENT_CAPACITY, >; impl cumulus_pallet_parachain_system::Config for Runtime { @@ -450,7 +445,7 @@ impl cumulus_pallet_parachain_system::Config for Runtime { type CheckAssociatedRelayNumber = cumulus_pallet_parachain_system::RelayNumberMonotonicallyIncreases; type ConsensusHook = ConsensusHook; - type RelayParentOffset = ConstU32; + type RelayParentOffset = ConstU32<{ relay_parent_offset() }>; type SchedulingSignatureVerifier = NoVerification; } @@ -460,11 +455,8 @@ impl pallet_aura::Config for Runtime { type AuthorityId = AuraId; type DisabledValidators = (); type MaxAuthorities = ConstU32<32>; - #[cfg(feature = "sync-backing")] - type AllowMultipleBlocksPerSlot = ConstBool; - #[cfg(not(feature = "sync-backing"))] - type AllowMultipleBlocksPerSlot = ConstBool; - type SlotDuration = ConstU64; + type AllowMultipleBlocksPerSlot = ConstBool<{ !cfg!(feature = "sync-backing") }>; + type SlotDuration = ConstU64<{ slot_duration() }>; } impl test_pallet::Config for Runtime {} @@ -531,7 +523,7 @@ pub type TxExtension = cumulus_pallet_parachain_system::block_weight::DynamicMax test_pallet::TestTransactionExtension, ), >, - ConstU32, + ConstU32<{ block_processing_velocity() }>, >; /// Unchecked extrinsic type as expected by this runtime. @@ -607,7 +599,7 @@ impl_runtime_apis! { impl cumulus_primitives_core::RelayParentOffsetApi for Runtime { fn relay_parent_offset() -> u32 { - RELAY_PARENT_OFFSET + relay_parent_offset() } fn max_claim_queue_offset() -> u8 { @@ -623,7 +615,7 @@ impl_runtime_apis! { impl sp_consensus_aura::AuraApi for Runtime { fn slot_duration() -> sp_consensus_aura::SlotDuration { - sp_consensus_aura::SlotDuration::from_millis(SLOT_DURATION) + sp_consensus_aura::SlotDuration::from_millis(slot_duration()) } fn authorities() -> Vec { @@ -732,11 +724,11 @@ impl_runtime_apis! { } } - // "Elastic scaling" should run with the fallback method. - #[cfg(any(not(feature = "elastic-scaling"), feature = "std"))] + // Some runtimes should run with the fallback method. + #[cfg(any(not(feature = "fallback-target-block-rate"), feature = "std"))] impl cumulus_primitives_core::TargetBlockRate for Runtime { fn target_block_rate() -> u32 { - BLOCK_PROCESSING_VELOCITY + block_processing_velocity() } } From 6b729ef11f04ecdaf525c241014548ddb19d4cc8 Mon Sep 17 00:00:00 2001 From: Serban Iorga Date: Sat, 30 May 2026 10:43:47 +0300 Subject: [PATCH 04/10] Remove "fallback-target-block-rate" feature --- cumulus/test/runtime/Cargo.toml | 1 - cumulus/test/runtime/build.rs | 2 -- cumulus/test/runtime/src/lib.rs | 2 -- 3 files changed, 5 deletions(-) diff --git a/cumulus/test/runtime/Cargo.toml b/cumulus/test/runtime/Cargo.toml index 64ebc8a8d862c..0dec519f54189 100644 --- a/cumulus/test/runtime/Cargo.toml +++ b/cumulus/test/runtime/Cargo.toml @@ -112,7 +112,6 @@ sync-backing = [] velocity-3 = [] velocity-6 = [] velocity-12 = [] -fallback-target-block-rate = [] relay-parent-offset-2 = [] diff --git a/cumulus/test/runtime/build.rs b/cumulus/test/runtime/build.rs index b8baa4cc1d898..51ea88c9ca40d 100644 --- a/cumulus/test/runtime/build.rs +++ b/cumulus/test/runtime/build.rs @@ -29,7 +29,6 @@ fn main() { WasmBuilder::init_with_defaults() .enable_feature("velocity-3") .enable_feature("increment-spec-version") - .enable_feature("fallback-target-block-rate") .set_file_name("wasm_binary_elastic_scaling.rs") .build(); @@ -61,7 +60,6 @@ fn main() { WasmBuilder::init_with_defaults() .enable_feature("12s-slot") .enable_feature("velocity-3") - .enable_feature("fallback-target-block-rate") .enable_feature("increment-spec-version") .set_file_name("wasm_binary_elastic_scaling_12s_slot.rs") .build(); diff --git a/cumulus/test/runtime/src/lib.rs b/cumulus/test/runtime/src/lib.rs index e32eb8e309986..8e48c80862023 100644 --- a/cumulus/test/runtime/src/lib.rs +++ b/cumulus/test/runtime/src/lib.rs @@ -724,8 +724,6 @@ impl_runtime_apis! { } } - // Some runtimes should run with the fallback method. - #[cfg(any(not(feature = "fallback-target-block-rate"), feature = "std"))] impl cumulus_primitives_core::TargetBlockRate for Runtime { fn target_block_rate() -> u32 { block_processing_velocity() From e6f3a747ba089b6cd06f741712fddf9010ac1a30 Mon Sep 17 00:00:00 2001 From: Serban Iorga Date: Tue, 2 Jun 2026 14:27:47 +0300 Subject: [PATCH 05/10] CR comments --- cumulus/test/runtime/Cargo.toml | 14 ++ cumulus/test/runtime/build.rs | 3 +- cumulus/test/runtime/src/flavors.rs | 128 ++++++++++++++++++ cumulus/test/runtime/src/lib.rs | 121 +---------------- .../tests/functional/scheduling_v3.rs | 2 +- 5 files changed, 148 insertions(+), 120 deletions(-) create mode 100644 cumulus/test/runtime/src/flavors.rs diff --git a/cumulus/test/runtime/Cargo.toml b/cumulus/test/runtime/Cargo.toml index 0dec519f54189..4860062ac82cb 100644 --- a/cumulus/test/runtime/Cargo.toml +++ b/cumulus/test/runtime/Cargo.toml @@ -105,14 +105,28 @@ std = [ increment-spec-version = [] +# The default parachain slot duration is 6s. The following features can be used to change this value: +# Change the parachain slot duration to 12s 12s-slot = [] +# Change the parachain slot duration to 12s 18s-slot = [] +# Configure the runtime to use sync backing. More specifically, this leads to: +# - setting `AllowMultipleBlocksPerSlot` to `false` +# - setting the unincluded segment capacity to 1 sync-backing = [] + +# The default block processing velocity is 1. The following features can be used to change this value: +# Change the block processing velocity to 3 velocity-3 = [] +# Change the block processing velocity to 6 velocity-6 = [] +# Change the block processing velocity to 12 velocity-12 = [] +# The default relay parent offset is 0. The following features can be used to change this value: +# Change the relay parent offset to 2 relay-parent-offset-2 = [] +# Configure the runtiem to use scheduling V3 v3-descriptor = [] diff --git a/cumulus/test/runtime/build.rs b/cumulus/test/runtime/build.rs index 51ea88c9ca40d..5928bf9c40981 100644 --- a/cumulus/test/runtime/build.rs +++ b/cumulus/test/runtime/build.rs @@ -32,7 +32,8 @@ fn main() { .set_file_name("wasm_binary_elastic_scaling.rs") .build(); - // A runtime with low slot duration of 500ms for low-latency testing with 12 cores. + // A runtime with 6s slots and block velocity 12. + // Coupled with 12 cores it can produce a block every 500ms. WasmBuilder::init_with_defaults() .enable_feature("velocity-12") .set_file_name("wasm_binary_elastic_scaling_500ms.rs") diff --git a/cumulus/test/runtime/src/flavors.rs b/cumulus/test/runtime/src/flavors.rs new file mode 100644 index 0000000000000..60faebe4bda67 --- /dev/null +++ b/cumulus/test/runtime/src/flavors.rs @@ -0,0 +1,128 @@ +// Copyright (C) Parity Technologies (UK) Ltd. +// This file is part of Cumulus. + +// Cumulus is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. + +// Cumulus 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 General Public License for more details. + +// You should have received a copy of the GNU General Public License +// along with Cumulus. If not, see . + +pub mod spec_version_incremented { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_spec_version_incremented.rs")); +} + +pub mod relay_parent_offset { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_relay_parent_offset.rs")); +} + +pub mod elastic_scaling_500ms { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_elastic_scaling_500ms.rs")); +} + +pub mod elastic_scaling { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_elastic_scaling.rs")); +} + +pub mod elastic_scaling_12s_slot { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_elastic_scaling_12s_slot.rs")); +} + +pub mod block_bundling { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_block_bundling.rs")); +} + +pub mod sync_backing { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_sync_backing.rs")); +} + +pub mod async_backing { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary.rs")); +} + +pub mod async_backing_v3 { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_async_backing_v3.rs")); +} + +pub mod async_backing_v3_rpo { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_async_backing_v3_rpo.rs")); +} + +pub mod elastic_scaling_v3 { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_elastic_scaling_v3.rs")); +} + +pub mod slot_duration_18s { + #[cfg(feature = "std")] + include!(concat!(env!("OUT_DIR"), "/wasm_binary_slot_duration_18s.rs")); +} + +pub(crate) const SCHEDULING_V3_ENABLED: bool = cfg!(feature = "v3-descriptor"); + +pub(crate) const fn relay_parent_offset() -> u32 { + if cfg!(feature = "relay-parent-offset-2") { + return 2; + } + + 0 +} + +pub(crate) const fn slot_duration() -> u64 { + if cfg!(feature = "18s-slot") { + return 18000; + } + + if cfg!(feature = "12s-slot") { + return 12000; + } + + 6000 +} + +pub(crate) const fn block_processing_velocity() -> u32 { + if cfg!(feature = "velocity-12") { + return 12; + } + + if cfg!(feature = "velocity-6") { + return 6; + } + + if cfg!(feature = "velocity-3") { + return 3; + } + + 1 +} + +pub(crate) const fn unincluded_segment_capacity() -> u32 { + if cfg!(feature = "sync-backing") { + return 1; + } + + // Without sync backing, the block flow is the following: + // + // - Collator produces the block(s) on relay chain block `X` + // - In the meantime the relay chain is building block `X + 1` + // - The collator sends the collation to the relay chain, and it gets backed on chain in relay + // block `X + 2` + // - The collation then gets included on chain in relay block `X + 3` + block_processing_velocity() * (3 + relay_parent_offset()) +} diff --git a/cumulus/test/runtime/src/lib.rs b/cumulus/test/runtime/src/lib.rs index 8e48c80862023..de21761b80ea0 100644 --- a/cumulus/test/runtime/src/lib.rs +++ b/cumulus/test/runtime/src/lib.rs @@ -22,66 +22,7 @@ #[cfg(feature = "std")] include!(concat!(env!("OUT_DIR"), "/wasm_binary.rs")); -pub mod spec_version_incremented { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_spec_version_incremented.rs")); -} - -pub mod relay_parent_offset { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_relay_parent_offset.rs")); -} - -pub mod elastic_scaling_500ms { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_elastic_scaling_500ms.rs")); -} - -pub mod elastic_scaling { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_elastic_scaling.rs")); -} - -pub mod elastic_scaling_12s_slot { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_elastic_scaling_12s_slot.rs")); -} - -pub mod block_bundling { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_block_bundling.rs")); -} - -pub mod sync_backing { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_sync_backing.rs")); -} - -pub mod async_backing { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary.rs")); -} - -pub mod async_backing_v3 { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_async_backing_v3.rs")); -} - -pub mod async_backing_v3_rpo { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_async_backing_v3_rpo.rs")); -} - -pub mod elastic_scaling_v3 { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_elastic_scaling_v3.rs")); -} - -pub mod slot_duration_18s { - #[cfg(feature = "std")] - include!(concat!(env!("OUT_DIR"), "/wasm_binary_slot_duration_18s.rs")); -} - +pub mod flavors; mod genesis_config_presets; pub mod test_pallet; @@ -106,6 +47,7 @@ use sp_version::RuntimeVersion; use cumulus_primitives_core::{ParaId, RelayProofRequest, VerifySchedulingSignature}; // A few exports that help ease life for downstream crates. +pub use flavors::*; pub use frame_support::{ construct_runtime, dispatch::DispatchClass, @@ -145,63 +87,6 @@ impl_opaque_keys! { /// The para-id used in this runtime. pub const PARACHAIN_ID: u32 = 100; -const SCHEDULING_V3_ENABLED: bool = cfg!(feature = "v3-descriptor"); - -const fn relay_parent_offset() -> u32 { - if cfg!(feature = "relay-parent-offset-2") { - return 2; - } - - 0 -} - -const fn slot_duration() -> u64 { - if cfg!(feature = "18s-slot") { - return 18000; - } - - if cfg!(feature = "12s-slot") { - return 12000; - } - - 6000 -} - -const fn block_processing_velocity() -> u32 { - if cfg!(feature = "velocity-12") { - return 12; - } - - if cfg!(feature = "velocity-6") { - return 6; - } - - if cfg!(feature = "velocity-3") { - return 3; - } - - 1 -} - -const fn unincluded_segment_capacity() -> u32 { - if cfg!(feature = "sync-backing") { - return 1; - } - - // Without sync backing, the block flow is the following: - // - // - Collator produces the block(s) on relay chain block `X` - // - In the meantime the relay chain is building block `X + 1` - // - The collator sends the collation to the relay chain, and it gets backed on chain in relay - // block `X + 2` - // - The collation then gets included on chain in relay block `X + 3` - // - As we are building on `RELAY_PARENT_OFFSET` old relay parents, the included block from the - // parachain is also `RELAY_PARENT_OFFSET` relay blocks older (one relay block may contain - // multiple parachain blocks). - block_processing_velocity() * (3 + relay_parent_offset()) -} -const UNINCLUDED_SEGMENT_CAPACITY: u32 = unincluded_segment_capacity(); - const RELAY_CHAIN_SLOT_DURATION_MILLIS: u32 = 6000; // The only difference between the two declarations below is the `spec_version`. With the @@ -429,7 +314,7 @@ type ConsensusHook = cumulus_pallet_aura_ext::FixedVelocityConsensusHook< Runtime, RELAY_CHAIN_SLOT_DURATION_MILLIS, { block_processing_velocity() }, - UNINCLUDED_SEGMENT_CAPACITY, + { unincluded_segment_capacity() }, >; impl cumulus_pallet_parachain_system::Config for Runtime { type WeightInfo = (); diff --git a/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs b/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs index fd4c3bdc3b30d..ccee2488ff05d 100644 --- a/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs +++ b/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs @@ -126,7 +126,7 @@ async fn scheduling_v2_and_v3_collator_with_v3_validators( // Verify both V3 and V2 candidates are backed in the same relay chain block window. let expected_v3_throughput = match para_chain { "async-backing-v3" => 18..21, - "async-backing-v3-rpo" => 13..21, + "async-backing-v3-rpo" => 12..21, _ => unreachable!("unexpected para_chain"), }; assert_para_throughput_with( From 5eb898d01b5f064320d0a026b32d5d11111c9be3 Mon Sep 17 00:00:00 2001 From: Serban Iorga Date: Tue, 2 Jun 2026 15:47:37 +0300 Subject: [PATCH 06/10] fix --- polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs b/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs index ccee2488ff05d..d2e0c4497ba56 100644 --- a/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs +++ b/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs @@ -125,7 +125,7 @@ async fn scheduling_v2_and_v3_collator_with_v3_validators( // Verify both V3 and V2 candidates are backed in the same relay chain block window. let expected_v3_throughput = match para_chain { - "async-backing-v3" => 18..21, + "async-backing-v3" => 16..21, "async-backing-v3-rpo" => 12..21, _ => unreachable!("unexpected para_chain"), }; From f0829f4099e8bffb800b4f70f52e86af565eb0dc Mon Sep 17 00:00:00 2001 From: Serban Iorga Date: Tue, 2 Jun 2026 17:25:45 +0300 Subject: [PATCH 07/10] CR comments --- cumulus/test/runtime/Cargo.toml | 2 +- cumulus/test/runtime/build.rs | 4 +--- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/cumulus/test/runtime/Cargo.toml b/cumulus/test/runtime/Cargo.toml index 4860062ac82cb..e449bd94e9ddf 100644 --- a/cumulus/test/runtime/Cargo.toml +++ b/cumulus/test/runtime/Cargo.toml @@ -108,7 +108,7 @@ increment-spec-version = [] # The default parachain slot duration is 6s. The following features can be used to change this value: # Change the parachain slot duration to 12s 12s-slot = [] -# Change the parachain slot duration to 12s +# Change the parachain slot duration to 18s 18s-slot = [] # Configure the runtime to use sync backing. More specifically, this leads to: diff --git a/cumulus/test/runtime/build.rs b/cumulus/test/runtime/build.rs index 5928bf9c40981..af4aa38e11277 100644 --- a/cumulus/test/runtime/build.rs +++ b/cumulus/test/runtime/build.rs @@ -73,12 +73,10 @@ fn main() { WasmBuilder::init_with_defaults() .enable_feature("v3-descriptor") - .import_memory() .set_file_name("wasm_binary_async_backing_v3.rs") .build(); - WasmBuilder::new() - .with_current_project() + WasmBuilder::init_with_defaults() .enable_feature("v3-descriptor") .enable_feature("relay-parent-offset-2") .set_file_name("wasm_binary_async_backing_v3_rpo.rs") From 42dbf658ac03c2ce3ffad154ca28a3443a4d4ec4 Mon Sep 17 00:00:00 2001 From: Serban Iorga Date: Wed, 3 Jun 2026 17:06:35 +0300 Subject: [PATCH 08/10] Try remove rpo from unincluded segment capacity Might hide issues for v3 scheduling tests --- cumulus/test/runtime/src/flavors.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cumulus/test/runtime/src/flavors.rs b/cumulus/test/runtime/src/flavors.rs index 60faebe4bda67..223d4658db743 100644 --- a/cumulus/test/runtime/src/flavors.rs +++ b/cumulus/test/runtime/src/flavors.rs @@ -124,5 +124,5 @@ pub(crate) const fn unincluded_segment_capacity() -> u32 { // - The collator sends the collation to the relay chain, and it gets backed on chain in relay // block `X + 2` // - The collation then gets included on chain in relay block `X + 3` - block_processing_velocity() * (3 + relay_parent_offset()) + block_processing_velocity() * 3 } From c1d1b3ac9fb8d60f8355c297f01166fb505457a3 Mon Sep 17 00:00:00 2001 From: Serban Iorga Date: Wed, 3 Jun 2026 18:28:28 +0300 Subject: [PATCH 09/10] undo scheduling v3 test expected throughput --- polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs b/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs index d2e0c4497ba56..978467ffe0077 100644 --- a/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs +++ b/polkadot/zombienet-sdk-tests/tests/functional/scheduling_v3.rs @@ -126,7 +126,7 @@ async fn scheduling_v2_and_v3_collator_with_v3_validators( // Verify both V3 and V2 candidates are backed in the same relay chain block window. let expected_v3_throughput = match para_chain { "async-backing-v3" => 16..21, - "async-backing-v3-rpo" => 12..21, + "async-backing-v3-rpo" => 8..21, _ => unreachable!("unexpected para_chain"), }; assert_para_throughput_with( From 650fc0c31dc1f3ef65867aafbbd7cd57a8ebcc2e Mon Sep 17 00:00:00 2001 From: Serban Iorga Date: Wed, 3 Jun 2026 22:23:45 +0300 Subject: [PATCH 10/10] Apply CR suggestion Co-authored-by: Iulian Barbu <14218860+iulianbarbu@users.noreply.github.com> --- cumulus/test/runtime/Cargo.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cumulus/test/runtime/Cargo.toml b/cumulus/test/runtime/Cargo.toml index e449bd94e9ddf..a4823c0007e3f 100644 --- a/cumulus/test/runtime/Cargo.toml +++ b/cumulus/test/runtime/Cargo.toml @@ -128,5 +128,5 @@ velocity-12 = [] # Change the relay parent offset to 2 relay-parent-offset-2 = [] -# Configure the runtiem to use scheduling V3 +# Configure the runtime to use scheduling V3 v3-descriptor = []