Code Snippets & Overview

With the introduction of XCM v3, a new XcmBaseWeight was introduced both for Kusama and Polkadot (here & here). The estimate is 64 kB per instruction:

pub const BaseXcmWeight: Weight = Weight::from_parts(1_000_000_000, 64 * 1024);

Inside XCM v3 we also have the same constant defined/used:

/// Default value for the proof size weight component. Set at 64 KB.
const DEFAULT_PROOF_SIZE: u64 = 64 * 1024;

It's used in various contests, but the one I want to highlight is when V2 XCM instructions are converted into V3 instructions. In particular the BuyExecution instruction:

// Convert from a v2 instruction to a v3 instruction.
impl<Call> TryFrom<OldInstruction<Call>> for Instruction<Call> {
    type Error = ();
    fn try_from(old_instruction: OldInstruction<Call>) -> result::Result<Self, ()> {
        use OldInstruction::*;
        Ok(match old_instruction {
            BuyExecution { fees, weight_limit } => Self::BuyExecution {
                fees: fees.try_into()?,
                weight_limit: weight_limit.try_into()?,

Weight limit conversion is done using the following piece of code:

impl TryFrom<OldWeightLimit> for WeightLimit {
    type Error = ();
    fn try_from(x: OldWeightLimit) -> result::Result<Self, ()> {
        use OldWeightLimit::*;
        match x {
            Limited(w) => Ok(Self::Limited(Weight::from_parts(w, DEFAULT_PROOF_SIZE))),
            Unlimited => Ok(Self::Unlimited),


I've been testing XCM v3 integration with Astar/Shiden/Shibuya runtimes (using polkadot-v0.9.39 dependencies), and based on the code examples shared above, I naively also updated the unit weight cost of instructions to:

pub UnitWeightCost: Weight = Weight::from_parts(1_000_000_000, 64 * 1024);

The scenario which produced an error for me (local zombienet setup), one chain is uplifted to use XCM v3, and the other is still on old code revision (XCM v3 not even integrated).

When using the reserve_transfer_assets functionality, from V2 chain, to V3 chain, a Error::Barrier will happen.

Given the numbers above, it is somehow expected.

  • v3 chain receives the v2 instruction sequence
  • it converts it into v3 instruction sequence
  • v3 Weigher will calculate the the required PoV size of the 4 instructions is 256 kB
  • BuyExecution will be converted from v2 to v3, and weight_limit will end up being 64 kB

AllowTopLevelPaidExecutionFrom will block the execution, since the amount being bought via BuyExecution isn't sufficient enough to cover the weight of 4 instructions.


In case my understanding above is correct (and please correct me if I'm wrong) what would be a good default proof size to choose for instructions?

I'm assuming we keep the default 64 kB for the BuyExecution v2<>v3 conversion.

1 Answer 1


This PR covers my question above. It is in fact a bug.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.