diff --git a/.github/scripts/release/release_lib.sh b/.github/scripts/release/release_lib.sh index f4ac971824c48..c468599b364de 100644 --- a/.github/scripts/release/release_lib.sh +++ b/.github/scripts/release/release_lib.sh @@ -195,6 +195,9 @@ function get_s3_url_base() { eth-rpc) printf "releases.parity.io/eth-rpc" ;; + subkey) + printf "releases.parity.io/subkey" + ;; *) printf "UNSUPPORTED BINARY $name" exit 1 diff --git a/.github/workflows/check-semver.yml b/.github/workflows/check-semver.yml index 08359b979712c..73509a94462de 100644 --- a/.github/workflows/check-semver.yml +++ b/.github/workflows/check-semver.yml @@ -11,7 +11,7 @@ concurrency: cancel-in-progress: true env: - TOOLCHAIN: nightly-2025-01-26 + TOOLCHAIN: nightly-2025-05-09 jobs: isdraft: @@ -78,7 +78,7 @@ jobs: - name: Install parity-publish # Set the target dir to cache the build. - run: CARGO_TARGET_DIR=./target/ cargo install parity-publish@0.10.5 --locked -q + run: CARGO_TARGET_DIR=./target/ cargo install parity-publish@0.10.6 --locked -q - name: Get original PR number shell: bash diff --git a/.github/workflows/publish-check-compile.yml b/.github/workflows/publish-check-compile.yml index d1b537ba49058..f0b4ce27f626d 100644 --- a/.github/workflows/publish-check-compile.yml +++ b/.github/workflows/publish-check-compile.yml @@ -38,14 +38,49 @@ jobs: - name: install parity-publish run: | - cargo install parity-publish@0.10.4 --locked -q + cargo install parity-publish@0.10.6 --locked -q - - name: parity-publish update plan - run: parity-publish --color always plan --skip-check --prdoc prdoc/ + - name: set current PR's prdoc name in a variable + env: + GITHUB_PR_NUM: ${{ github.event.pull_request.number }} + run: | + echo "CURRENT_PRDOC=pr_${GITHUB_PR_NUM}.prdoc" >> $GITHUB_ENV - - name: parity-publish apply plan + - name: parity-publish update plan w/o current prdoc + run: | + if [ -f prdoc/$CURRENT_PRDOC ]; then + mv prdoc/$CURRENT_PRDOC . + fi + parity-publish --color always plan --skip-check --prdoc prdoc/ + + # The code base is not in master's state (due to commits brought by the + # current PR), but we're interested in all master's prdocs to be applied + # as if master is a stable branch, and in next steps we're following up with + # a patch release of all crates based on some newly added prdocs + # (meaning only the current prdoc). + - name: parity-publish apply plan on the code state prior to current prdoc run: parity-publish --color always apply --registry + - name: move all prdocs except current one to unstable dir + run: | + if [ -f $CURRENT_PRDOC ]; then + mkdir prdoc/unstable + mv prdoc/pr_*.prdoc prdoc/unstable + mv $CURRENT_PRDOC prdoc + fi + + - name: parity-publish update plan just for PR's prdoc + run: | + if [ -f "prdoc/$CURRENT_PRDOC" ]; then + parity-publish --color always plan --skip-check --prdoc prdoc/ + fi + + - name: parity-publish apply plan + run: | + if [ -f "prdoc/$CURRENT_PRDOC" ]; then + parity-publish --color always apply --registry + fi + - name: parity-publish check compile run: | packages="$(parity-publish apply --print)" diff --git a/.github/workflows/publish-check-crates.yml b/.github/workflows/publish-check-crates.yml index 7aef518e90d10..3ffd0515f22fe 100644 --- a/.github/workflows/publish-check-crates.yml +++ b/.github/workflows/publish-check-crates.yml @@ -27,7 +27,7 @@ jobs: cache-on-failure: true - name: install parity-publish - run: cargo install parity-publish@0.10.4 --locked -q + run: cargo install parity-publish@0.10.6 --locked -q - name: parity-publish check run: parity-publish --color always check --allow-unpublished diff --git a/.github/workflows/release-20_build-rc.yml b/.github/workflows/release-20_build-rc.yml index 11d126a69be39..e11d0070bde76 100644 --- a/.github/workflows/release-20_build-rc.yml +++ b/.github/workflows/release-20_build-rc.yml @@ -15,6 +15,7 @@ on: - chain-spec-builder - substrate-node - eth-rpc + - subkey - all release_tag: @@ -163,6 +164,21 @@ jobs: attestations: write contents: read + build-subkey-binary: + needs: [validate-inputs] + if: ${{ inputs.binary == 'subkey' || inputs.binary == 'all' }} + uses: "./.github/workflows/release-reusable-rc-build.yml" + with: + binary: '["subkey"]' + package: subkey + release_tag: ${{ needs.validate-inputs.outputs.release_tag }} + target: x86_64-unknown-linux-gnu + secrets: inherit + permissions: + id-token: write + attestations: write + contents: read + build-polkadot-macos-binary: needs: [validate-inputs] if: ${{ inputs.binary == 'polkadot' || inputs.binary == 'all' }} @@ -268,3 +284,18 @@ jobs: id-token: write attestations: write contents: read + + build-subkey-macos-binary: + needs: [validate-inputs] + if: ${{ inputs.binary == 'subkey' || inputs.binary == 'all' }} + uses: "./.github/workflows/release-reusable-rc-build.yml" + with: + binary: '["subkey"]' + package: subkey + release_tag: ${{ needs.validate-inputs.outputs.release_tag }} + target: aarch64-apple-darwin + secrets: inherit + permissions: + id-token: write + attestations: write + contents: read diff --git a/.github/workflows/release-22_combined-rc-runtime-builds-release-draft.yml b/.github/workflows/release-22_combined-rc-runtime-builds-release-draft.yml index f8473be81ee14..ac5e4b0af8ab9 100644 --- a/.github/workflows/release-22_combined-rc-runtime-builds-release-draft.yml +++ b/.github/workflows/release-22_combined-rc-runtime-builds-release-draft.yml @@ -41,6 +41,7 @@ on: - chain-spec-builder - substrate-node - eth-rpc + - subkey - all release_tag: description: Tag matching the actual release candidate with the format polkadot-stableYYMM(-X)-rcY or polkadot-stableYYMM(-X) diff --git a/.github/workflows/release-build-binary.yml b/.github/workflows/release-build-binary.yml index a5adab421a8a4..1fab39a7ef9fa 100644 --- a/.github/workflows/release-build-binary.yml +++ b/.github/workflows/release-build-binary.yml @@ -66,11 +66,12 @@ jobs: PROFILE=${{ inputs.profile }} if [ "${{ inputs.binary }}" = "polkadot" ]; then for binary in polkadot polkadot-prepare-worker polkadot-execute-worker; do - echo "Building $binary..." - ./.github/scripts/release/build-linux-release.sh $binary ${{ inputs.package }} "${PROFILE}" ${{ inputs.features }} + echo "Building $binary with profile $PROFILE and features ${{ inputs.features }}" + ./.github/scripts/release/build-linux-release.sh $binary ${{ inputs.package }} ${{ inputs.features }} done else - ./.github/scripts/release/build-linux-release.sh ${{ inputs.binary }} ${{ inputs.package }} "${PROFILE}" ${{ inputs.features }} + echo "Building ${{ inputs.binary }} with profile $PROFILE and features ${{ inputs.features }}" + ./.github/scripts/release/build-linux-release.sh ${{ inputs.binary }} ${{ inputs.package }} ${{ inputs.features }} fi - name: Upload ${{ inputs.binary }} artifacts diff --git a/.github/workflows/release-reusable-rc-build.yml b/.github/workflows/release-reusable-rc-build.yml index 973796cbf39f2..77bc48104cc59 100644 --- a/.github/workflows/release-reusable-rc-build.yml +++ b/.github/workflows/release-reusable-rc-build.yml @@ -301,10 +301,7 @@ jobs: package: ${{ inputs.package }} release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-polkadot-parachain-artifacts-to-s3: if: ${{ inputs.package == 'polkadot-parachain-bin' && inputs.target == 'x86_64-unknown-linux-gnu' }} @@ -314,10 +311,7 @@ jobs: package: polkadot-parachain release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-polkadot-omni-node-artifacts-to-s3: if: ${{ inputs.package == 'polkadot-omni-node' && inputs.target == 'x86_64-unknown-linux-gnu' }} @@ -327,10 +321,7 @@ jobs: package: ${{ inputs.package }} release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-frame-omni-bencher-artifacts-to-s3: if: ${{ inputs.package == 'frame-omni-bencher' && inputs.target == 'x86_64-unknown-linux-gnu' }} @@ -340,10 +331,7 @@ jobs: package: ${{ inputs.package }} release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-chain-spec-builder-artifacts-to-s3: if: ${{ inputs.package == 'staging-chain-spec-builder' && inputs.target == 'x86_64-unknown-linux-gnu' }} @@ -353,10 +341,7 @@ jobs: package: chain-spec-builder release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-substrate-node-artifacts-to-s3: if: ${{ inputs.package == 'staging-node-cli' && inputs.target == 'x86_64-unknown-linux-gnu' }} @@ -366,10 +351,7 @@ jobs: package: substrate-node release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-eth-rpc-artifacts-to-s3: if: ${{ inputs.package == 'pallet-revive-eth-rpc' && inputs.target == 'x86_64-unknown-linux-gnu' }} @@ -379,10 +361,17 @@ jobs: package: eth-rpc release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit + + upload-subkey-artifacts-to-s3: + if: ${{ inputs.package == 'subkey' && inputs.target == 'x86_64-unknown-linux-gnu' }} + needs: [build-rc] + uses: ./.github/workflows/release-reusable-s3-upload.yml + with: + package: subkey + release_tag: ${{ inputs.release_tag }} + target: ${{ inputs.target }} + secrets: inherit upload-polkadot-macos-artifacts-to-s3: if: ${{ inputs.package == 'polkadot' && inputs.target == 'aarch64-apple-darwin' }} @@ -394,10 +383,7 @@ jobs: package: ${{ inputs.package }} release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-polkadot-prepare-worker-macos-artifacts-to-s3: if: ${{ inputs.package == 'polkadot' && inputs.target == 'aarch64-apple-darwin' }} @@ -407,10 +393,7 @@ jobs: package: polkadot-prepare-worker release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-polkadot-execute-worker-macos-artifacts-to-s3: if: ${{ inputs.package == 'polkadot' && inputs.target == 'aarch64-apple-darwin' }} @@ -420,10 +403,10 @@ jobs: package: polkadot-execute-worker release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit + # AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} + # AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} + # AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} upload-polkadot-omni-node-macos-artifacts-to-s3: if: ${{ inputs.package == 'polkadot-omni-node' && inputs.target == 'aarch64-apple-darwin' }} @@ -433,10 +416,7 @@ jobs: package: ${{ inputs.package }} release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-polkadot-parachain-macos-artifacts-to-s3: if: ${{ inputs.package == 'polkadot-parachain-bin' && inputs.target == 'aarch64-apple-darwin' }} @@ -446,10 +426,7 @@ jobs: package: polkadot-parachain release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-frame-omni-bencher-macos-artifacts-to-s3: if: ${{ inputs.package == 'frame-omni-bencher' && inputs.target == 'aarch64-apple-darwin' }} @@ -459,10 +436,10 @@ jobs: package: ${{ inputs.package }} release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit + # AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} + # AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} + # AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} upload-chain-spec-builder-macos-artifacts-to-s3: if: ${{ inputs.package == 'staging-chain-spec-builder' && inputs.target == 'aarch64-apple-darwin' }} @@ -472,10 +449,7 @@ jobs: package: chain-spec-builder release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit upload-substrate-node-macos-artifacts-to-s3: if: ${{ inputs.package == 'staging-node-cli' && inputs.target == 'aarch64-apple-darwin' }} @@ -485,10 +459,10 @@ jobs: package: substrate-node release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit + # AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} + # AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} + # AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} upload-eth-rpc-macos-artifacts-to-s3: if: ${{ inputs.package == 'pallet-revive-eth-rpc' && inputs.target == 'aarch64-apple-darwin' }} @@ -498,7 +472,14 @@ jobs: package: eth-rpc release_tag: ${{ inputs.release_tag }} target: ${{ inputs.target }} - secrets: - AWS_DEFAULT_REGION: ${{ secrets.AWS_DEFAULT_REGION }} - AWS_RELEASE_ACCESS_KEY_ID: ${{ secrets.AWS_RELEASE_ACCESS_KEY_ID }} - AWS_RELEASE_SECRET_ACCESS_KEY: ${{ secrets.AWS_RELEASE_SECRET_ACCESS_KEY }} + secrets: inherit + + upload-subkey-macos-artifacts-to-s3: + if: ${{ inputs.package == 'subkey' && inputs.target == 'aarch64-apple-darwin' }} + needs: [build-macos-rc] + uses: ./.github/workflows/release-reusable-s3-upload.yml + with: + package: subkey + release_tag: ${{ inputs.release_tag }} + target: ${{ inputs.target }} + secrets: inherit diff --git a/.github/workflows/release-reusable-s3-upload.yml b/.github/workflows/release-reusable-s3-upload.yml index b4c7b5d77bb53..b4606ef23437a 100644 --- a/.github/workflows/release-reusable-s3-upload.yml +++ b/.github/workflows/release-reusable-s3-upload.yml @@ -18,14 +18,6 @@ on: required: true type: string - secrets: - AWS_DEFAULT_REGION: - required: true - AWS_RELEASE_ACCESS_KEY_ID: - required: true - AWS_RELEASE_SECRET_ACCESS_KEY: - required: true - jobs: upload-artifacts-to-s3: runs-on: ubuntu-latest diff --git a/Cargo.lock b/Cargo.lock index 4c4d0344bf222..ffc452d440738 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -12,29 +12,20 @@ dependencies = [ "regex", ] -[[package]] -name = "addr2line" -version = "0.21.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8a30b2e23b9e17a9f90641c7ab1549cd9b44f296d3ccbf309d2863cfe398a0cb" -dependencies = [ - "gimli 0.28.0", -] - [[package]] name = "addr2line" version = "0.24.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "dfbe277e56a376000877090da837660b4427aad530e3028d44e0bffe4f89a1c1" dependencies = [ - "gimli 0.31.1", + "gimli", ] [[package]] -name = "adler" -version = "1.0.2" +name = "adler2" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" +checksum = "320119579fcad9c21884f5c4861d16174d0e06250625266f50fe6898340abefa" [[package]] name = "adler32" @@ -54,9 +45,9 @@ dependencies = [ [[package]] name = "aes" -version = "0.8.3" +version = "0.8.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ac1f845298e95f983ff1944b728ae08b8cebab80d684f0a832ed0fc74dfa27e2" +checksum = "b169f7a6d4742236a0a00c541b845991d0ac43e546831af1249753ab4c3aa3a0" dependencies = [ "cfg-if", "cipher 0.4.4", @@ -74,27 +65,27 @@ dependencies = [ "cipher 0.4.4", "ctr", "ghash", - "subtle 2.5.0", + "subtle 2.6.1", ] [[package]] name = "ahash" -version = "0.8.11" +version = "0.8.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e89da841a80418a9b391ebaea17f5c112ffaaa96f621d2c285b5174da76b9011" +checksum = "5a15f179cd60c4584b8a8c596927aadc462e27f2ca70c04e0071964a73ba7a75" dependencies = [ "cfg-if", - "getrandom 0.2.10", + "getrandom 0.3.3", "once_cell", "version_check", - "zerocopy 0.7.32", + "zerocopy", ] [[package]] name = "aho-corasick" -version = "1.0.4" +version = "1.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6748e8def348ed4d14996fa801f4122cd763fff530258cdc03f64b25f89d3a5a" +checksum = "8e60d3430d3a69478ad0993f19238d2df97c507009a52b3c10addcd7f6bcb916" dependencies = [ "memchr", ] @@ -107,9 +98,9 @@ checksum = "683d7910e743518b0e34f1186f92494becacb047c7b6bf616c96772180fef923" [[package]] name = "alloy-core" -version = "1.1.2" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a3c5a28f166629752f2e7246b813cdea3243cca59aab2d4264b1fd68392c10eb" +checksum = "bfe6c56d58fbfa9f0f6299376e8ce33091fc6494239466814c3f54b55743cb09" dependencies = [ "alloy-dyn-abi", "alloy-json-abi", @@ -120,9 +111,9 @@ dependencies = [ [[package]] name = "alloy-dyn-abi" -version = "1.1.2" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "18cc14d832bc3331ca22a1c7819de1ede99f58f61a7d123952af7dde8de124a6" +checksum = "a3f56873f3cac7a2c63d8e98a4314b8311aa96adb1a0f82ae923eb2119809d2c" dependencies = [ "alloy-json-abi", "alloy-primitives", @@ -131,14 +122,71 @@ dependencies = [ "itoa", "serde", "serde_json", - "winnow 0.7.10", + "winnow 0.7.13", +] + +[[package]] +name = "alloy-eip2124" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "741bdd7499908b3aa0b159bba11e71c8cddd009a2c2eb7a06e825f1ec87900a5" +dependencies = [ + "alloy-primitives", + "alloy-rlp", + "crc", + "serde", + "thiserror 2.0.16", +] + +[[package]] +name = "alloy-eip2930" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b82752a889170df67bbb36d42ca63c531eb16274f0d7299ae2a680facba17bd" +dependencies = [ + "alloy-primitives", + "alloy-rlp", + "serde", +] + +[[package]] +name = "alloy-eip7702" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9d4769c6ffddca380b0070d71c8b7f30bed375543fe76bb2f74ec0acf4b7cd16" +dependencies = [ + "alloy-primitives", + "alloy-rlp", + "k256", + "serde", + "thiserror 2.0.16", +] + +[[package]] +name = "alloy-eips" +version = "1.0.26" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ccab489a99806d6586118b4712506e56c2888cdf4798f29b401511bc3af13475" +dependencies = [ + "alloy-eip2124", + "alloy-eip2930", + "alloy-eip7702", + "alloy-primitives", + "alloy-rlp", + "alloy-serde", + "auto_impl", + "c-kzg", + "derive_more 2.0.1", + "either", + "serde", + "sha2 0.10.9", ] [[package]] name = "alloy-json-abi" -version = "1.1.2" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3ccaa79753d7bf15f06399ea76922afbfaf8d18bebed9e8fc452984b4a90dcc9" +checksum = "125a1c373261b252e53e04d6e92c37d881833afc1315fceab53fd46045695640" dependencies = [ "alloy-primitives", "alloy-sol-type-parser", @@ -148,24 +196,24 @@ dependencies = [ [[package]] name = "alloy-primitives" -version = "1.1.2" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "18c35fc4b03ace65001676358ffbbaefe2a2b27ee50fe777c345082c7c888be8" +checksum = "bc9485c56de23438127a731a6b4c87803d49faf1a7068dcd1d8768aca3a9edb9" dependencies = [ "alloy-rlp", "bytes", "cfg-if", "const-hex", "derive_more 2.0.1", - "foldhash", - "hashbrown 0.15.3", + "foldhash 0.1.5", + "hashbrown 0.15.5", "indexmap", "itoa", "k256", "keccak-asm", "paste", "proptest", - "rand 0.9.0", + "rand 0.9.2", "ruint", "rustc-hash 2.1.1", "serde", @@ -175,78 +223,100 @@ dependencies = [ [[package]] name = "alloy-rlp" -version = "0.3.3" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cc0fac0fc16baf1f63f78b47c3d24718f3619b0714076f6a02957d808d52cbef" +checksum = "5f70d83b765fdc080dbcd4f4db70d8d23fe4761f2f02ebfa9146b833900634b4" dependencies = [ - "arrayvec 0.7.4", + "alloy-rlp-derive", + "arrayvec 0.7.6", "bytes", - "smol_str", +] + +[[package]] +name = "alloy-rlp-derive" +version = "0.3.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "64b728d511962dda67c1bc7ea7c03736ec275ed2cf4c35d9585298ac9ccf3b73" +dependencies = [ + "proc-macro2 1.0.101", + "quote 1.0.40", + "syn 2.0.106", +] + +[[package]] +name = "alloy-serde" +version = "1.0.26" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "93cb27da33b618fe729ab6b053275e754fbb31782caa83dfd11219d7e2e8ebf1" +dependencies = [ + "alloy-primitives", + "serde", + "serde_json", ] [[package]] name = "alloy-sol-macro" -version = "1.1.2" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8612e0658964d616344f199ab251a49d48113992d81b92dab93ed855faa66383" +checksum = "d20d867dcf42019d4779519a1ceb55eba8d7f3d0e4f0a89bcba82b8f9eb01e48" dependencies = [ "alloy-sol-macro-expander", "alloy-sol-macro-input", "proc-macro-error2", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "alloy-sol-macro-expander" -version = "1.1.2" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a384edac7283bc4c010a355fb648082860c04b826bb7a814c45263c8f304c74" +checksum = "b74e91b0b553c115d14bd0ed41898309356dc85d0e3d4b9014c4e7715e48c8ad" dependencies = [ "alloy-sol-macro-input", "const-hex", "heck 0.5.0", "indexmap", "proc-macro-error2", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", "syn-solidity", "tiny-keccak", ] [[package]] name = "alloy-sol-macro-input" -version = "1.1.2" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0dd588c2d516da7deb421b8c166dc60b7ae31bca5beea29ab6621fcfa53d6ca5" +checksum = "84194d31220803f5f62d0a00f583fd3a062b36382e2bea446f1af96727754565" dependencies = [ "const-hex", "dunce", "heck 0.5.0", "macro-string", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", "syn-solidity", ] [[package]] name = "alloy-sol-type-parser" -version = "1.1.2" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e86ddeb70792c7ceaad23e57d52250107ebbb86733e52f4a25d8dc1abc931837" +checksum = "fe8c27b3cf6b2bb8361904732f955bc7c05e00be5f469cec7e2280b6167f3ff0" dependencies = [ "serde", - "winnow 0.7.10", + "winnow 0.7.13", ] [[package]] name = "alloy-sol-types" -version = "1.1.2" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "584cb97bfc5746cb9dcc4def77da11694b5d6d7339be91b7480a6a68dc129387" +checksum = "f5383d34ea00079e6dd89c652bcbdb764db160cef84e6250926961a0b2295d04" dependencies = [ "alloy-json-abi", "alloy-primitives", @@ -283,57 +353,59 @@ checksum = "4b46cbb362ab8752921c97e041f5e366ee6297bd428a31275b9fcf1e380f7299" [[package]] name = "anstream" -version = "0.6.11" +version = "0.6.20" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6e2e1ebcb11de5c03c67de28a7df593d32191b44939c482e97702baaaa6ab6a5" +checksum = "3ae563653d1938f79b1ab1b5e668c87c76a9930414574a6583a7b7e11a8e6192" dependencies = [ "anstyle", "anstyle-parse", "anstyle-query", "anstyle-wincon", "colorchoice", + "is_terminal_polyfill", "utf8parse", ] [[package]] name = "anstyle" -version = "1.0.6" +version = "1.0.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8901269c6307e8d93993578286ac0edf7f195079ffff5ebdeea6a59ffb7e36bc" +checksum = "862ed96ca487e809f1c8e5a8447f6ee2cf102f846893800b20cebdf541fc6bbd" [[package]] name = "anstyle-parse" -version = "0.2.1" +version = "0.2.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "938874ff5980b03a87c5524b3ae5b59cf99b1d6bc836848df7bc5ada9643c333" +checksum = "4e7644824f0aa2c7b9384579234ef10eb7efb6a0deb83f9630a49594dd9c15c2" dependencies = [ "utf8parse", ] [[package]] name = "anstyle-query" -version = "1.0.0" +version = "1.1.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5ca11d4be1bab0c8bc8734a9aa7bf4ee8316d462a08c6ac5052f888fef5b494b" +checksum = "9e231f6134f61b71076a3eab506c379d4f36122f2af15a9ff04415ea4c3339e2" dependencies = [ - "windows-sys 0.48.0", + "windows-sys 0.60.2", ] [[package]] name = "anstyle-wincon" -version = "3.0.1" +version = "3.0.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f0699d10d2f4d628a98ee7b57b289abbc98ff3bad977cb3152709d4bf2330628" +checksum = "3e0633414522a32ffaac8ac6cc8f748e090c5717661fddeea04219e2344f5f2a" dependencies = [ "anstyle", - "windows-sys 0.48.0", + "once_cell_polyfill", + "windows-sys 0.60.2", ] [[package]] name = "anyhow" -version = "1.0.98" +version = "1.0.99" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e16d2d3311acee920a9eb8d33b8cbc1787ce4a264e85f964c2404b969bdcd487" +checksum = "b0674a1ddeecb70197781e945de4b3b8ffb61fa939a5597bcf48503737663100" [[package]] name = "approx" @@ -353,16 +425,16 @@ dependencies = [ "include_dir", "itertools 0.10.5", "proc-macro-error", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "arbitrary" -version = "1.4.1" +version = "1.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dde20b3d026af13f561bdd0f15edf01fc734f0dafcedbaf42bba506a9517f223" +checksum = "c3d036a3c4ab069c7b410a2ce876bd74808d2d0888a82667669f8e783a898bf1" dependencies = [ "derive_arbitrary", ] @@ -428,6 +500,18 @@ dependencies = [ "ark-std 0.4.0", ] +[[package]] +name = "ark-bn254" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d69eab57e8d2663efa5c63135b2af4f396d66424f88954c21104125ab6b3e6bc" +dependencies = [ + "ark-ec 0.5.0", + "ark-ff 0.5.0", + "ark-r1cs-std", + "ark-std 0.5.0", +] + [[package]] name = "ark-bw6-761" version = "0.4.0" @@ -484,7 +568,7 @@ dependencies = [ "ark-std 0.5.0", "educe", "fnv", - "hashbrown 0.15.3", + "hashbrown 0.15.5", "itertools 0.13.0", "num-bigint", "num-integer", @@ -589,7 +673,7 @@ dependencies = [ "num-bigint", "num-traits", "paste", - "rustc_version 0.4.0", + "rustc_version 0.4.1", "zeroize", ] @@ -603,7 +687,7 @@ dependencies = [ "ark-ff-macros 0.5.0", "ark-serialize 0.5.0", "ark-std 0.5.0", - "arrayvec 0.7.4", + "arrayvec 0.7.6", "digest 0.10.7", "educe", "itertools 0.13.0", @@ -641,7 +725,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "62945a2f7e6de02a31fe400aa489f0e0f5b2502e69f95f853adb82a96c7a6b60" dependencies = [ "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -664,7 +748,7 @@ checksum = "7abe79b0e4288889c4574159ab790824d0033b9fdcb2a112a3182fac2e514565" dependencies = [ "num-bigint", "num-traits", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "syn 1.0.109", ] @@ -677,9 +761,9 @@ checksum = "09be120733ee33f7693ceaa202ca41accd5653b779563608f1234f78ae07c4b3" dependencies = [ "num-bigint", "num-traits", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -720,10 +804,39 @@ dependencies = [ "ark-std 0.5.0", "educe", "fnv", - "hashbrown 0.15.3", + "hashbrown 0.15.5", "rayon", ] +[[package]] +name = "ark-r1cs-std" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "941551ef1df4c7a401de7068758db6503598e6f01850bdb2cfdb614a1f9dbea1" +dependencies = [ + "ark-ec 0.5.0", + "ark-ff 0.5.0", + "ark-relations", + "ark-std 0.5.0", + "educe", + "num-bigint", + "num-integer", + "num-traits", + "tracing", +] + +[[package]] +name = "ark-relations" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ec46ddc93e7af44bcab5230937635b06fb5744464dd6a7e7b083e80ebd274384" +dependencies = [ + "ark-ff 0.5.0", + "ark-std 0.5.0", + "tracing", + "tracing-subscriber 0.2.25", +] + [[package]] name = "ark-scale" version = "0.0.12" @@ -780,7 +893,7 @@ checksum = "3f4d068aaf107ebcd7dfb52bc748f8030e0fc930ac8e360146ca54c1203088f7" dependencies = [ "ark-serialize-derive 0.5.0", "ark-std 0.5.0", - "arrayvec 0.7.4", + "arrayvec 0.7.6", "digest 0.10.7", "num-bigint", "rayon", @@ -792,7 +905,7 @@ version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ae3281bc6d0fd7e549af32b52511e1302185bd688fd3359fa36423346ff682ea" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "syn 1.0.109", ] @@ -803,9 +916,9 @@ version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "213888f660fddcca0d257e88e54ac05bca01885f258ccdf695bafd77031bb69d" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -869,31 +982,32 @@ dependencies = [ "digest 0.10.7", "rand_chacha 0.3.1", "rayon", - "sha2 0.10.8", + "sha2 0.10.9", "w3f-ring-proof", "zeroize", ] [[package]] name = "array-bytes" -version = "6.2.2" +version = "6.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6f840fb7195bcfc5e17ea40c26e5ce6d5b9ce5d584466e17703209657e459ae0" +checksum = "5d5dde061bd34119e902bbb2d9b90c5692635cf59fb91d582c2b68043f1b8293" [[package]] name = "array-bytes" -version = "9.1.2" +version = "9.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4449507daf4f07a8c8309e122d32a53d15c9f33e77eaf01c839fea42ccd4d673" +checksum = "27d55334c98d756b32dcceb60248647ab34f027690f87f9a362fd292676ee927" dependencies = [ "smallvec", + "thiserror 2.0.16", ] [[package]] name = "arrayref" -version = "0.3.7" +version = "0.3.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6b4930d2cb77ce62f89ee5d5289b4ac049559b1c45539271f5ed4fdc7db34545" +checksum = "76a2e8124351fda1ef8aaaa3bbd7ebbcb486bbcd4225aca0aa0d84bb2db8fecb" [[package]] name = "arrayvec" @@ -906,52 +1020,52 @@ dependencies = [ [[package]] name = "arrayvec" -version = "0.7.4" +version = "0.7.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "96d30a06541fbafbc7f82ed10c06164cfbd2c401138f6addd8404629c4b16711" +checksum = "7c02d123df017efcdfbd739ef81735b36c5ba83ec3c59c80a9d7ecc718f92e50" [[package]] name = "asn1-rs" -version = "0.6.1" +version = "0.6.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "22ad1373757efa0f70ec53939aabc7152e1591cb485208052993070ac8d2429d" +checksum = "5493c3bedbacf7fd7382c6346bbd66687d12bbaad3a89a2d2c303ee6cf20b048" dependencies = [ - "asn1-rs-derive 0.5.0", + "asn1-rs-derive 0.5.1", "asn1-rs-impl", "displaydoc", - "nom", + "nom 7.1.3", "num-traits", "rusticata-macros", - "thiserror 1.0.65", + "thiserror 1.0.69", "time", ] [[package]] name = "asn1-rs" -version = "0.7.0" +version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "607495ec7113b178fbba7a6166a27f99e774359ef4823adbefd756b5b81d7970" +checksum = "56624a96882bb8c26d61312ae18cb45868e5a9992ea73c58e45c3101e56a1e60" dependencies = [ "asn1-rs-derive 0.6.0", "asn1-rs-impl", "displaydoc", - "nom", + "nom 7.1.3", "num-traits", "rusticata-macros", - "thiserror 2.0.12", + "thiserror 2.0.16", "time", ] [[package]] name = "asn1-rs-derive" -version = "0.5.0" +version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7378575ff571966e99a744addeff0bff98b8ada0dedf1956d59e634db95eaac1" +checksum = "965c2d33e53cb6b267e148a4cb0760bc01f4904c1cd4bb4002a085bb016d1490" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", - "synstructure 0.13.1", + "syn 2.0.106", + "synstructure 0.13.2", ] [[package]] @@ -960,10 +1074,10 @@ version = "0.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3109e49b1e4909e9db6515a30c633684d68cdeaa252f215214cb4fa1a5bfee2c" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", - "synstructure 0.13.1", + "syn 2.0.106", + "synstructure 0.13.2", ] [[package]] @@ -972,20 +1086,21 @@ version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7b18050c2cd6fe86c3a76584ef5e0baf286d038cda203eb6223df2cc413565f7" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "assert_cmd" -version = "2.0.14" +version = "2.0.17" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ed72493ac66d5804837f480ab3766c72bdfab91a65e565fc54fa9e42db0073a8" +checksum = "2bd389a4b2970a01282ee455294913c0a43724daedcd1a24c3eb0ec1c1320b66" dependencies = [ "anstyle", "bstr", "doc-comment", + "libc", "predicates", "predicates-core", "predicates-tree", @@ -1377,12 +1492,11 @@ dependencies = [ [[package]] name = "async-channel" -version = "2.3.0" +version = "2.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9f2776ead772134d55b62dd45e59a79e21612d85d0af729b8b7d3967d601a62a" +checksum = "924ed96dd52d1b75e9c1a3e6275715fd320f5f9439fb5a4a11fa51f4221158d2" dependencies = [ "concurrent-queue", - "event-listener 5.3.1", "event-listener-strategy", "futures-core", "pin-project-lite", @@ -1390,15 +1504,15 @@ dependencies = [ [[package]] name = "async-executor" -version = "1.5.1" +version = "1.13.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6fa3dc5f2a8564f07759c008b9109dc0d39de92a88d5588b8a5036d286383afb" +checksum = "bb812ffb58524bdd10860d7d974e2f01cc0950c2438a74ee5ec2e2280c6c4ffa" dependencies = [ - "async-lock 2.8.0", "async-task", "concurrent-queue", - "fastrand 1.9.0", - "futures-lite 1.13.0", + "fastrand 2.3.0", + "futures-lite 2.6.1", + "pin-project-lite", "slab", ] @@ -1416,27 +1530,27 @@ dependencies = [ [[package]] name = "async-fs" -version = "2.1.2" +version = "2.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ebcd09b382f40fcd159c2d695175b2ae620ffa5f3bd6f664131efff4e8b9e04a" +checksum = "09f7e37c0ed80b2a977691c47dae8625cfb21e205827106c64f7c588766b2e50" dependencies = [ - "async-lock 3.4.0", + "async-lock 3.4.1", "blocking", - "futures-lite 2.3.0", + "futures-lite 2.6.1", ] [[package]] name = "async-global-executor" -version = "2.3.1" +version = "2.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f1b6f5d7df27bd294849f8eec66ecfc63d11814df7a4f5d74168a2394467b776" +checksum = "05b1b633a2115cd122d73b955eadd9916c18c8f510ec9cd1686404c60ad1c29c" dependencies = [ - "async-channel 1.9.0", + "async-channel 2.5.0", "async-executor", - "async-io 1.13.0", - "async-lock 2.8.0", + "async-io 2.5.0", + "async-lock 3.4.1", "blocking", - "futures-lite 1.13.0", + "futures-lite 2.6.1", "once_cell", ] @@ -1454,29 +1568,28 @@ dependencies = [ "log", "parking", "polling 2.8.0", - "rustix 0.37.23", + "rustix 0.37.28", "slab", - "socket2 0.4.9", + "socket2 0.4.10", "waker-fn", ] [[package]] name = "async-io" -version = "2.3.3" +version = "2.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d6baa8f0178795da0e71bc42c9e5d13261aac7ee549853162e66a241ba17964" +checksum = "19634d6336019ef220f09fd31168ce5c184b295cbf80345437cc36094ef223ca" dependencies = [ - "async-lock 3.4.0", + "async-lock 3.4.1", "cfg-if", "concurrent-queue", "futures-io", - "futures-lite 2.3.0", + "futures-lite 2.6.1", "parking", - "polling 3.4.0", - "rustix 0.38.42", + "polling 3.10.0", + "rustix 1.0.8", "slab", - "tracing", - "windows-sys 0.52.0", + "windows-sys 0.60.2", ] [[package]] @@ -1490,23 +1603,22 @@ dependencies = [ [[package]] name = "async-lock" -version = "3.4.0" +version = "3.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ff6e472cdea888a4bd64f342f09b3f50e1886d32afe8df3d663c01140b811b18" +checksum = "5fd03604047cee9b6ce9de9f70c6cd540a0520c813cbd49bae61f33ab80ed1dc" dependencies = [ - "event-listener 5.3.1", + "event-listener 5.4.1", "event-listener-strategy", "pin-project-lite", ] [[package]] name = "async-net" -version = "1.7.0" +version = "1.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4051e67316bc7eff608fe723df5d32ed639946adcd69e07df41fd42a7b411f1f" +checksum = "0434b1ed18ce1cf5769b8ac540e33f01fa9471058b5e89da9e06f3c882a8c12f" dependencies = [ "async-io 1.13.0", - "autocfg", "blocking", "futures-lite 1.13.0", ] @@ -1517,83 +1629,81 @@ version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b948000fad4873c1c9339d60f2623323a0cfd3816e5181033c6a5cb68b2accf7" dependencies = [ - "async-io 2.3.3", + "async-io 2.5.0", "blocking", - "futures-lite 2.3.0", + "futures-lite 2.6.1", ] [[package]] name = "async-process" -version = "1.7.0" +version = "1.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a9d28b1d97e08915212e2e45310d47854eafa69600756fc735fb788f75199c9" +checksum = "ea6438ba0a08d81529c69b36700fa2f95837bfe3e776ab39cde9c14d9149da88" dependencies = [ "async-io 1.13.0", "async-lock 2.8.0", - "autocfg", + "async-signal", "blocking", "cfg-if", - "event-listener 2.5.3", + "event-listener 3.1.0", "futures-lite 1.13.0", - "rustix 0.37.23", - "signal-hook", + "rustix 0.38.44", "windows-sys 0.48.0", ] [[package]] name = "async-process" -version = "2.3.0" +version = "2.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "63255f1dc2381611000436537bbedfe83183faa303a5a0edaf191edef06526bb" +checksum = "65daa13722ad51e6ab1a1b9c01299142bc75135b337923cfa10e79bbbd669f00" dependencies = [ - "async-channel 2.3.0", - "async-io 2.3.3", - "async-lock 3.4.0", + "async-channel 2.5.0", + "async-io 2.5.0", + "async-lock 3.4.1", "async-signal", "async-task", "blocking", "cfg-if", - "event-listener 5.3.1", - "futures-lite 2.3.0", - "rustix 0.38.42", - "tracing", + "event-listener 5.4.1", + "futures-lite 2.6.1", + "rustix 1.0.8", ] [[package]] name = "async-signal" -version = "0.2.9" +version = "0.2.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dfb3634b73397aa844481f814fad23bbf07fdb0eabec10f2eb95e58944b1ec32" +checksum = "f567af260ef69e1d52c2b560ce0ea230763e6fbb9214a85d768760a920e3e3c1" dependencies = [ - "async-io 2.3.3", - "async-lock 3.4.0", + "async-io 2.5.0", + "async-lock 3.4.1", "atomic-waker", "cfg-if", "futures-core", "futures-io", - "rustix 0.38.42", + "rustix 1.0.8", "signal-hook-registry", "slab", - "windows-sys 0.52.0", + "windows-sys 0.60.2", ] [[package]] name = "async-std" -version = "1.12.0" +version = "1.13.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "62565bb4402e926b29953c785397c6dc0391b7b446e45008b0049eb43cec6f5d" +checksum = "2c8e079a4ab67ae52b7403632e4618815d6db36d2a010cfe41b02c1b1578f93b" dependencies = [ "async-attributes", "async-channel 1.9.0", "async-global-executor", - "async-io 1.13.0", - "async-lock 2.8.0", + "async-io 2.5.0", + "async-lock 3.4.1", "crossbeam-utils", "futures-channel", "futures-core", "futures-io", - "futures-lite 1.13.0", - "gloo-timers", + "futures-lite 2.6.1", + "gloo-timers 0.3.0", "kv-log-macro", "log", "memchr", @@ -1606,9 +1716,9 @@ dependencies = [ [[package]] name = "async-stream" -version = "0.3.5" +version = "0.3.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cd56dd203fef61ac097dd65721a419ddccb106b2d2b70ba60a6b529f03961a51" +checksum = "0b5a71a6f37880a80d1d7f19efd781e4b5de42c88f0722cc13bcb6cc2cfe8476" dependencies = [ "async-stream-impl", "futures-core", @@ -1617,13 +1727,13 @@ dependencies = [ [[package]] name = "async-stream-impl" -version = "0.3.5" +version = "0.3.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "16e62a023e7c117e27523144c5d2459f4397fcc3cab0085af8e2224f643a0193" +checksum = "c7c24de15d275a1ecfd47a380fb4d5ec9bfe0933f309ed5e705b775596a3574d" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -1634,13 +1744,13 @@ checksum = "8b75356056920673b02621b35afd0f7dda9306d03c79a30f5c56c44cf256e3de" [[package]] name = "async-trait" -version = "0.1.88" +version = "0.1.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e539d3fca749fcee5236ab05e93a52867dd549cc157c8cb7f99595f3cedffdb5" +checksum = "9035ad2d096bed7955a320ee7e2230574d28fd3c3a0f186cbea1ff3c7eed5dbb" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -1686,9 +1796,9 @@ checksum = "a8ab6b55fe97976e46f91ddbed8d147d966475dc29b2032757ba47e02376fbc3" [[package]] name = "atomic-waker" -version = "1.1.1" +version = "1.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1181e1e0d1fce796a03db1ae795d67167da795f9cf4a39c37589e85ef57f26d3" +checksum = "1505bd5d3d116872e7271a6d4e16d81d0c8570876c8de68093a09ac269d8aac0" [[package]] name = "attohttpc" @@ -1696,28 +1806,37 @@ version = "0.24.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8d9a9bf8b79a749ee0b911b91b671cc2b6c670bdbc7e3dfd537576ddc94bb2a2" dependencies = [ - "http 0.2.9", + "http 0.2.12", "log", "url", ] +[[package]] +name = "aurora-engine-modexp" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "518bc5745a6264b5fd7b09dffb9667e400ee9e2bbe18555fac75e1fe9afa0df9" +dependencies = [ + "hex", + "num", +] + [[package]] name = "auto_impl" -version = "1.1.0" +version = "1.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fee3da8ef1276b0bee5dd1c7258010d8fffd31801447323115a25560e1327b89" +checksum = "ffdcb70bdbc4d478427380519163274ac86e52916e10f0a8889adf0f96d3fee7" dependencies = [ - "proc-macro-error", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 1.0.109", + "syn 2.0.106", ] [[package]] name = "autocfg" -version = "1.1.0" +version = "1.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" +checksum = "c08606f8c3cbf4ce6ec8e28fb0014a2c086708fe954eaa885384a6165172e7e8" [[package]] name = "average" @@ -1730,30 +1849,36 @@ dependencies = [ "num-traits", ] +[[package]] +name = "az" +version = "1.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b7e4c2464d97fe331d41de9d5db0def0a96f4d823b8b32a2efd503578988973" + [[package]] name = "backoff" version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b62ddb9cb1ec0a098ad4bbf9344d0713fa193ae1a80af55febcff2627b6a00c1" dependencies = [ - "getrandom 0.2.10", + "getrandom 0.2.16", "instant", "rand 0.8.5", ] [[package]] name = "backtrace" -version = "0.3.71" +version = "0.3.75" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "26b05800d2e817c8b3b4b54abd461726265fa9789ae34330622f2db9ee696f9d" +checksum = "6806a6321ec58106fea15becdad98371e28d92ccbc7c8f1b3b6dd724fe8f1002" dependencies = [ - "addr2line 0.21.0", - "cc", + "addr2line", "cfg-if", "libc", "miniz_oxide", - "object 0.32.2", + "object", "rustc-demangle", + "windows-targets 0.52.6", ] [[package]] @@ -1794,15 +1919,15 @@ checksum = "72b3254f16251a8381aa12e40e3c4d2f0199f8c6508fbecb9d91f575e0fbb8c6" [[package]] name = "base64ct" -version = "1.6.0" +version = "1.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8c3c1a368f70d6cf7302d78f8f7093da241fb8e8807c05cc9e51a125895a6d5b" +checksum = "55248b47b0caf0546f7988906588779981c43bb1bc9d0c44087278f80cdb44ba" [[package]] name = "binary-merkle-tree" version = "13.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "hash-db", "log", "parity-scale-codec", @@ -1832,35 +1957,36 @@ dependencies = [ "lazycell", "peeking_take_while", "prettyplease", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "regex", "rustc-hash 1.1.0", "shlex", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "bip32" -version = "0.5.2" +version = "0.5.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aa13fae8b6255872fd86f7faf4b41168661d7d78609f7bfe6771b85c6739a15b" +checksum = "db40d3dfbeab4e031d78c844642fa0caa0b0db11ce1607ac9d2986dff1405c69" dependencies = [ "bs58", "hmac 0.12.1", "k256", "rand_core 0.6.4", "ripemd", - "sha2 0.10.8", - "subtle 2.5.0", + "secp256k1 0.27.0", + "sha2 0.10.9", + "subtle 2.6.1", "zeroize", ] [[package]] name = "bip39" -version = "2.1.0" +version = "2.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "33415e24172c1b7d6066f6d999545375ab8e1d95421d6784bdfff9496f292387" +checksum = "43d193de1f7487df1914d3a568b772458861d33f9c54249612cc2893d6915054" dependencies = [ "bitcoin_hashes 0.13.0", "serde", @@ -1901,7 +2027,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1930a4dabfebb8d7d9992db18ebe3ae2876f0a305fab206fd168df931ede293b" dependencies = [ "bitcoin-internals", - "hex-conservative 0.1.1", + "hex-conservative 0.1.2", ] [[package]] @@ -1922,9 +2048,9 @@ checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" [[package]] name = "bitflags" -version = "2.6.0" +version = "2.9.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b048fb63fd8b5923fc5aa7b340d8e156aec7ec02f0c78fa8a6ddc2613f6f71de" +checksum = "34efbcccd345379ca2868b2b2c9d3782e9cc58ba87bc7d79d5b53d9c9ae6f25d" dependencies = [ "serde", ] @@ -1975,37 +2101,37 @@ dependencies = [ [[package]] name = "blake2b_simd" -version = "1.0.2" +version = "1.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "23285ad32269793932e830392f2fe2f83e26488fd3ec778883a93c8323735780" +checksum = "06e903a20b159e944f91ec8499fe1e55651480c541ea0a584f5d967c49ad9d99" dependencies = [ "arrayref", - "arrayvec 0.7.4", - "constant_time_eq 0.3.0", + "arrayvec 0.7.6", + "constant_time_eq 0.3.1", ] [[package]] name = "blake2s_simd" -version = "1.0.1" +version = "1.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6637f448b9e61dfadbdcbae9a885fadee1f3eaffb1f8d3c1965d3ade8bdfd44f" +checksum = "e90f7deecfac93095eb874a40febd69427776e24e1bd7f87f33ac62d6f0174df" dependencies = [ "arrayref", - "arrayvec 0.7.4", - "constant_time_eq 0.2.6", + "arrayvec 0.7.6", + "constant_time_eq 0.3.1", ] [[package]] name = "blake3" -version = "1.5.4" +version = "1.8.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d82033247fd8e890df8f740e407ad4d038debb9eb1f40533fffb32e7d17dc6f7" +checksum = "3888aaa89e4b2a40fca9848e400f6a658a5a3978de7be858e209cafa8be9a4a0" dependencies = [ "arrayref", - "arrayvec 0.7.4", + "arrayvec 0.7.6", "cc", "cfg-if", - "constant_time_eq 0.3.0", + "constant_time_eq 0.3.1", ] [[package]] @@ -2028,17 +2154,27 @@ dependencies = [ [[package]] name = "blocking" -version = "1.3.1" +version = "1.6.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "77231a1c8f801696fc0123ec6150ce92cffb8e164a02afb9c8ddee0e9b65ad65" +checksum = "e83f8d02be6967315521be875afa792a316e28d57b5a2d401897e2a7921b7f21" dependencies = [ - "async-channel 1.9.0", - "async-lock 2.8.0", + "async-channel 2.5.0", "async-task", - "atomic-waker", - "fastrand 1.9.0", - "futures-lite 1.13.0", - "log", + "futures-io", + "futures-lite 2.6.1", + "piper", +] + +[[package]] +name = "blst" +version = "0.3.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4fd49896f12ac9b6dcd7a5998466b9b58263a695a3dd1ecc1aaca2e12a90b080" +dependencies = [ + "cc", + "glob", + "threadpool", + "zeroize", ] [[package]] @@ -2055,9 +2191,9 @@ dependencies = [ [[package]] name = "bounded-collections" -version = "0.2.3" +version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "32ed0a820ed50891d36358e997d27741a6142e382242df40ff01c89bcdcc7a2b" +checksum = "64ad8a0bed7827f0b07a5d23cec2e58cc02038a99e4ca81616cb2bb2025f804d" dependencies = [ "log", "parity-scale-codec", @@ -2075,7 +2211,7 @@ dependencies = [ "log", "parity-scale-codec", "scale-info", - "schemars", + "schemars 1.0.4", "serde", ] @@ -2085,7 +2221,7 @@ version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "68534a48cbf63a4b1323c433cf21238c9ec23711e0df13b08c33e5c2082663ce" dependencies = [ - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -2797,18 +2933,18 @@ version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bf88ba1141d185c399bee5288d850d63b8369520c1eafc32a0430b5b6c287bf4" dependencies = [ - "sha2 0.10.8", + "sha2 0.10.9", "tinyvec", ] [[package]] name = "bstr" -version = "1.6.0" +version = "1.12.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6798148dccfbff0fae41c7574d2fa8f1ef3492fba0face179de5d8d447d67b05" +checksum = "234113d19d0d7d613b40e86fb654acf958910802bcceab913a4f9e7cda03b1a4" dependencies = [ "memchr", - "regex-automata 0.3.6", + "regex-automata 0.4.10", "serde", ] @@ -2844,9 +2980,9 @@ checksum = "e3b5ca7a04898ad4bcd41c90c5285445ff5b791899bb1b0abdd2a2aa791211d7" [[package]] name = "bytemuck" -version = "1.13.1" +version = "1.23.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "17febce684fd15d89027105661fec94afb475cb995fbc59d2865198446ba2eea" +checksum = "3995eaeebcdf32f91f980d360f78732ddc061097ab4e39991ae7a6ace9194677" [[package]] name = "byteorder" @@ -2865,15 +3001,29 @@ dependencies = [ [[package]] name = "bzip2-sys" -version = "0.1.11+1.0.8" +version = "0.1.13+1.0.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "736a955f3fa7875102d57c82b8cac37ec45224a07fd32d58f9f7a186b6cd4cdc" +checksum = "225bff33b2141874fe80d71e07d6eec4f85c5c216453dd96388240f96e1acc14" dependencies = [ "cc", - "libc", "pkg-config", ] +[[package]] +name = "c-kzg" +version = "2.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7318cfa722931cb5fe0838b98d3ce5621e75f6a6408abc21721d80de9223f2e4" +dependencies = [ + "blst", + "cc", + "glob", + "hex", + "libc", + "once_cell", + "serde", +] + [[package]] name = "c2-chacha" version = "0.3.3" @@ -2886,18 +3036,18 @@ dependencies = [ [[package]] name = "camino" -version = "1.1.6" +version = "1.1.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c59e92b5a388f549b863a7bea62612c09f24c8393560709a54558a9abdfb3b9c" +checksum = "5d07aa9a93b00c76f71bc35d598bed923f6d4f3a9ca5c24b7737ae1a292841c0" dependencies = [ "serde", ] [[package]] name = "cargo-platform" -version = "0.1.3" +version = "0.1.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2cfa25e60aea747ec7e1124f238816749faa93759c6ff5b31f1ccdda137f4479" +checksum = "e35af189006b9c0f00a064685c727031e3ed2d8020f7ba284d78cc2671bd36ea" dependencies = [ "serde", ] @@ -2910,10 +3060,10 @@ checksum = "eee4243f1f26fc7a42710e7439c149e2b10b05472f88090acce52632f231a73a" dependencies = [ "camino", "cargo-platform", - "semver 1.0.18", + "semver 1.0.26", "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -2930,9 +3080,9 @@ checksum = "a2698f953def977c68f935bb0dfa959375ad4638570e969e2f1e9f433cbf1af6" [[package]] name = "cc" -version = "1.1.24" +version = "1.2.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "812acba72f0a070b003d3697490d2b55b837230ae7c6c6497f05cc2ddbb8d938" +checksum = "42bc4aea80032b7bf409b0bc7ccad88853858911b7713a8062fdc0623867bedc" dependencies = [ "jobserver", "libc", @@ -2951,23 +3101,23 @@ version = "0.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6fac387a98bb7c37292057cffc56d62ecb629900026402633ae9160df93a8766" dependencies = [ - "nom", + "nom 7.1.3", ] [[package]] name = "cfg-expr" -version = "0.15.5" +version = "0.15.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "03915af431787e6ffdcc74c645077518c6b6e01f80b761e0fbbfa288536311b3" +checksum = "d067ad48b8650848b989a59a86c6c36a995d02d2bf778d45c3c5d57bc2718f02" dependencies = [ "smallvec", ] [[package]] name = "cfg-if" -version = "1.0.0" +version = "1.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" +checksum = "2fd1289c04a9ea8cb22300a459a72a385d7c73d3259e2ed7dcb2af674838cfa9" [[package]] name = "cfg_aliases" @@ -3038,9 +3188,9 @@ dependencies = [ [[package]] name = "chrono" -version = "0.4.40" +version = "0.4.41" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1a7964611d71df112cb1730f2ee67324fcf4d0fc6606acbbe9bfe06df124637c" +checksum = "c469d952047f47f91b68d1cba3f10d63c11d73e4636f24f08daf0278abf01c4d" dependencies = [ "android-tzdata", "iana-time-zone", @@ -3053,9 +3203,9 @@ dependencies = [ [[package]] name = "ciborium" -version = "0.2.1" +version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "effd91f6c78e5a4ace8a5d3c0b6bfaec9e2baaef55f3efc00e45fb2e477ee926" +checksum = "42e69ffd6f0917f5c029256a24d0161db17cea3997d185db0d35926308770f0e" dependencies = [ "ciborium-io", "ciborium-ll", @@ -3064,15 +3214,15 @@ dependencies = [ [[package]] name = "ciborium-io" -version = "0.2.1" +version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cdf919175532b369853f5d5e20b26b43112613fd6fe7aee757e35f7a44642656" +checksum = "05afea1e0a06c9be33d539b876f1ce3692f4afea2cb41f740e7743225ed1c757" [[package]] name = "ciborium-ll" -version = "0.2.1" +version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "defaa24ecc093c77630e6c15e17c51f5e187bf35ee514f4e2d67baaa96dae22b" +checksum = "57663b653d948a338bfb3eeba9bb2fd5fcfaecb9e199e87e1eda4d9e8b240fd9" dependencies = [ "ciborium-io", "half", @@ -3099,7 +3249,7 @@ checksum = "3147d8272e8fa0ccd29ce51194dd98f79ddfb8191ba9e3409884e751798acf3a" dependencies = [ "core2", "multibase", - "multihash 0.19.1", + "multihash 0.19.3", "unsigned-varint 0.8.0", ] @@ -3125,9 +3275,9 @@ dependencies = [ [[package]] name = "clang-sys" -version = "1.6.1" +version = "1.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c688fc74432808e3eb684cae8830a86be1d66a2bd58e1f248ed0960a590baf6f" +checksum = "0b023947811758c97c59bf9d1c188fd619ad4718dcaa767947df1cadb14f39f4" dependencies = [ "glob", "libc", @@ -3136,9 +3286,9 @@ dependencies = [ [[package]] name = "clap" -version = "4.5.13" +version = "4.5.45" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0fbb260a053428790f3de475e304ff84cdbc4face759ea7a3e64c1edd938a7fc" +checksum = "1fc0e74a703892159f5ae7d3aac52c8e6c392f5ae5f359c70b5881d60aaac318" dependencies = [ "clap_builder", "clap_derive", @@ -3146,9 +3296,9 @@ dependencies = [ [[package]] name = "clap_builder" -version = "4.5.13" +version = "4.5.44" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "64b17d7ea74e9f833c7dbf2cbe4fb12ff26783eda4782a8975b72f895c9b4d99" +checksum = "b3e7f4214277f3c7aa526a59dd3fbe306a370daee1f8b7b8c987069cd8e888a8" dependencies = [ "anstream", "anstyle", @@ -3159,39 +3309,39 @@ dependencies = [ [[package]] name = "clap_complete" -version = "4.5.13" +version = "4.5.57" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aa3c596da3cf0983427b0df0dba359df9182c13bd5b519b585a482b0c351f4e8" +checksum = "4d9501bd3f5f09f7bbee01da9a511073ed30a80cd7a509f1214bb74eadea71ad" dependencies = [ "clap", ] [[package]] name = "clap_derive" -version = "4.5.13" +version = "4.5.45" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "501d359d5f3dcaf6ecdeee48833ae73ec6e42723a1e52419c79abf9507eec0a0" +checksum = "14cb31bb0a7d536caef2639baa7fad459e15c3144efefa6dbd1c84562c4739f6" dependencies = [ "heck 0.5.0", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "clap_lex" -version = "0.7.0" +version = "0.7.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "98cc8fbded0c607b7ba9dd60cd98df59af97e84d24e49c8557331cfc26d301ce" +checksum = "b94f61472cee1439c0b966b47e3aca9ae07e45d070759512cd390ea2bebc6675" [[package]] name = "cmd_lib" -version = "1.9.5" +version = "1.9.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "371c15a3c178d0117091bd84414545309ca979555b1aad573ef591ad58818d41" +checksum = "1af0f9b65935ff457da75535a6b6ff117ac858f03f71191188b3b696f90aec5a" dependencies = [ "cmd_lib_macros", - "env_logger 0.10.1", + "env_logger 0.10.2", "faccess", "lazy_static", "log", @@ -3200,25 +3350,24 @@ dependencies = [ [[package]] name = "cmd_lib_macros" -version = "1.9.5" +version = "1.9.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cb844bd05be34d91eb67101329aeba9d3337094c04fd8507d821db7ebb488eaf" +checksum = "1e69eee115667ccda8b9ed7010bcf13356ad45269fc92aa78534890b42809a64" dependencies = [ "proc-macro-error2", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "coarsetime" -version = "0.1.23" +version = "0.1.36" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a90d114103adbc625300f346d4d09dfb4ab1c4a8df6868435dd903392ecf4354" +checksum = "91849686042de1b41cd81490edc83afbcb0abe5a9b6f2c4114f23ce8cca1bcf4" dependencies = [ "libc", - "once_cell", - "wasi 0.11.0+wasi-snapshot-preview1", + "wasix", "wasm-bindgen", ] @@ -3228,17 +3377,18 @@ version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0fa961b519f0b462e3a3b4a34b64d119eeaca1d59af726fe450bbba07a9fc0a1" dependencies = [ - "thiserror 2.0.12", + "thiserror 2.0.16", ] [[package]] name = "codespan-reporting" -version = "0.11.1" +version = "0.12.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3538270d33cc669650c4b093848450d380def10c331d38c768e34cac80576e6e" +checksum = "fe6d2e5af09e8c8ad56c969f2157a3d4238cebc7c55f0a517728c38f7b200f81" dependencies = [ + "serde", "termcolor", - "unicode-width 0.1.10", + "unicode-width", ] [[package]] @@ -3362,9 +3512,9 @@ dependencies = [ [[package]] name = "color-eyre" -version = "0.6.3" +version = "0.6.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "55146f5e46f237f7423d74111267d4597b59b0dad0ffaf7303bce9945d843ad5" +checksum = "e5920befb47832a6d61ee3a3a846565cfa39b331331e68a3b1d1116630f2f26d" dependencies = [ "backtrace", "eyre", @@ -3375,47 +3525,46 @@ dependencies = [ [[package]] name = "color-print" -version = "0.3.4" +version = "0.3.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f2a5e6504ed8648554968650feecea00557a3476bc040d0ffc33080e66b646d0" +checksum = "3aa954171903797d5623e047d9ab69d91b493657917bdfb8c2c80ecaf9cdb6f4" dependencies = [ "color-print-proc-macro", ] [[package]] name = "color-print-proc-macro" -version = "0.3.4" +version = "0.3.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d51beaa537d73d2d1ff34ee70bc095f170420ab2ec5d687ecd3ec2b0d092514b" +checksum = "692186b5ebe54007e45a59aea47ece9eb4108e141326c304cdc91699a7118a22" dependencies = [ - "nom", - "proc-macro2 1.0.95", + "nom 7.1.3", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 1.0.109", + "syn 2.0.106", ] [[package]] name = "colorchoice" -version = "1.0.0" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "acbf1af155f9b9ef647e42cdc158db4b64a1b61f743629225fde6f3e0be2a7c7" +checksum = "b05b61dc5112cbb17e4b6cd61790d9845d13888356391624cbe7e41efeac1e75" [[package]] name = "colored" -version = "2.0.4" +version = "2.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2674ec482fbc38012cf31e6c42ba0177b431a0cb6f15fe40efa5aab1bda516f6" +checksum = "117725a109d387c937a1533ce01b450cbde6b88abceea8473c4d7a85853cda3c" dependencies = [ - "is-terminal", "lazy_static", - "windows-sys 0.48.0", + "windows-sys 0.59.0", ] [[package]] name = "combine" -version = "4.6.6" +version = "4.6.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "35ed6e9d84f0b51a7f52daf1c7d71dd136fd7a3f41a8462b8cdb8c78d920fad4" +checksum = "ba5a308b75df32fe02788e748662718f03fde005016435c444eea572398219fd" dependencies = [ "bytes", "memchr", @@ -3428,7 +3577,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4a65ebfec4fb190b6f90e944a817d60499ee0744e582530e2c9900a22e591d9a" dependencies = [ "unicode-segmentation", - "unicode-width 0.2.0", + "unicode-width", ] [[package]] @@ -3448,22 +3597,22 @@ dependencies = [ [[package]] name = "console" -version = "0.15.8" +version = "0.15.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0e1f83fc076bd6dd27517eacdf25fef6c4dfe5f1d7448bafaaf3a26f13b5e4eb" +checksum = "054ccb5b10f9f2cbf51eb355ca1d05c2d279ce1804688d0db74b4733a5aeafd8" dependencies = [ "encode_unicode", - "lazy_static", "libc", - "unicode-width 0.1.10", - "windows-sys 0.52.0", + "once_cell", + "unicode-width", + "windows-sys 0.59.0", ] [[package]] name = "const-hex" -version = "1.14.0" +version = "1.15.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4b0485bab839b018a8f1723fc5391819fea5f8f0f32288ef8a735fd096b6160c" +checksum = "dccd746bf9b1038c0507b7cec21eb2b11222db96a2902c96e8c185d6d20fb9c4" dependencies = [ "cfg-if", "cpufeatures", @@ -3474,29 +3623,27 @@ dependencies = [ [[package]] name = "const-oid" -version = "0.9.5" +version = "0.9.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "28c122c3980598d243d63d9a704629a2d748d101f278052ff068be5a4423ab6f" +checksum = "c2459377285ad874054d797f3ccebf984978aa39129f6eafde5cdc8315b612f8" [[package]] name = "const-random" -version = "0.1.15" +version = "0.1.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "368a7a772ead6ce7e1de82bfb04c485f3db8ec744f72925af5735e29a22cc18e" +checksum = "87e00182fe74b066627d63b85fd550ac2998d4b0bd86bfed477a0ae4c7c71359" dependencies = [ "const-random-macro", - "proc-macro-hack", ] [[package]] name = "const-random-macro" -version = "0.1.15" +version = "0.1.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9d7d6ab3c3a2282db210df5f02c4dab6e0a7057af0fb7ebd4070f30fe05c0ddb" +checksum = "f9d839f2a20b0aee515dc581a6172f2321f96cab76c1a38a4c584a194955390e" dependencies = [ - "getrandom 0.2.10", + "getrandom 0.2.16", "once_cell", - "proc-macro-hack", "tiny-keccak", ] @@ -3515,9 +3662,9 @@ version = "0.2.34" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1d57c2eccfb16dbac1f4e61e206105db5820c9d26c3c472bc17c774259ef7744" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "unicode-xid 0.2.4", + "unicode-xid 0.2.6", ] [[package]] @@ -3528,21 +3675,24 @@ checksum = "245097e9a4535ee1e3e3931fcfcd55a796a44c643e8596ff6566d68f09b87bbc" [[package]] name = "constant_time_eq" -version = "0.2.6" +version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "21a53c0a4d288377e7415b53dcfc3c04da5cdc2cc95c8d5ac178b58f0b861ad6" +checksum = "7c74b8349d32d297c9134b8c88677813a227df8f779daa29bfc29c183fe3dca6" [[package]] -name = "constant_time_eq" -version = "0.3.0" +name = "convert_case" +version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f7144d30dcf0fafbce74250a3963025d8d52177934239851c917d29f1df280c2" +checksum = "6245d59a3e82a7fc217c5828a6692dbc6dfb63a0c8c90495621f7b9d79704a0e" [[package]] name = "convert_case" -version = "0.4.0" +version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6245d59a3e82a7fc217c5828a6692dbc6dfb63a0c8c90495621f7b9d79704a0e" +checksum = "bb402b8d4c85569410425650ce3eddc7d698ed96d39a73f941b08fb63082f1e7" +dependencies = [ + "unicode-segmentation", +] [[package]] name = "core-foundation" @@ -3554,11 +3704,21 @@ dependencies = [ "libc", ] +[[package]] +name = "core-foundation" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b2a6cd9ae233e7f62ba4e9353e81a88df7fc8a5987b8d445b4d90c879bd156f6" +dependencies = [ + "core-foundation-sys", + "libc", +] + [[package]] name = "core-foundation-sys" -version = "0.8.6" +version = "0.8.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "06ea2b9bc92be3c2baa9334a323ebca2d6f074ff852cd1d7b11064035cd3868f" +checksum = "773648b94d0e5d620f64f280777445740e61fe701025087ec8b57f45c791888b" [[package]] name = "core2" @@ -3768,9 +3928,9 @@ dependencies = [ [[package]] name = "cpp_demangle" -version = "0.4.3" +version = "0.4.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7e8227005286ec39567949b33df9896bcadfa6051bccca2488129f108ca23119" +checksum = "96e58d342ad113c2b878f16d5d034c03be492ae460cdbc02b7f0f2284d310c7d" dependencies = [ "cfg-if", ] @@ -3787,9 +3947,9 @@ dependencies = [ [[package]] name = "cpufeatures" -version = "0.2.9" +version = "0.2.17" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a17b76ff3a4162b0b27f354a0c87015ddad39d35f9c0c36607a3bdd175dde1f1" +checksum = "59ed5838eebb26a2bb2e58f6d5b5316989ae9d08bab10e0e6d103e656d1b0280" dependencies = [ "libc", ] @@ -3846,8 +4006,8 @@ dependencies = [ "cranelift-control", "cranelift-entity", "cranelift-isle", - "gimli 0.31.1", - "hashbrown 0.15.3", + "gimli", + "hashbrown 0.15.5", "log", "pulley-interpreter", "regalloc2 0.12.2", @@ -3933,9 +4093,9 @@ checksum = "b530783809a55cb68d070e0de60cfbb3db0dc94c8850dd5725411422bedcf6bb" [[package]] name = "crc" -version = "3.2.1" +version = "3.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "69e6e4d7b33a94f0991c26729976b10ebde1d34c3ee82408fb536164fa10d636" +checksum = "9710d3b3739c2e349eb44fe848ad0b7c8cb1e42bd87ee49371df2f7acaf3e675" dependencies = [ "crc-catalog", ] @@ -3948,9 +4108,9 @@ checksum = "19d374276b40fb8bbdee95aef7c7fa6b5316ec764510eb64b8dd0e2ed0d7e7f5" [[package]] name = "crc32fast" -version = "1.3.2" +version = "1.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b540bd8bc810d3885c6ea91e2018302f68baba2129ab3e88f32389ee9370880d" +checksum = "9481c1c90cbf2ac953f07c8d4a58aa3945c425b7185c9154d67a65e4230da511" dependencies = [ "cfg-if", ] @@ -4010,58 +4170,53 @@ dependencies = [ [[package]] name = "crossbeam-deque" -version = "0.8.3" +version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ce6fd6f855243022dcecf8702fef0c297d4338e226845fe067f6341ad9fa0cef" +checksum = "9dd111b7b7f7d55b72c0a6ae361660ee5853c9af73f70c3c2ef6858b950e2e51" dependencies = [ - "cfg-if", "crossbeam-epoch", "crossbeam-utils", ] [[package]] name = "crossbeam-epoch" -version = "0.9.15" +version = "0.9.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ae211234986c545741a7dc064309f67ee1e5ad243d0e48335adc0484d960bcc7" +checksum = "5b82ac4a3c2ca9c3460964f020e1402edd5753411d7737aa39c3714ad1b5420e" dependencies = [ - "autocfg", - "cfg-if", "crossbeam-utils", - "memoffset", - "scopeguard", ] [[package]] name = "crossbeam-queue" -version = "0.3.11" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "df0346b5d5e76ac2fe4e327c5fd1118d6be7c51dfb18f9b7922923f287471e35" +checksum = "0f58bbc28f91df819d0aa2a2c00cd19754769c2fad90579b3592b1c9ba7a3115" dependencies = [ "crossbeam-utils", ] [[package]] name = "crossbeam-utils" -version = "0.8.20" +version = "0.8.21" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "22ec99545bb0ed0ea7bb9b8e1e9122ea386ff8a48c0922e43f36d45ab09e0e80" +checksum = "d0a5c400df2834b80a4c3327b3aad3a4c4cd4de0629063962b03235697506a28" [[package]] name = "crunchy" -version = "0.2.2" +version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a81dae078cea95a014a339291cec439d2f232ebe854a9d672b796c6afafa9b7" +checksum = "460fbee9c2c2f33933d720630a6a0bac33ba7053db5344fac858d4b8952d77d5" [[package]] name = "crypto-bigint" -version = "0.5.2" +version = "0.5.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cf4c2f4e1afd912bc40bfd6fed5d9dc1f288e0ba01bfcc835cc5bc3eb13efe15" +checksum = "0dc92fb57ca44df6db8059111ab3af99a63d5d0f8375d9972e319a379c6bab76" dependencies = [ "generic-array 0.14.7", "rand_core 0.6.4", - "subtle 2.5.0", + "subtle 2.6.1", "zeroize", ] @@ -4093,7 +4248,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b584a330336237c1eecd3e94266efb216c56ed91225d634cb2991c5f3fd1aeab" dependencies = [ "generic-array 0.14.7", - "subtle 2.5.0", + "subtle 2.6.1", ] [[package]] @@ -4107,7 +4262,7 @@ dependencies = [ "generic-array 0.14.7", "poly1305", "salsa20", - "subtle 2.5.0", + "subtle 2.6.1", "zeroize", ] @@ -4122,11 +4277,11 @@ dependencies = [ [[package]] name = "ctrlc" -version = "3.4.5" +version = "3.4.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "90eeab0aa92f3f9b4e87f258c72b139c207d251f9cbc1080a0086b86a8870dd3" +checksum = "46f93780a459b7d656ef7f071fe699c4d3d2cb201c4b24d085b6ddc505276e73" dependencies = [ - "nix 0.29.0", + "nix 0.30.1", "windows-sys 0.59.0", ] @@ -4134,7 +4289,7 @@ dependencies = [ name = "cumulus-client-bootnodes" version = "0.1.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "async-channel 1.9.0", "cumulus-primitives-core", "cumulus-relay-chain-interface", @@ -4183,7 +4338,7 @@ dependencies = [ "cumulus-test-runtime", "futures", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-node-primitives", "polkadot-node-subsystem", "polkadot-node-subsystem-test-helpers", @@ -4216,7 +4371,7 @@ dependencies = [ "cumulus-test-relay-sproof-builder", "futures", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-node-primitives", "polkadot-node-subsystem", "polkadot-node-subsystem-util", @@ -4303,7 +4458,7 @@ dependencies = [ "sp-inherents", "sp-runtime", "sp-state-machine", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -4315,7 +4470,7 @@ dependencies = [ "cumulus-primitives-core", "cumulus-relay-chain-interface", "futures", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-consensus", "sp-api", "sp-block-builder", @@ -4340,7 +4495,7 @@ dependencies = [ "futures", "futures-timer", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-node-primitives", "polkadot-node-subsystem", "polkadot-parachain-primitives", @@ -4512,7 +4667,7 @@ dependencies = [ "frame-support", "frame-system", "futures", - "hashbrown 0.15.3", + "hashbrown 0.15.5", "hex-literal", "impl-trait-for-tuples", "log", @@ -4549,10 +4704,10 @@ dependencies = [ name = "cumulus-pallet-parachain-system-proc-macro" version = "0.6.0" dependencies = [ - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -4670,7 +4825,7 @@ dependencies = [ "sp-io", "sp-maybe-compressed-blob", "tracing", - "tracing-subscriber", + "tracing-subscriber 0.3.19", ] [[package]] @@ -4812,14 +4967,14 @@ dependencies = [ "sp-blockchain", "sp-state-machine", "sp-version", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] name = "cumulus-relay-chain-minimal-node" version = "0.7.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "async-channel 1.9.0", "async-trait", "cumulus-client-bootnodes", @@ -4884,7 +5039,7 @@ dependencies = [ "sp-storage 19.0.0", "sp-version", "substrate-prometheus-endpoint", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-util", "tracing", @@ -5091,7 +5246,7 @@ version = "0.1.0" dependencies = [ "anyhow", "cumulus-zombienet-sdk-helpers", - "env_logger 0.11.3", + "env_logger 0.11.8", "futures", "log", "polkadot-primitives", @@ -5108,24 +5263,24 @@ dependencies = [ [[package]] name = "curl" -version = "0.4.46" +version = "0.4.49" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1e2161dd6eba090ff1594084e95fd67aeccf04382ffea77999ea94ed42ec67b6" +checksum = "79fc3b6dd0b87ba36e565715bf9a2ced221311db47bd18011676f24a6066edbc" dependencies = [ "curl-sys", "libc", "openssl-probe", "openssl-sys", "schannel", - "socket2 0.5.9", - "windows-sys 0.52.0", + "socket2 0.6.0", + "windows-sys 0.59.0", ] [[package]] name = "curl-sys" -version = "0.4.72+curl-8.6.0" +version = "0.4.83+curl-8.15.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "29cbdc8314c447d11e8fd156dcdd031d9e02a7a976163e396b548c03153bc9ea" +checksum = "5830daf304027db10c82632a464879d46a3f7c4ba17a31592657ad16c719b483" dependencies = [ "cc", "libc", @@ -5134,7 +5289,7 @@ dependencies = [ "openssl-sys", "pkg-config", "vcpkg", - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] @@ -5148,20 +5303,20 @@ dependencies = [ "curve25519-dalek-derive", "digest 0.10.7", "fiat-crypto", - "rustc_version 0.4.0", - "subtle 2.5.0", + "rustc_version 0.4.1", + "subtle 2.6.1", "zeroize", ] [[package]] name = "curve25519-dalek-derive" -version = "0.1.0" +version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "83fdaf97f4804dcebfa5862639bc9ce4121e82140bec2a987ac5140294865b5b" +checksum = "f46882e17999c6cc590af592290432be3bce0428cb0d5f8b6715e4dc7b383eb3" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -5179,53 +5334,71 @@ dependencies = [ [[package]] name = "cxx" -version = "1.0.106" +version = "1.0.169" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "28403c86fc49e3401fdf45499ba37fad6493d9329449d6449d7f0e10f4654d28" +checksum = "df881e2764e20d320c9c8ddd8670018b1abaa2557e73811f03d5b2643da671d7" dependencies = [ "cc", + "cxxbridge-cmd", "cxxbridge-flags", "cxxbridge-macro", + "foldhash 0.2.0", "link-cplusplus", ] [[package]] name = "cxx-build" -version = "1.0.106" +version = "1.0.169" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "78da94fef01786dc3e0c76eafcd187abcaa9972c78e05ff4041e24fdf059c285" +checksum = "acef58f684c0c9b7bffc111657c9f1364e4fa47af46fd7f03b71b7a4066ac372" dependencies = [ "cc", "codespan-reporting", - "once_cell", - "proc-macro2 1.0.95", + "indexmap", + "proc-macro2 1.0.101", "quote 1.0.40", "scratch", - "syn 2.0.98", + "syn 2.0.106", +] + +[[package]] +name = "cxxbridge-cmd" +version = "1.0.169" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "669616995d33251cb7215f96820d78a810ee218573246830fb96f29961e1712a" +dependencies = [ + "clap", + "codespan-reporting", + "indexmap", + "proc-macro2 1.0.101", + "quote 1.0.40", + "syn 2.0.106", ] [[package]] name = "cxxbridge-flags" -version = "1.0.106" +version = "1.0.169" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e2a6f5e1dfb4b34292ad4ea1facbfdaa1824705b231610087b00b17008641809" +checksum = "9aebcb754a24722d34e7f4e021376862179194cc5ec83ded2dd84b9db36be106" [[package]] name = "cxxbridge-macro" -version = "1.0.106" +version = "1.0.169" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "50c49547d73ba8dcfd4ad7325d64c6d5391ff4224d498fc39a6f3f49825a530d" +checksum = "3ea9594efbebf2f822925b6368eea741dd2677bb411313e50c2de8ba8c3d3a62" dependencies = [ - "proc-macro2 1.0.95", + "indexmap", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "rustversion", + "syn 2.0.106", ] [[package]] name = "darling" -version = "0.20.10" +version = "0.20.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6f63b86c8a8826a49b8c21f08a2d07338eec8d900540f8630dc76284be802989" +checksum = "fc7f46116c46ff9ab3eb1597a45688b6715c6e628b5c133e288e709a29bcb4ee" dependencies = [ "darling_core", "darling_macro", @@ -5233,53 +5406,53 @@ dependencies = [ [[package]] name = "darling_core" -version = "0.20.10" +version = "0.20.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "95133861a8032aaea082871032f5815eb9e98cef03fa916ab4500513994df9e5" +checksum = "0d00b9596d185e565c2207a0b01f8bd1a135483d02d9b7b0a54b11da8d53412e" dependencies = [ "fnv", "ident_case", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "strsim", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "darling_macro" -version = "0.20.10" +version = "0.20.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d336a2a514f6ccccaa3e09b02d41d35330c07ddf03a62165fcec10bb561c7806" +checksum = "fc34b93ccb385b40dc71c6fceac4b2ad23662c7eeb248cf10d529b7e055b6ead" dependencies = [ "darling_core", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "dashmap" -version = "5.5.1" +version = "5.5.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "edd72493923899c6f10c641bdbdeddc7183d6396641d99c1a0d1597f37f92e28" +checksum = "978747c1d849a7d2ee5e8adc0159961c48fb7e5db2f06af6723b80123bb53856" dependencies = [ "cfg-if", "hashbrown 0.14.5", "lock_api", "once_cell", - "parking_lot_core 0.9.8", + "parking_lot_core 0.9.11", ] [[package]] name = "data-encoding" -version = "2.6.0" +version = "2.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e8566979429cf69b49a5c740c60791108e86440e8be149bbea4fe54d2c32d6e2" +checksum = "2a2330da5de22e8a3cb63252ce2abb30116bf5265e89c0e01bc17015ce30a476" [[package]] name = "data-encoding-macro" -version = "0.1.13" +version = "0.1.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c904b33cc60130e1aeea4956ab803d08a3f4a0ca82d64ed757afac3891f2bb99" +checksum = "47ce6c96ea0102f01122a185683611bd5ac8d99e62bc59dd12e6bda344ee673d" dependencies = [ "data-encoding", "data-encoding-macro-internal", @@ -5287,12 +5460,12 @@ dependencies = [ [[package]] name = "data-encoding-macro-internal" -version = "0.1.11" +version = "0.1.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8fdf3fce3ce863539ec1d7fd1b6dcc3c645663376b43ed376bbf887733e4f772" +checksum = "8d162beedaa69905488a8da94f5ac3edb4dd4788b732fadb7bd120b2625c1976" dependencies = [ "data-encoding", - "syn 1.0.109", + "syn 2.0.106", ] [[package]] @@ -5306,9 +5479,9 @@ dependencies = [ [[package]] name = "der" -version = "0.7.8" +version = "0.7.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fffa369a668c8af7dbf8b5e56c9f744fbd399949ed171606040001947de40b1c" +checksum = "e7c1832837b905bbfb5101e07cc24c8deddf52f93225eee6ead5f4d63d53ddcb" dependencies = [ "const-oid", "pem-rfc7468", @@ -5321,9 +5494,9 @@ version = "9.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5cd0a5c643689626bec213c4d8bd4d96acc8ffdb4ad4bb6bc16abf27d5f4b553" dependencies = [ - "asn1-rs 0.6.1", + "asn1-rs 0.6.2", "displaydoc", - "nom", + "nom 7.1.3", "num-bigint", "num-traits", "rusticata-macros", @@ -5335,9 +5508,9 @@ version = "10.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "07da5016415d5a3c4dd39b11ed26f915f52fc4e0dc197d87908bc916e51bc1a6" dependencies = [ - "asn1-rs 0.7.0", + "asn1-rs 0.7.1", "displaydoc", - "nom", + "nom 7.1.3", "num-bigint", "num-traits", "rusticata-macros", @@ -5345,9 +5518,9 @@ dependencies = [ [[package]] name = "deranged" -version = "0.3.11" +version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b42b6fa04a440b495c8b04d0e71b707c585f83cb9cb28cf8cd0d976c315e31b4" +checksum = "9c9e6a11ca8224451684bc0d7d5a7adbf8f2fd6887261a1cfc3c0432f9d4068e" dependencies = [ "powerfmt", ] @@ -5358,7 +5531,7 @@ version = "2.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fcc3dd5e9e9c0b295d6e1e4d811fb6f157d5ffd784b8d202fc62eac8035a770b" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "syn 1.0.109", ] @@ -5369,44 +5542,44 @@ version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d65d7ce8132b7c0e54497a4d9a55a1c2a0912a0d786cf894472ba818fba45762" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "derive-where" -version = "1.2.7" +version = "1.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "62d671cc41a825ebabc75757b62d3d168c577f9149b2d49ece1dad1f72119d25" +checksum = "ef941ded77d15ca19b40374869ac6000af1c9f2a4c0f3d4c70926287e6364a8f" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "derive_arbitrary" -version = "1.4.1" +version = "1.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "30542c1ad912e0e3d22a1935c290e12e8a29d704a420177a31faad4a601a0800" +checksum = "1e567bd82dcff979e4b03460c307b3cdc9e96fde3d73bed1496d2bc75d9dd62a" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "derive_more" -version = "0.99.17" +version = "0.99.20" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4fb810d30a7c1953f91334de7244731fc3f3c10d7fe163338a35b9f640960321" +checksum = "6edb4b64a43d977b8e99788fe3a04d483834fba1215a7e02caa415b626497f7f" dependencies = [ - "convert_case", - "proc-macro2 1.0.95", + "convert_case 0.4.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "rustc_version 0.4.0", - "syn 1.0.109", + "rustc_version 0.4.1", + "syn 2.0.106", ] [[package]] @@ -5433,10 +5606,10 @@ version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "cb7330aeadfbe296029522e6c40f315320aba36fc43a5b3632f3795348f3bd22" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", - "unicode-xid 0.2.4", + "syn 2.0.106", + "unicode-xid 0.2.6", ] [[package]] @@ -5445,10 +5618,11 @@ version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bda628edc44c4bb645fbe0f758797143e4e07926f7ebf4e9bdfbd3d2ce621df3" dependencies = [ - "proc-macro2 1.0.95", + "convert_case 0.7.1", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", - "unicode-xid 0.2.4", + "syn 2.0.106", + "unicode-xid 0.2.6", ] [[package]] @@ -5490,7 +5664,7 @@ dependencies = [ "block-buffer 0.10.4", "const-oid", "crypto-common", - "subtle 2.5.0", + "subtle 2.6.1", ] [[package]] @@ -5546,28 +5720,30 @@ dependencies = [ [[package]] name = "displaydoc" -version = "0.2.4" +version = "0.2.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "487585f4d0c6655fe74905e2504d8ad6908e4db67f744eb140876906c2f3175d" +checksum = "97369cbbc041bc366949bc74d34658d6cda5621039731c6310521892a3a20ae0" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "dissimilar" -version = "1.0.7" +version = "1.0.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "86e3bdc80eee6e16b2b6b0f87fbc98c04bee3455e35174c0de1a125d0688c632" +checksum = "8975ffdaa0ef3661bfe02dbdcc06c9f829dfafe6a3c474de366a8d5e44276921" [[package]] name = "dlmalloc" -version = "0.2.4" +version = "0.2.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "203540e710bfadb90e5e29930baf5d10270cec1f43ab34f46f78b147b2de715a" +checksum = "06cdfe340b16dd990c54cce79743613fa09fbb16774f33a77c9fd196f8f3fa30" dependencies = [ + "cfg-if", "libc", + "windows-sys 0.60.2", ] [[package]] @@ -5594,12 +5770,12 @@ dependencies = [ "common-path", "derive-syn-parse", "once_cell", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "regex", - "syn 2.0.98", + "syn 2.0.106", "termcolor", - "toml", + "toml 0.8.23", "walkdir", ] @@ -5617,9 +5793,9 @@ checksum = "1435fa1053d8b2fbbe9be7e97eca7f33d37b28409959813daefc1446a14247f1" [[package]] name = "downcast-rs" -version = "1.2.0" +version = "1.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9ea835d29036a4087793836fa931b08837ad5e957da9e23886b29586fb9b6650" +checksum = "75b325c5dbd37f80359721ad39aca5a29fb04c89279657cffdda8736d0c0b9d2" [[package]] name = "drawille" @@ -5633,21 +5809,21 @@ dependencies = [ [[package]] name = "dtoa" -version = "1.0.9" +version = "1.0.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dcbb2bf8e87535c23f7a8a321e364ce21462d0ff10cb6407820e8e96dfff6653" +checksum = "d6add3b8cff394282be81f3fc1a0605db594ed69890078ca6e2cab1c408bcf04" [[package]] name = "dunce" -version = "1.0.4" +version = "1.0.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "56ce8c6da7551ec6c462cbaf3bfbc75131ebbfa1c944aeaa9dab51ca1c5f0c3b" +checksum = "92773504d58c093f6de2459af4af33faa518c13451eb8f2b5698ed3d36e7c813" [[package]] name = "dyn-clonable" -version = "0.9.0" +version = "0.9.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4e9232f0e607a262ceb9bd5141a3dfb3e4db6994b31989bbfd845878cba59fd4" +checksum = "a36efbb9bfd58e1723780aa04b61aba95ace6a05d9ffabfdb0b43672552f0805" dependencies = [ "dyn-clonable-impl", "dyn-clone", @@ -5655,20 +5831,20 @@ dependencies = [ [[package]] name = "dyn-clonable-impl" -version = "0.9.0" +version = "0.9.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "558e40ea573c374cf53507fd240b7ee2f5477df7cfebdb97323ec61c719399c5" +checksum = "7e8671d54058979a37a26f3511fbf8d198ba1aa35ffb202c42587d918d77213a" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 1.0.109", + "syn 2.0.106", ] [[package]] name = "dyn-clone" -version = "1.0.17" +version = "1.0.20" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d6ef0072f8a535281e4876be788938b528e9a1d43900b82c2569af7da799125" +checksum = "d0881ea181b1df73ff77ffaaf9c7544ecc11e82fba9b5f27b262a3c73a332555" [[package]] name = "easy-cast" @@ -5681,9 +5857,9 @@ dependencies = [ [[package]] name = "ecdsa" -version = "0.16.8" +version = "0.16.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a4b1e0c257a9e9f25f90ff76d7a68360ed497ee519c8e428d1825ef0000799d4" +checksum = "ee27f32b5c5292967d2d4a9d7f1e0b0aed2c15daded5a60300e4abb9d8020bca" dependencies = [ "der", "digest 0.10.7", @@ -5696,9 +5872,9 @@ dependencies = [ [[package]] name = "ed25519" -version = "2.2.2" +version = "2.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "60f6d271ca33075c88028be6f04d502853d63a5ece419d269c15315d4fc1cf1d" +checksum = "115531babc129696a58c64a4fef0a8bf9e9698629fb97e9e40767d235cfbcd53" dependencies = [ "pkcs8", "signature", @@ -5706,31 +5882,32 @@ dependencies = [ [[package]] name = "ed25519-dalek" -version = "2.1.1" +version = "2.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4a3daa8e81a3963a60642bcc1f90a670680bd4a77535faa384e9d1c79d620871" +checksum = "70e796c081cee67dc755e1a36a0a172b897fab85fc3f6bc48307991f64e4eca9" dependencies = [ "curve25519-dalek", "ed25519", "rand_core 0.6.4", "serde", - "sha2 0.10.8", - "subtle 2.5.0", + "sha2 0.10.9", + "subtle 2.6.1", "zeroize", ] [[package]] name = "ed25519-zebra" -version = "4.0.3" +version = "4.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7d9ce6874da5d4415896cd45ffbc4d1cfc0c4f9c079427bd870742c30f2f65a9" +checksum = "0017d969298eec91e3db7a2985a8cab4df6341d86e6f3a6f5878b13fb7846bc9" dependencies = [ "curve25519-dalek", "ed25519", - "hashbrown 0.14.5", - "hex", + "hashbrown 0.15.5", + "pkcs8", "rand_core 0.6.4", - "sha2 0.10.8", + "sha2 0.10.9", + "subtle 2.6.1", "zeroize", ] @@ -5741,16 +5918,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1d7bc049e1bd8cdeb31b68bbd586a9464ecf9f3944af3958a7a9d0f8b9799417" dependencies = [ "enum-ordinalize", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "either" -version = "1.13.0" +version = "1.15.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "60b1af1c220855b6ceac025d3f6ecdd2b7c4894bfe9cd9bda4fbb4bc7c0d4cf0" +checksum = "48c757948c5ede0e46177b7add2e67155f70e33c07fea8284df6576da70b3719" dependencies = [ "serde", ] @@ -5771,7 +5948,7 @@ dependencies = [ "rand_core 0.6.4", "sec1", "serdect", - "subtle 2.5.0", + "subtle 2.6.1", "zeroize", ] @@ -5831,29 +6008,29 @@ dependencies = [ [[package]] name = "encode_unicode" -version = "0.3.6" +version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a357d28ed41a50f9c765dbfe56cbc04a64e53e5fc58ba79fbc34c10ef3df831f" +checksum = "34aa73646ffb006b8f5147f3dc182bd4bcb190227ce861fc4a4844bf8e3cb2c0" [[package]] name = "encoding_rs" -version = "0.8.33" +version = "0.8.35" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7268b386296a025e474d5140678f75d6de9493ae55a5d709eeb9dd08149945e1" +checksum = "75030f3c4f45dafd7586dd6780965a8c7e8e285a5ecb86713e63a79c5b2766f3" dependencies = [ "cfg-if", ] [[package]] name = "enum-as-inner" -version = "0.6.0" +version = "0.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5ffccbb6966c05b32ef8fbac435df276c4ae4d3dc55a8cd0eb9745e6c12f546a" +checksum = "a1e6a265c649f3f5979b601d26f1d05ada116434c87741c9493cb56218f76cbc" dependencies = [ - "heck 0.4.1", - "proc-macro2 1.0.95", + "heck 0.5.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -5871,40 +6048,40 @@ version = "4.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0d28318a75d4aead5c4db25382e8ef717932d0346600cacae6357eb5941bc5ff" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "enumflags2" -version = "0.7.11" +version = "0.7.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ba2f4b465f5318854c6f8dd686ede6c0a9dc67d4b1ac241cf0eb51521a309147" +checksum = "1027f7680c853e056ebcec683615fb6fbbc07dbaa13b4d5d9442b146ded4ecef" dependencies = [ "enumflags2_derive", ] [[package]] name = "enumflags2_derive" -version = "0.7.11" +version = "0.7.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fc4caf64a58d7a6d65ab00639b046ff54399a39f5f2554728895ace4b297cd79" +checksum = "67c78a4d8fdf9953a5c9d458f9efe940fd97a0cab0941c075a813ac594733827" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "enumn" -version = "0.1.13" +version = "0.1.14" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6fd000fd6988e73bbe993ea3db9b1aa64906ab88766d654973924340c8cddb42" +checksum = "2f9ed6b3789237c8a0c1c505af1c7eb2c560df6186f01b098c3a1064ea532f38" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -5929,9 +6106,9 @@ dependencies = [ [[package]] name = "env_logger" -version = "0.10.1" +version = "0.10.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "95b3f3e67048839cb0d0781f445682a35113da7121f7c949db0e2be96a4fbece" +checksum = "4cd405aab171cb85d6735e5c8d9db038c17d3ca007a4d2c25f337935c3d90580" dependencies = [ "humantime", "is-terminal", @@ -5942,14 +6119,14 @@ dependencies = [ [[package]] name = "env_logger" -version = "0.11.3" +version = "0.11.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "38b35839ba51819680ba087cd351788c9a3c476841207e0b8cee0b04722343b9" +checksum = "13c863f0904021b108aa8b2f55046443e6b1ebde8fd4a15c399893aae4fa069f" dependencies = [ "anstream", "anstyle", "env_filter", - "humantime", + "jiff", "log", ] @@ -5961,9 +6138,9 @@ checksum = "e48c92028aaa870e83d51c64e5d4e0b6981b360c522198c23959f219a4e1b15b" [[package]] name = "equivalent" -version = "1.0.1" +version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5" +checksum = "877a4ace8713b0bcf2a4e7eec82529c029f1d0619886d18145fea96c3ffe5c0f" [[package]] name = "equivocation-detector" @@ -5981,11 +6158,12 @@ dependencies = [ [[package]] name = "erased-serde" -version = "0.4.4" +version = "0.4.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2b73807008a3c7f171cc40312f37d95ef0396e048b5848d775f54b1a4dd4a0d3" +checksum = "e004d887f51fcb9fef17317a2f3525c887d8aa3f4f50fed920816a688284a5b7" dependencies = [ "serde", + "typeid", ] [[package]] @@ -6000,12 +6178,12 @@ dependencies = [ [[package]] name = "errno" -version = "0.3.10" +version = "0.3.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "33d852cb9b869c2a9b3df2f71a3074817f01e1844f839a144f5fcef059a4eb5d" +checksum = "778e2ac28f6c47af28e4907f13ffd1e1ddbd400980a9abd7c8df189bf578a5ad" dependencies = [ "libc", - "windows-sys 0.59.0", + "windows-sys 0.60.2", ] [[package]] @@ -6075,9 +6253,20 @@ checksum = "0206175f82b8d6bf6652ff7d71a1e27fd2e4efde587fd368662814d6ec1d9ce0" [[package]] name = "event-listener" -version = "5.3.1" +version = "3.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d93877bcde0eb80ca09131a08d23f0a5c18a620b01db137dba666d18cd9b30c2" +dependencies = [ + "concurrent-queue", + "parking", + "pin-project-lite", +] + +[[package]] +name = "event-listener" +version = "5.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6032be9bd27023a771701cc49f9f053c751055f71efb2e0ae5c15809093675ba" +checksum = "e13b66accf52311f30a0db42147dadea9850cb48cd070028831ae5f5d4b856ab" dependencies = [ "concurrent-queue", "parking", @@ -6086,11 +6275,11 @@ dependencies = [ [[package]] name = "event-listener-strategy" -version = "0.5.2" +version = "0.5.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0f214dc438f977e6d4e3500aaa277f5ad94ca83fbbd9b1a15713ce2344ccc5a1" +checksum = "8be9f3dfaaffdae2972880079a491a1a8bb7cbed0b8dd7a347f668b4150a3b93" dependencies = [ - "event-listener 5.3.1", + "event-listener 5.4.1", "pin-project-lite", ] @@ -6113,16 +6302,16 @@ dependencies = [ "file-guard", "fs-err", "prettyplease", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "eyre" -version = "0.6.8" +version = "0.6.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4c2b6b5a29c02cdc822728b7d7b8ae1bab3e3b05d44522770ddd49722eeac7eb" +checksum = "7cd915d99f24784cdc19fd37ef22b97e3ff0ae756c7e492e9fbfe897d61e2aec" dependencies = [ "indenter", "once_cell", @@ -6152,8 +6341,8 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6e24cb5a94bcae1e5408b0effca5cd7172ea3c5755049c5f3af4cd283a165298" dependencies = [ "bit-set", - "regex-automata 0.4.8", - "regex-syntax 0.8.5", + "regex-automata 0.4.10", + "regex-syntax 0.8.6", ] [[package]] @@ -6177,7 +6366,7 @@ version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "139834ddba373bbdd213dffe02c8d110508dcf1726c2be27e8d1f7d7e1856418" dependencies = [ - "arrayvec 0.7.4", + "arrayvec 0.7.6", "auto_impl", "bytes", ] @@ -6188,7 +6377,7 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ce8dba4714ef14b8274c371879b175aa55b16b30f269663f19d576f380018dc4" dependencies = [ - "arrayvec 0.7.4", + "arrayvec 0.7.6", "auto_impl", "bytes", ] @@ -6200,7 +6389,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ec6f82451ff7f0568c6181287189126d492b5654e30a788add08027b6363d019" dependencies = [ "fatality-proc-macro", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -6211,10 +6400,10 @@ checksum = "eb42427514b063d97ce21d5199f36c0c307d981434a6be32582bc79fe5bd2303" dependencies = [ "expander", "indexmap", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -6224,7 +6413,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e182f7dbc2ef73d9ef67351c5fbbea084729c48362d3ce9dd44c28e32e277fe5" dependencies = [ "libc", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -6245,19 +6434,19 @@ dependencies = [ [[package]] name = "ff" -version = "0.13.0" +version = "0.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ded41244b729663b1e574f1b4fb731469f69f79c17667b5d776b16cda0479449" +checksum = "c0b50bfb653653f9ca9095b427bed08ab8d75a137839d9ad64eb11810d5b6393" dependencies = [ "rand_core 0.6.4", - "subtle 2.5.0", + "subtle 2.6.1", ] [[package]] name = "fiat-crypto" -version = "0.2.5" +version = "0.2.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "27573eac26f4dd11e2b1916c3fe1baa56407c83c71a773a8ba17ec0bca03b6b7" +checksum = "28dea519a9695b9977216879a3ebfddf92f1c08c05d984f8996aecd6ecdc811d" [[package]] name = "file-guard" @@ -6271,14 +6460,14 @@ dependencies = [ [[package]] name = "filetime" -version = "0.2.22" +version = "0.2.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d4029edd3e734da6fe05b6cd7bd2960760a616bd2ddd0d59a0124746d6272af0" +checksum = "bc0505cd1b6fa6580283f6bdf70a73fcf4aba1184038c90902b92b3dd0df63ed" dependencies = [ "cfg-if", "libc", - "redox_syscall 0.3.5", - "windows-sys 0.48.0", + "libredox", + "windows-sys 0.60.2", ] [[package]] @@ -6293,7 +6482,7 @@ dependencies = [ "log", "num-traits", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", "scale-info", ] @@ -6309,7 +6498,7 @@ dependencies = [ "futures", "log", "num-traits", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "relay-utils", ] @@ -6353,11 +6542,17 @@ version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0ce7134b9999ecaf8bcd65542e436736ef32ddca1b3e06094cb6ec5755203b80" +[[package]] +name = "fixedbitset" +version = "0.5.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1d674e81391d1e1ab681a28d99df07927c6d4aa5b027d7da16ba32d1d21ecd99" + [[package]] name = "flate2" -version = "1.0.27" +version = "1.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c6c98ee8095e9d1dcbf2fcc6d95acccb90d1c81db1e44725c6a984b1dbdfb010" +checksum = "4a3d7db9596fecd151c5f638c0ee5d5bd487b6e0ea232e5dc96d5250f6f94b1d" dependencies = [ "crc32fast", "miniz_oxide", @@ -6392,6 +6587,12 @@ version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d9c4f5dac5e15c24eb999c26181a6ca40b39fe946cbe4c263c7209467bc83af2" +[[package]] +name = "foldhash" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77ce24cb58228fbb8aa041425bb1050850ac19177686ea6e0f41a70416f56fdb" + [[package]] name = "foreign-types" version = "0.3.2" @@ -6416,9 +6617,9 @@ dependencies = [ [[package]] name = "form_urlencoded" -version = "1.2.1" +version = "1.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e13624c2627564efccf4934284bdd98cbaa14e79b0b5a141218e507b3a823456" +checksum = "cb4cb245038516f5f85277875cdaa4f7d2c9a0fa0468de06ed190163b1581fcf" dependencies = [ "percent-encoding", ] @@ -6430,7 +6631,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8835f84f38484cc86f110a805655697908257fb9a7af005234060891557198e9" dependencies = [ "nonempty", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -6445,15 +6646,15 @@ dependencies = [ [[package]] name = "fragile" -version = "2.0.0" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6c2141d6d6c8512188a7891b4b01590a45f6dac67afb4f255c4124dbb86d4eaa" +checksum = "28dd6caf6059519a65843af8fe2a3ae298b14b80179855aeb4adc2c1934ee619" [[package]] name = "frame-benchmarking" version = "28.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "frame-support", "frame-support-procedural", "frame-system", @@ -6483,7 +6684,7 @@ name = "frame-benchmarking-cli" version = "32.0.0" dependencies = [ "Inflector", - "array-bytes 6.2.2", + "array-bytes 6.2.3", "chrono", "clap", "comfy-table", @@ -6538,9 +6739,9 @@ dependencies = [ "sp-version", "sp-wasm-interface 20.0.0", "substrate-test-runtime", - "subxt 0.41.0", - "subxt-signer 0.41.0", - "thiserror 1.0.65", + "subxt 0.43.0", + "subxt-signer 0.43.0", + "thiserror 1.0.69", "thousands", "westend-runtime", ] @@ -6578,7 +6779,21 @@ version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a7cb8796f93fa038f979a014234d632e9688a120e745f936e2635123c77537f7" dependencies = [ - "frame-metadata 20.0.0", + "frame-metadata 21.0.0", + "parity-scale-codec", + "scale-decode 0.16.0", + "scale-info", + "scale-type-resolver", + "sp-crypto-hashing 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "frame-decode" +version = "0.8.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6e56c0e51972d7b26ff76966c4d0f2307030df9daa5ce0885149ece1ab7ca5ad" +dependencies = [ + "frame-metadata 23.0.0", "parity-scale-codec", "scale-decode 0.16.0", "scale-info", @@ -6593,12 +6808,12 @@ dependencies = [ "frame-election-provider-support", "frame-support", "parity-scale-codec", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", "scale-info", "sp-arithmetic", - "syn 2.0.98", + "syn 2.0.106", "trybuild", ] @@ -6638,7 +6853,7 @@ name = "frame-executive" version = "28.0.0" dependencies = [ "aquamarine", - "array-bytes 6.2.2", + "array-bytes 6.2.3", "frame-support", "frame-system", "frame-try-runtime", @@ -6680,6 +6895,17 @@ dependencies = [ "serde", ] +[[package]] +name = "frame-metadata" +version = "21.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "20dfd1d7eae1d94e32e869e2fb272d81f52dd8db57820a373adb83ea24d7d862" +dependencies = [ + "cfg-if", + "parity-scale-codec", + "scale-info", +] + [[package]] name = "frame-metadata" version = "23.0.0" @@ -6696,7 +6922,7 @@ dependencies = [ name = "frame-metadata-hash-extension" version = "0.1.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "const-hex", "docify", "frame-metadata 23.0.0", @@ -6729,7 +6955,7 @@ dependencies = [ "sp-runtime", "sp-statement-store", "tempfile", - "tracing-subscriber", + "tracing-subscriber 0.3.19", ] [[package]] @@ -6773,7 +6999,7 @@ version = "28.0.0" dependencies = [ "Inflector", "aquamarine", - "array-bytes 6.2.2", + "array-bytes 6.2.3", "binary-merkle-tree", "bitflags 1.3.2", "docify", @@ -6830,7 +7056,7 @@ dependencies = [ "parity-scale-codec", "pretty_assertions", "proc-macro-warning", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "regex", "scale-info", @@ -6838,7 +7064,7 @@ dependencies = [ "sp-io", "sp-metadata-ir", "sp-runtime", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -6846,19 +7072,19 @@ name = "frame-support-procedural-tools" version = "10.0.0" dependencies = [ "frame-support-procedural-tools-derive", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "frame-support-procedural-tools-derive" version = "11.0.0" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -6980,9 +7206,12 @@ dependencies = [ [[package]] name = "fs-err" -version = "2.9.0" +version = "2.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0845fa252299212f0389d64ba26f34fa32cfe41588355f21ed507c59a0f64541" +checksum = "88a41f105fe1d5b6b34b2055e3dc59bb79b46b48b2040b9e6c7b4b5de097aa41" +dependencies = [ + "autocfg", +] [[package]] name = "fs2" @@ -7000,7 +7229,7 @@ version = "0.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "29f9df8a11882c4e3335eb2d18a0137c505d9ca927470b0cac9c6f0ae07d28f7" dependencies = [ - "rustix 0.38.42", + "rustix 0.38.44", "windows-sys 0.48.0", ] @@ -7077,7 +7306,7 @@ checksum = "1d930c203dd0b6ff06e0201a4a2fe9149b43c684fd4420555b26d21b1a02956f" dependencies = [ "futures-core", "lock_api", - "parking_lot 0.12.3", + "parking_lot 0.12.4", ] [[package]] @@ -7103,9 +7332,9 @@ dependencies = [ [[package]] name = "futures-lite" -version = "2.3.0" +version = "2.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "52527eb5074e35e9339c6b4e8d12600c7128b68fb25dcb9fa9dec18f7c25f3a5" +checksum = "f78e10609fe0e0b3f4157ffab1876319b5b0db102a2c60dc4626306dc46b44ad" dependencies = [ "fastrand 2.3.0", "futures-core", @@ -7120,9 +7349,9 @@ version = "0.3.31" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "162ee34ebcb7c64a8abebc059ce0fee27c2262618d7b60ed8faf72fef13c3650" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -7132,7 +7361,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a8f2f12607f92c69b12ed746fabf9ca4f5c482cba46679c1a75b874ed7c26adb" dependencies = [ "futures-io", - "rustls 0.23.18", + "rustls 0.23.31", "rustls-pki-types", ] @@ -7154,7 +7383,7 @@ version = "3.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f288b0a4f20f9a56b5d1da57e2227c661b7b16168e2f72365f57b63326e29b24" dependencies = [ - "gloo-timers", + "gloo-timers 0.2.6", "send_wrapper", ] @@ -7191,15 +7420,16 @@ dependencies = [ [[package]] name = "generator" -version = "0.8.4" +version = "0.8.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cc6bd114ceda131d3b1d665eba35788690ad37f5916457286b32ab6fd3c438dd" +checksum = "605183a538e3e2a9c1038635cc5c2d194e2ee8fd0d1b66b8349fad7dbacce5a2" dependencies = [ + "cc", "cfg-if", "libc", "log", "rustversion", - "windows 0.58.0", + "windows 0.61.3", ] [[package]] @@ -7234,25 +7464,29 @@ dependencies = [ [[package]] name = "getrandom" -version = "0.2.10" +version = "0.2.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "be4136b2a15dd319360be1c07d9933517ccf0be8f16bf62a3bee4f0d618df427" +checksum = "335ff9f135e4384c8150d6f27c6daed433577f86b4750418338c01a1a2528592" dependencies = [ "cfg-if", + "js-sys", "libc", - "wasi 0.11.0+wasi-snapshot-preview1", + "wasi 0.11.1+wasi-snapshot-preview1", + "wasm-bindgen", ] [[package]] name = "getrandom" -version = "0.3.1" +version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "43a49c392881ce6d5c3b8cb70f98717b7c07aabbdff06687b9030dbfbe2725f8" +checksum = "26145e563e54f2cadc477553f1ec5ee650b00862f0a58bcd12cbdc5f0ea2d2f4" dependencies = [ "cfg-if", + "js-sys", "libc", - "wasi 0.13.3+wasi-0.2.2", - "windows-targets 0.52.6", + "r-efi", + "wasi 0.14.2+wasi-0.2.4", + "wasm-bindgen", ] [[package]] @@ -7267,20 +7501,14 @@ dependencies = [ [[package]] name = "ghash" -version = "0.5.0" +version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d930750de5717d2dd0b8c0d42c076c0e884c81a73e6cab859bbd2339c71e3e40" +checksum = "f0d8a4362ccb29cb0b265253fb0a2728f592895ee6854fd9bc13f2ffda266ff1" dependencies = [ - "opaque-debug 0.3.0", + "opaque-debug 0.3.1", "polyval", ] -[[package]] -name = "gimli" -version = "0.28.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6fb8d784f27acf97159b40fc4db5ecd8aa23b9ad5ef69cdd136d3bc80665f0c0" - [[package]] name = "gimli" version = "0.31.1" @@ -7294,11 +7522,11 @@ dependencies = [ [[package]] name = "git2" -version = "0.20.0" +version = "0.20.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3fda788993cc341f69012feba8bf45c0ba4f3291fcc08e214b4d5a7332d88aff" +checksum = "2deb07a133b1520dc1a5690e9bd08950108873d7ed5de38dcc74d3b5ebffa110" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", "libc", "libgit2-sys", "log", @@ -7307,9 +7535,9 @@ dependencies = [ [[package]] name = "glob" -version = "0.3.1" +version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d2fabcfbdc87f4758337ca535fb41a6d701b65693ce38287d856d1674551ec9b" +checksum = "0cc23270f6e1808e30a928bdc84dea0b9b4136a8bc82338574f23baf47bbd280" [[package]] name = "glob-match" @@ -7327,12 +7555,12 @@ dependencies = [ "futures-core", "futures-sink", "gloo-utils", - "http 1.1.0", + "http 1.3.1", "js-sys", "pin-project", "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", "wasm-bindgen", "wasm-bindgen-futures", "web-sys", @@ -7350,6 +7578,18 @@ dependencies = [ "wasm-bindgen", ] +[[package]] +name = "gloo-timers" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bbb143cf96099802033e0d4f4963b19fd2e0b728bcf076cd9cf7f6634f092994" +dependencies = [ + "futures-channel", + "futures-core", + "js-sys", + "wasm-bindgen", +] + [[package]] name = "gloo-utils" version = "0.2.0" @@ -7409,6 +7649,16 @@ dependencies = [ "testnet-parachains-constants", ] +[[package]] +name = "gmp-mpfr-sys" +version = "1.6.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a636fb6a653382a379ee1e5593dacdc628667994167024c143214cafd40c1a86" +dependencies = [ + "libc", + "windows-sys 0.60.2", +] + [[package]] name = "governance-westend-integration-tests" version = "0.0.0" @@ -7431,9 +7681,9 @@ dependencies = [ [[package]] name = "governor" -version = "0.6.0" +version = "0.6.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "821239e5672ff23e2a7060901fa622950bbd80b649cdaadd78d1c1767ed14eb4" +checksum = "68a7f542ee6b35af73b06abc0dad1c1bae89964e4e253bc4b587b91c9637867b" dependencies = [ "cfg-if", "dashmap", @@ -7441,10 +7691,12 @@ dependencies = [ "futures-timer", "no-std-compat", "nonzero_ext", - "parking_lot 0.12.3", + "parking_lot 0.12.4", + "portable-atomic", "quanta", "rand 0.8.5", "smallvec", + "spinning_top", ] [[package]] @@ -7455,21 +7707,21 @@ checksum = "f0f9ef7462f7c099f518d754361858f86d8a07af53ba9af0fe635bbccb151a63" dependencies = [ "ff", "rand_core 0.6.4", - "subtle 2.5.0", + "subtle 2.6.1", ] [[package]] name = "h2" -version = "0.3.26" +version = "0.3.27" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "81fe527a889e1532da5c525686d96d4c2e74cdd345badf8dfef9f6b39dd5f5e8" +checksum = "0beca50380b1fc32983fc1cb4587bfa4bb9e78fc259aad4a0032d2080309222d" dependencies = [ "bytes", "fnv", "futures-core", "futures-sink", "futures-util", - "http 0.2.9", + "http 0.2.12", "indexmap", "slab", "tokio", @@ -7479,16 +7731,16 @@ dependencies = [ [[package]] name = "h2" -version = "0.4.5" +version = "0.4.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fa82e28a107a8cc405f0839610bdc9b15f1e25ec7d696aa5cf173edbcb1486ab" +checksum = "f3c0b69cfcb4e1b9f1bf2f53f95f766e4661169728ec61cd3fe5a0166f2d1386" dependencies = [ "atomic-waker", "bytes", "fnv", "futures-core", "futures-sink", - "http 1.1.0", + "http 1.3.1", "indexmap", "slab", "tokio", @@ -7498,22 +7750,26 @@ dependencies = [ [[package]] name = "half" -version = "1.8.2" +version = "2.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eabb4a44450da02c90444cf74558da904edde8fb4e9035a9a6a4e15445af0bd7" +checksum = "459196ed295495a68f7d7fe1d84f6c4b7ff0e21fe3017b2f283c6fac3ad803c9" +dependencies = [ + "cfg-if", + "crunchy", +] [[package]] name = "handlebars" -version = "5.1.0" +version = "5.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ab283476b99e66691dee3f1640fea91487a8d81f50fb5ecc75538f8f8879a1e4" +checksum = "d08485b96a0e6393e9e4d1b8d48cf74ad6c063cd905eb33f42c1ce3f0377539b" dependencies = [ "log", "pest", "pest_derive", "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -7553,13 +7809,13 @@ dependencies = [ [[package]] name = "hashbrown" -version = "0.15.3" +version = "0.15.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "84b26c544d002229e640969970a2e74021aadf6e2f96372b9c58eff97de08eb3" +checksum = "9229cfe53dfd69f0609a49f65461bd93001ea1ef889cd5529dd176593f5338a1" dependencies = [ "allocator-api2", "equivalent", - "foldhash", + "foldhash 0.1.5", "serde", ] @@ -7574,11 +7830,11 @@ dependencies = [ [[package]] name = "hashlink" -version = "0.9.1" +version = "0.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6ba4ff7128dee98c7dc9794b6a411377e1404dba1c97deb8d1a55297bd25d8af" +checksum = "7382cf6263419f2d8df38c55d7da83da5c18aef87fc7a7fc1fb1e344edfe14c1" dependencies = [ - "hashbrown 0.14.5", + "hashbrown 0.15.5", ] [[package]] @@ -7599,6 +7855,12 @@ version = "0.3.9" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d231dfb89cfffdbc30e7fc41579ed6066ad03abda9e567ccafae602b97ec5024" +[[package]] +name = "hermit-abi" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fc0fef456e4baa96da950455cd02c081ca953b141298e41db3fc7e36b1da849c" + [[package]] name = "hex" version = "0.4.3" @@ -7610,9 +7872,9 @@ dependencies = [ [[package]] name = "hex-conservative" -version = "0.1.1" +version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "30ed443af458ccb6d81c1e7e661545f94d3176752fb1df2f543b902a1e0f51e2" +checksum = "212ab92002354b4819390025006c897e8140934349e8635c9b077f47b4dcbd20" [[package]] name = "hex-conservative" @@ -7620,7 +7882,7 @@ version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5313b072ce3c597065a808dbf612c4c8e8590bdbf8b579508bf7a762c5eae6cd" dependencies = [ - "arrayvec 0.7.4", + "arrayvec 0.7.6", ] [[package]] @@ -7631,9 +7893,9 @@ checksum = "6fe2267d4ed49bc07b63801559be28c718ea06c4738b7a03c94df7386d2cde46" [[package]] name = "hickory-proto" -version = "0.24.1" +version = "0.24.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "07698b8420e2f0d6447a436ba999ec85d8fbf2a398bbd737b82cac4a2e96e512" +checksum = "92652067c9ce6f66ce53cc38d1169daa36e6e7eb7dd3b63b5103bd9d97117248" dependencies = [ "async-trait", "cfg-if", @@ -7642,12 +7904,12 @@ dependencies = [ "futures-channel", "futures-io", "futures-util", - "idna 0.4.0", + "idna", "ipnet", "once_cell", "rand 0.8.5", - "socket2 0.5.9", - "thiserror 1.0.65", + "socket2 0.5.10", + "thiserror 1.0.69", "tinyvec", "tokio", "tracing", @@ -7667,12 +7929,12 @@ dependencies = [ "futures-channel", "futures-io", "futures-util", - "idna 1.0.3", + "idna", "ipnet", "once_cell", - "rand 0.9.0", - "ring 0.17.8", - "thiserror 2.0.12", + "rand 0.9.2", + "ring 0.17.14", + "thiserror 2.0.16", "tinyvec", "tokio", "tracing", @@ -7681,21 +7943,21 @@ dependencies = [ [[package]] name = "hickory-resolver" -version = "0.24.2" +version = "0.24.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0a2e2aba9c389ce5267d31cf1e4dace82390ae276b0b364ea55630b1fa1b44b4" +checksum = "cbb117a1ca520e111743ab2f6688eddee69db4e0ea242545a604dce8a66fd22e" dependencies = [ "cfg-if", "futures-util", - "hickory-proto 0.24.1", + "hickory-proto 0.24.4", "ipconfig", "lru-cache", "once_cell", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", "resolv-conf", "smallvec", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tracing", ] @@ -7712,11 +7974,11 @@ dependencies = [ "ipconfig", "moka", "once_cell", - "parking_lot 0.12.3", - "rand 0.9.0", + "parking_lot 0.12.4", + "rand 0.9.2", "resolv-conf", "smallvec", - "thiserror 2.0.12", + "thiserror 2.0.16", "tokio", "tracing", ] @@ -7762,41 +8024,31 @@ dependencies = [ [[package]] name = "home" -version = "0.5.9" +version = "0.5.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e3d1354bf6b7235cb4a0576c2619fd4ed18183f689b12b006a0ee7329eeff9a5" +checksum = "589533453244b0995c858700322199b2becb13b627df2851f64a2775d024abcf" dependencies = [ - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] name = "honggfuzz" -version = "0.5.55" +version = "0.5.57" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "848e9c511092e0daa0a35a63e8e6e475a3e8f870741448b9f6028d69b142f18e" +checksum = "fc563d4f41b17364d5c48ded509f2bcf1c3f6ae9c7f203055b4a5c325072d57e" dependencies = [ "arbitrary", "lazy_static", - "memmap2 0.5.10", - "rustc_version 0.4.0", -] - -[[package]] -name = "hostname" -version = "0.3.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3c731c3e10504cc8ed35cfe2f1db4c9274c3d35fa486e3b31df46f068ef3e867" -dependencies = [ - "libc", - "match_cfg", - "winapi", + "memmap2 0.9.8", + "rustc_version 0.4.1", + "semver 1.0.26", ] [[package]] name = "http" -version = "0.2.9" +version = "0.2.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bd6effc99afb63425aff9b05836f029929e345a6148a14b7ecd5ab67af944482" +checksum = "601cbb57e577e2f5ef5be8e7b83f0f63994f25aa94d673e54a92d5c516d101f1" dependencies = [ "bytes", "fnv", @@ -7805,9 +8057,9 @@ dependencies = [ [[package]] name = "http" -version = "1.1.0" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "21b9ddb458710bc376481b842f5da65cdf31522de232c1ca8146abce2a358258" +checksum = "f4a85d31aea989eead29a3aaf9e1115a180df8282431156e533de47660892565" dependencies = [ "bytes", "fnv", @@ -7816,35 +8068,35 @@ dependencies = [ [[package]] name = "http-body" -version = "0.4.5" +version = "0.4.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d5f38f16d184e36f2408a55281cd658ecbd3ca05cce6d6510a176eca393e26d1" +checksum = "7ceab25649e9960c0311ea418d17bee82c0dcec1bd053b5f9a66e265a693bed2" dependencies = [ "bytes", - "http 0.2.9", + "http 0.2.12", "pin-project-lite", ] [[package]] name = "http-body" -version = "1.0.0" +version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1cac85db508abc24a2e48553ba12a996e87244a0395ce011e62b37158745d643" +checksum = "1efedce1fb8e6913f23e0c92de8e62cd5b772a67e7b3946df930a62566c93184" dependencies = [ "bytes", - "http 1.1.0", + "http 1.3.1", ] [[package]] name = "http-body-util" -version = "0.1.2" +version = "0.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "793429d76616a256bcb62c2a2ec2bed781c8307e797e2598c50010f2bee2544f" +checksum = "b021d93e26becf5dc7e1b75b1bed1fd93124b374ceb73f43d4d4eafec896a64a" dependencies = [ "bytes", - "futures-util", - "http 1.1.0", - "http-body 1.0.0", + "futures-core", + "http 1.3.1", + "http-body 1.0.1", "pin-project-lite", ] @@ -7856,9 +8108,9 @@ checksum = "add0ab9360ddbd88cfeb3bd9574a1d85cfdfa14db10b3e21d3700dbc4328758f" [[package]] name = "httparse" -version = "1.10.0" +version = "1.10.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f2d708df4e7140240a16cd6ab0ab65c972d7433ab77819ea693fde9c43811e2a" +checksum = "6dbf3de79e51f3d586ab4cb9d5c3e2c14aa28ed23d180cf89b4df0454a69cc87" [[package]] name = "httpdate" @@ -7868,9 +8120,9 @@ checksum = "df3b46402a9d5adb4c86a0cf463f42e19994e3ee891101b1841f30a545cb49a9" [[package]] name = "humantime" -version = "2.1.0" +version = "2.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4" +checksum = "9b112acc8b3adf4b107a8ec20977da0273a8c386765a3ec0229bd500a1443f9f" [[package]] name = "humantime-serde" @@ -7884,22 +8136,22 @@ dependencies = [ [[package]] name = "hyper" -version = "0.14.29" +version = "0.14.32" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f361cde2f109281a220d4307746cdfd5ee3f410da58a70377762396775634b33" +checksum = "41dfc780fdec9373c01bae43289ea34c972e40ee3c9f6b3c8801a35f35586ce7" dependencies = [ "bytes", "futures-channel", "futures-core", "futures-util", - "h2 0.3.26", - "http 0.2.9", - "http-body 0.4.5", + "h2 0.3.27", + "http 0.2.12", + "http-body 0.4.6", "httparse", "httpdate", "itoa", "pin-project-lite", - "socket2 0.5.9", + "socket2 0.5.10", "tokio", "tower-service", "tracing", @@ -7908,20 +8160,22 @@ dependencies = [ [[package]] name = "hyper" -version = "1.6.0" +version = "1.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cc2b571658e38e0c01b1fdca3bbbe93c00d3d71693ff2770043f8c29bc7d6f80" +checksum = "eb3aa54a13a0dfe7fbe3a59e0c76093041720fdc77b110cc0fc260fafb4dc51e" dependencies = [ + "atomic-waker", "bytes", "futures-channel", - "futures-util", - "h2 0.4.5", - "http 1.1.0", - "http-body 1.0.0", + "futures-core", + "h2 0.4.12", + "http 1.3.1", + "http-body 1.0.1", "httparse", "httpdate", "itoa", "pin-project-lite", + "pin-utils", "smallvec", "tokio", "want", @@ -7934,10 +8188,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ec3efd23720e2049821a693cbc7e65ea87c72f1c58ff2f9522ff332b1491e590" dependencies = [ "futures-util", - "http 0.2.9", - "hyper 0.14.29", + "http 0.2.12", + "hyper 0.14.32", "log", - "rustls 0.21.7", + "rustls 0.21.12", "rustls-native-certs 0.6.3", "tokio", "tokio-rustls 0.24.1", @@ -7945,22 +8199,21 @@ dependencies = [ [[package]] name = "hyper-rustls" -version = "0.27.3" +version = "0.27.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "08afdbb5c31130e3034af566421053ab03787c640246a446327f550d11bcb333" +checksum = "e3c93eb611681b207e1fe55d5a71ecf91572ec8a6705cdb6857f7d8d5242cf58" dependencies = [ - "futures-util", - "http 1.1.0", - "hyper 1.6.0", + "http 1.3.1", + "hyper 1.7.0", "hyper-util", "log", - "rustls 0.23.18", - "rustls-native-certs 0.8.0", + "rustls 0.23.31", + "rustls-native-certs 0.8.1", "rustls-pki-types", "tokio", - "tokio-rustls 0.26.0", + "tokio-rustls 0.26.2", "tower-service", - "webpki-roots 0.26.3", + "webpki-roots 1.0.2", ] [[package]] @@ -7969,7 +8222,7 @@ version = "0.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bbb958482e8c7be4bc3cf272a766a2b0bf1a6755e7a6ae777f017a31d11b13b1" dependencies = [ - "hyper 0.14.29", + "hyper 0.14.32", "pin-project-lite", "tokio", "tokio-io-timeout", @@ -7983,7 +8236,7 @@ checksum = "70206fc6890eaca9fde8a0bf71caa2ddfc9fe045ac9e5c70df101a7dbde866e0" dependencies = [ "bytes", "http-body-util", - "hyper 1.6.0", + "hyper 1.7.0", "hyper-util", "native-tls", "tokio", @@ -7993,35 +8246,43 @@ dependencies = [ [[package]] name = "hyper-util" -version = "0.1.10" +version = "0.1.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "df2dcfbe0677734ab2f3ffa7fa7bfd4706bfdc1ef393f2ee30184aed67e631b4" +checksum = "8d9b05277c7e8da2c93a568989bb6207bef0112e8d17df7a6eda4a3cf143bc5e" dependencies = [ + "base64 0.22.1", "bytes", "futures-channel", + "futures-core", "futures-util", - "http 1.1.0", - "http-body 1.0.0", - "hyper 1.6.0", + "http 1.3.1", + "http-body 1.0.1", + "hyper 1.7.0", + "ipnet", + "libc", + "percent-encoding", "pin-project-lite", - "socket2 0.5.9", + "socket2 0.6.0", + "system-configuration", "tokio", "tower-service", "tracing", + "windows-registry", ] [[package]] name = "iana-time-zone" -version = "0.1.57" +version = "0.1.63" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2fad5b825842d2b38bd206f3e81d6957625fd7f0a361e345c30e01a0ae2dd613" +checksum = "b0c919e5debc312ad217002b8048a17b7d83f80703865bbfcfebb0458b0b27d8" dependencies = [ "android_system_properties", "core-foundation-sys", "iana-time-zone-haiku", "js-sys", + "log", "wasm-bindgen", - "windows 0.48.0", + "windows-core 0.61.2", ] [[package]] @@ -8035,21 +8296,22 @@ dependencies = [ [[package]] name = "icu_collections" -version = "1.5.0" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "db2fa452206ebee18c4b5c2274dbf1de17008e874b4dc4f0aea9d01ca79e4526" +checksum = "200072f5d0e3614556f94a9930d5dc3e0662a652823904c3a75dc3b0af7fee47" dependencies = [ "displaydoc", + "potential_utf", "yoke", "zerofrom", "zerovec", ] [[package]] -name = "icu_locid" -version = "1.5.0" +name = "icu_locale_core" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "13acbb8371917fc971be86fc8057c41a64b521c184808a698c02acc242dbf637" +checksum = "0cde2700ccaed3872079a65fb1a78f6c0a36c91570f28755dda67bc8f7d9f00a" dependencies = [ "displaydoc", "litemap", @@ -8058,31 +8320,11 @@ dependencies = [ "zerovec", ] -[[package]] -name = "icu_locid_transform" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "01d11ac35de8e40fdeda00d9e1e9d92525f3f9d887cdd7aa81d727596788b54e" -dependencies = [ - "displaydoc", - "icu_locid", - "icu_locid_transform_data", - "icu_provider", - "tinystr", - "zerovec", -] - -[[package]] -name = "icu_locid_transform_data" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fdc8ff3388f852bede6b579ad4e978ab004f139284d7b28715f773507b946f6e" - [[package]] name = "icu_normalizer" -version = "1.5.0" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "19ce3e0da2ec68599d193c93d088142efd7f9c5d6fc9b803774855747dc6a84f" +checksum = "436880e8e18df4d7bbc06d58432329d6458cc84531f7ac5f024e93deadb37979" dependencies = [ "displaydoc", "icu_collections", @@ -8090,67 +8332,54 @@ dependencies = [ "icu_properties", "icu_provider", "smallvec", - "utf16_iter", - "utf8_iter", - "write16", "zerovec", ] [[package]] name = "icu_normalizer_data" -version = "1.5.0" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f8cafbf7aa791e9b22bec55a167906f9e1215fd475cd22adfcf660e03e989516" +checksum = "00210d6893afc98edb752b664b8890f0ef174c8adbb8d0be9710fa66fbbf72d3" [[package]] name = "icu_properties" -version = "1.5.1" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "93d6020766cfc6302c15dbbc9c8778c37e62c14427cb7f6e601d849e092aeef5" +checksum = "016c619c1eeb94efb86809b015c58f479963de65bdb6253345c1a1276f22e32b" dependencies = [ "displaydoc", "icu_collections", - "icu_locid_transform", + "icu_locale_core", "icu_properties_data", "icu_provider", - "tinystr", + "potential_utf", + "zerotrie", "zerovec", ] [[package]] name = "icu_properties_data" -version = "1.5.0" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "67a8effbc3dd3e4ba1afa8ad918d5684b8868b3b26500753effea8d2eed19569" +checksum = "298459143998310acd25ffe6810ed544932242d3f07083eee1084d83a71bd632" [[package]] name = "icu_provider" -version = "1.5.0" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6ed421c8a8ef78d3e2dbc98a973be2f3770cb42b606e3ab18d6237c4dfde68d9" +checksum = "03c80da27b5f4187909049ee2d72f276f0d9f99a42c306bd0131ecfe04d8e5af" dependencies = [ "displaydoc", - "icu_locid", - "icu_provider_macros", + "icu_locale_core", "stable_deref_trait", "tinystr", "writeable", "yoke", "zerofrom", + "zerotrie", "zerovec", ] -[[package]] -name = "icu_provider_macros" -version = "1.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1ec89e9337638ecdc08744df490b221a7399bf8d164eb52a665454e60e075ad6" -dependencies = [ - "proc-macro2 1.0.95", - "quote 1.0.40", - "syn 2.0.98", -] - [[package]] name = "ident_case" version = "1.0.1" @@ -8159,19 +8388,9 @@ checksum = "b9e0384b61958566e926dc50660321d12159025e767c18e043daf26b70104c39" [[package]] name = "idna" -version = "0.4.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7d20d6b07bfbc108882d88ed8e37d39636dcc260e15e30c45e6ba089610b917c" -dependencies = [ - "unicode-bidi", - "unicode-normalization", -] - -[[package]] -name = "idna" -version = "1.0.3" +version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "686f825264d630750a544639377bae737628043f20d38bbc029e8f29ea968a7e" +checksum = "3b0875f23caa03898994f6ddc501886a45c7d3d62d04d2d90788d47be1b1e4de" dependencies = [ "idna_adapter", "smallvec", @@ -8180,9 +8399,9 @@ dependencies = [ [[package]] name = "idna_adapter" -version = "1.2.0" +version = "1.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "daca1df1c957320b2cf139ac61e7bd64fed304c5040df000a745aa1de3b4ef71" +checksum = "3acae9609540aa318d1bc588455225fb2085b9ed0c4f6bd0d9d5bcd86f1a0344" dependencies = [ "icu_normalizer", "icu_properties", @@ -8200,21 +8419,25 @@ dependencies = [ [[package]] name = "if-watch" -version = "3.2.0" +version = "3.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d6b0422c86d7ce0e97169cc42e04ae643caf278874a7a3c87b8150a220dc7e1e" +checksum = "cdf9d64cfcf380606e64f9a0bcf493616b65331199f984151a6fa11a7b3cde38" dependencies = [ - "async-io 2.3.3", - "core-foundation", + "async-io 2.5.0", + "core-foundation 0.9.4", "fnv", "futures", "if-addrs", "ipnet", "log", + "netlink-packet-core", + "netlink-packet-route", + "netlink-proto", + "netlink-sys", "rtnetlink", - "system-configuration 0.5.1", + "system-configuration", "tokio", - "windows 0.51.1", + "windows 0.53.0", ] [[package]] @@ -8227,8 +8450,8 @@ dependencies = [ "attohttpc", "bytes", "futures", - "http 0.2.9", - "hyper 0.14.29", + "http 0.2.12", + "hyper 0.14.32", "log", "rand 0.8.5", "tokio", @@ -8289,44 +8512,44 @@ version = "0.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a0eb5a3343abf848c0984fe4604b2b105da9539376e24fc0a3b0007411ae4fd9" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "include_dir" -version = "0.7.3" +version = "0.7.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "18762faeff7122e89e0857b02f7ce6fcc0d101d5e9ad2ad7846cc01d61b7f19e" +checksum = "923d117408f1e49d914f1a379a309cffe4f18c05cf4e3d12e613a15fc81bd0dd" dependencies = [ "include_dir_macros", ] [[package]] name = "include_dir_macros" -version = "0.7.3" +version = "0.7.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b139284b5cf57ecfa712bcc66950bb635b31aff41c188e8a4cfc758eca374a3f" +checksum = "7cab85a7ed0bd5f0e76d93846e0147172bed2e2d3f859bcc33a8d9699cad1a75" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", ] [[package]] name = "indenter" -version = "0.3.3" +version = "0.3.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ce23b50ad8242c51a442f3ff322d56b02f08852c77e4c0b4d3fd684abc89c683" +checksum = "964de6e86d545b246d84badc0fef527924ace5134f30641c203ef52ba83f58d5" [[package]] name = "indexmap" -version = "2.9.0" +version = "2.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cea70ddb795996207ad57735b50c5982d8844f38ba9ee5f1aedcfb708a2aa11e" +checksum = "f2481980430f9f78649238835720ddccc57e52df14ffce1c6f37391d61b563e9" dependencies = [ "equivalent", - "hashbrown 0.15.3", + "hashbrown 0.15.5", "serde", ] @@ -8338,22 +8561,22 @@ checksum = "8e04e2fd2b8188ea827b32ef11de88377086d690286ab35747ef7f9bf3ccb590" [[package]] name = "indicatif" -version = "0.17.7" +version = "0.17.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fb28741c9db9a713d93deb3bb9515c20788cef5815265bee4980e87bde7e0f25" +checksum = "183b3088984b400f4cfac3620d5e076c84da5364016b4f49473de574b2586235" dependencies = [ "console", - "instant", "number_prefix", "portable-atomic", - "unicode-width 0.1.10", + "unicode-width", + "web-time", ] [[package]] name = "inout" -version = "0.1.3" +version = "0.1.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a0c10553d664a4d0bcff9f4215d0aac67a639cc68ef660840afe309b807bc9f5" +checksum = "879f10e63c20629ecabbb64a8010319738c66a5cd0c29b02d63d272b03751d01" dependencies = [ "generic-array 0.14.7", ] @@ -8382,11 +8605,22 @@ version = "1.0.11" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "eae7b9aee968036d54dce06cebaefd919e4472e753296daccd6d344e3e2df0c2" dependencies = [ - "hermit-abi", + "hermit-abi 0.3.9", "libc", "windows-sys 0.48.0", ] +[[package]] +name = "io-uring" +version = "0.7.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "046fa2d4d00aea763528b4950358d0ead425372445dc8ff86312b3c69ff7727b" +dependencies = [ + "bitflags 2.9.3", + "cfg-if", + "libc", +] + [[package]] name = "ip_network" version = "0.4.1" @@ -8399,7 +8633,7 @@ version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b58db92f96b720de98181bbbe63c831e87005ab460c1bf306eb2622b4707997f" dependencies = [ - "socket2 0.5.9", + "socket2 0.5.10", "widestring", "windows-sys 0.48.0", "winreg", @@ -8407,30 +8641,46 @@ dependencies = [ [[package]] name = "ipnet" -version = "2.8.0" +version = "2.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "28b29a3cd74f0f4598934efe3aeba42bae0eb4680554128851ebbecb02af14e6" +checksum = "469fb0b9cefa57e3ef31275ee7cacb78f2fdca44e4765491884a2b119d4eb130" + +[[package]] +name = "iri-string" +version = "0.7.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dbc5ebe9c3a1a7a5127f920a418f7585e9e758e911d0466ed004f393b0e380b2" +dependencies = [ + "memchr", + "serde", +] [[package]] name = "is-terminal" -version = "0.4.9" +version = "0.4.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cb0889898416213fab133e1d33a0e5858a48177452750691bde3666d0fdbaf8b" +checksum = "e04d7f318608d35d4b61ddd75cbdaee86b023ebe2bd5a66ee0915f0bf93095a9" dependencies = [ - "hermit-abi", - "rustix 0.38.42", - "windows-sys 0.48.0", + "hermit-abi 0.5.2", + "libc", + "windows-sys 0.59.0", ] [[package]] name = "is_executable" -version = "1.0.1" +version = "1.0.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fa9acdc6d67b75e626ad644734e8bc6df893d9cd2a834129065d3dd6158ea9c8" +checksum = "baabb8b4867b26294d818bf3f651a454b6901431711abb96e296245888d6e8c4" dependencies = [ - "winapi", + "windows-sys 0.60.2", ] +[[package]] +name = "is_terminal_polyfill" +version = "1.70.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7943c866cc5cd64cbc25b2e01621d07fa8eb2a1a23160ee81ce38704e97b8ecf" + [[package]] name = "isahc" version = "1.7.2" @@ -8445,7 +8695,7 @@ dependencies = [ "encoding_rs", "event-listener 2.5.3", "futures-lite 1.13.0", - "http 0.2.9", + "http 0.2.12", "log", "mime", "once_cell", @@ -8505,17 +8755,17 @@ dependencies = [ [[package]] name = "itoa" -version = "1.0.9" +version = "1.0.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "af150ab688ff2122fcef229be89cb50dd66af9e01a4ff320cc137eecc9bacc38" +checksum = "4a5f13b858c8d314ee3e8f639011f7ccefe71f97f96e50151fb991f267928e2c" [[package]] name = "jam-codec" -version = "0.1.0" +version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d72f2fb8cfd27f6c52ea7d0528df594f7f2ed006feac153e9393ec567aafea98" +checksum = "cb948eace373d99de60501a02fb17125d30ac632570de20dccc74370cdd611b9" dependencies = [ - "arrayvec 0.7.4", + "arrayvec 0.7.6", "bitvec", "byte-slice-cast", "const_format", @@ -8527,28 +8777,54 @@ dependencies = [ [[package]] name = "jam-codec-derive" -version = "0.1.0" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "319af585c4c8a6b5552a52b7787a1ab3e4d59df7614190b1f85b9b842488789d" +dependencies = [ + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", + "quote 1.0.40", + "syn 2.0.106", +] + +[[package]] +name = "jiff" +version = "0.2.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "be1f93b8b1eb69c77f24bbb0afdf66f54b632ee39af40ca21c4365a1d7347e49" +dependencies = [ + "jiff-static", + "log", + "portable-atomic", + "portable-atomic-util", + "serde", +] + +[[package]] +name = "jiff-static" +version = "0.2.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "09985146f40378e13af626964ac9c206d9d9b67c40c70805898d9954f709bcf5" +checksum = "03343451ff899767262ec32146f6d559dd759fdadf42ff0e227c7c48f72594b4" dependencies = [ - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "jni" -version = "0.19.0" +version = "0.21.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c6df18c2e3db7e453d3c6ac5b3e9d5182664d28788126d39b91f2d1e22b017ec" +checksum = "1a87aa2bb7d2af34197c04845522473242e1aa17c12f4935d5856491a7fb8c97" dependencies = [ "cesu8", + "cfg-if", "combine", "jni-sys", "log", - "thiserror 1.0.65", + "thiserror 1.0.69", "walkdir", + "windows-sys 0.45.0", ] [[package]] @@ -8559,19 +8835,21 @@ checksum = "8eaf4bc02d17cbdd7ff4c7438cafcdf7fb9a4613313ad11b4f8fefe7d3fa0130" [[package]] name = "jobserver" -version = "0.1.32" +version = "0.1.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "48d1dbcbbeb6a7fec7e059840aa538bd62aaccf972c7346c4d9d2059312853d0" +checksum = "9afb3de4395d6b3e67a780b6de64b51c978ecf11cb9a462c66be7d4ca9039d33" dependencies = [ + "getrandom 0.3.3", "libc", ] [[package]] name = "js-sys" -version = "0.3.72" +version = "0.3.77" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6a88f1bda2bd75b0452a14784937d796722fdebfe50df998aeb3f0b7603019a9" +checksum = "1cfaf33c695fc6e08064efbc1f72ec937429614f25eef83af942d0e227c3a28f" dependencies = [ + "once_cell", "wasm-bindgen", ] @@ -8583,7 +8861,7 @@ checksum = "ec9ad60d674508f3ca8f380a928cfe7b096bc729c4e2dbfe3852bc45da3ab30b" dependencies = [ "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -8596,7 +8874,7 @@ dependencies = [ "pest_derive", "regex", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -8612,9 +8890,9 @@ dependencies = [ [[package]] name = "jsonrpsee" -version = "0.24.8" +version = "0.24.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "834af00800e962dee8f7bfc0f60601de215e73e78e5497d733a2919da837d3c8" +checksum = "37b26c20e2178756451cfeb0661fb74c47dd5988cb7e3939de7e9241fd604d42" dependencies = [ "jsonrpsee-client-transport", "jsonrpsee-core", @@ -8630,24 +8908,24 @@ dependencies = [ [[package]] name = "jsonrpsee-client-transport" -version = "0.24.7" +version = "0.24.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "548125b159ba1314104f5bb5f38519e03a41862786aa3925cf349aae9cdd546e" +checksum = "bacb85abf4117092455e1573625e21b8f8ef4dec8aff13361140b2dc266cdff2" dependencies = [ "base64 0.22.1", "futures-channel", "futures-util", "gloo-net", - "http 1.1.0", + "http 1.3.1", "jsonrpsee-core", "pin-project", - "rustls 0.23.18", + "rustls 0.23.31", "rustls-pki-types", "rustls-platform-verifier", - "soketto 0.8.0", - "thiserror 1.0.65", + "soketto 0.8.1", + "thiserror 1.0.69", "tokio", - "tokio-rustls 0.26.0", + "tokio-rustls 0.26.2", "tokio-util", "tracing", "url", @@ -8655,25 +8933,25 @@ dependencies = [ [[package]] name = "jsonrpsee-core" -version = "0.24.7" +version = "0.24.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f2882f6f8acb9fdaec7cefc4fd607119a9bd709831df7d7672a1d3b644628280" +checksum = "456196007ca3a14db478346f58c7238028d55ee15c1df15115596e411ff27925" dependencies = [ "async-trait", "bytes", "futures-timer", "futures-util", - "http 1.1.0", - "http-body 1.0.0", + "http 1.3.1", + "http-body 1.0.1", "http-body-util", "jsonrpsee-types", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project", "rand 0.8.5", "rustc-hash 2.1.1", "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-stream", "tracing", @@ -8682,53 +8960,53 @@ dependencies = [ [[package]] name = "jsonrpsee-http-client" -version = "0.24.7" +version = "0.24.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b3638bc4617f96675973253b3a45006933bde93c2fd8a6170b33c777cc389e5b" +checksum = "c872b6c9961a4ccc543e321bb5b89f6b2d2c7fe8b61906918273a3333c95400c" dependencies = [ "async-trait", "base64 0.22.1", - "http-body 1.0.0", - "hyper 1.6.0", - "hyper-rustls 0.27.3", + "http-body 1.0.1", + "hyper 1.7.0", + "hyper-rustls 0.27.7", "hyper-util", "jsonrpsee-core", "jsonrpsee-types", - "rustls 0.23.18", + "rustls 0.23.31", "rustls-platform-verifier", "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", - "tower", + "tower 0.4.13", "tracing", "url", ] [[package]] name = "jsonrpsee-proc-macros" -version = "0.24.7" +version = "0.24.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c06c01ae0007548e73412c08e2285ffe5d723195bf268bce67b1b77c3bb2a14d" +checksum = "5e65763c942dfc9358146571911b0cd1c361c2d63e2d2305622d40d36376ca80" dependencies = [ "heck 0.5.0", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "jsonrpsee-server" -version = "0.24.7" +version = "0.24.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "82ad8ddc14be1d4290cd68046e7d1d37acd408efed6d3ca08aefcc3ad6da069c" +checksum = "55e363146da18e50ad2b51a0a7925fc423137a0b1371af8235b1c231a0647328" dependencies = [ "futures-util", - "http 1.1.0", - "http-body 1.0.0", + "http 1.3.1", + "http-body 1.0.1", "http-body-util", - "hyper 1.6.0", + "hyper 1.7.0", "hyper-util", "jsonrpsee-core", "jsonrpsee-types", @@ -8736,32 +9014,32 @@ dependencies = [ "route-recognizer", "serde", "serde_json", - "soketto 0.8.0", - "thiserror 1.0.65", + "soketto 0.8.1", + "thiserror 1.0.69", "tokio", "tokio-stream", "tokio-util", - "tower", + "tower 0.4.13", "tracing", ] [[package]] name = "jsonrpsee-types" -version = "0.24.7" +version = "0.24.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a178c60086f24cc35bb82f57c651d0d25d99c4742b4d335de04e97fa1f08a8a1" +checksum = "08a8e70baf945b6b5752fc8eb38c918a48f1234daf11355e07106d963f860089" dependencies = [ - "http 1.1.0", + "http 1.3.1", "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] name = "jsonrpsee-wasm-client" -version = "0.24.7" +version = "0.24.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1a01cd500915d24ab28ca17527e23901ef1be6d659a2322451e1045532516c25" +checksum = "e6558a9586cad43019dafd0b6311d0938f46efc116b34b28c74778bc11a2edf6" dependencies = [ "jsonrpsee-client-transport", "jsonrpsee-core", @@ -8770,11 +9048,11 @@ dependencies = [ [[package]] name = "jsonrpsee-ws-client" -version = "0.24.7" +version = "0.24.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0fe322e0896d0955a3ebdd5bf813571c53fea29edd713bc315b76620b327e86d" +checksum = "01b3323d890aa384f12148e8d2a1fd18eb66e9e7e825f9de4fa53bcc19b93eef" dependencies = [ - "http 1.1.0", + "http 1.3.1", "jsonrpsee-client-transport", "jsonrpsee-core", "jsonrpsee-types", @@ -8792,7 +9070,7 @@ dependencies = [ "elliptic-curve", "once_cell", "serdect", - "sha2 0.10.8", + "sha2 0.10.9", ] [[package]] @@ -8811,9 +9089,9 @@ dependencies = [ [[package]] name = "keccak" -version = "0.1.4" +version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8f6d5ed8676d904364de097082f4e7d240b571b67989ced0240f08b7f966f940" +checksum = "ecc2af9a1119c51f12a14607e783cb977bde58bc069ff0c3da1095e635d70654" dependencies = [ "cpufeatures", ] @@ -8859,7 +9137,7 @@ checksum = "c33070833c9ee02266356de0c43f723152bd38bd96ddf52c82b3af10c9138b28" name = "kitchensink-runtime" version = "3.0.0-dev" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "log", "node-primitives", "pallet-example-mbm", @@ -8898,9 +9176,9 @@ dependencies = [ "either", "futures", "home", - "http 0.2.9", - "http-body 0.4.5", - "hyper 0.14.29", + "http 0.2.12", + "http-body 0.4.6", + "hyper 0.14.32", "hyper-rustls 0.24.2", "hyper-timeout", "jsonpath-rust", @@ -8909,17 +9187,17 @@ dependencies = [ "pem", "pin-project", "rand 0.8.5", - "rustls 0.21.7", - "rustls-pemfile 1.0.3", + "rustls 0.21.12", + "rustls-pemfile", "secrecy 0.8.0", "serde", "serde_json", "serde_yaml", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-tungstenite 0.20.1", "tokio-util", - "tower", + "tower 0.4.13", "tower-http 0.4.4", "tracing", ] @@ -8932,13 +9210,13 @@ checksum = "b5bba93d054786eba7994d03ce522f368ef7d48c88a1826faa28478d85fb63ae" dependencies = [ "chrono", "form_urlencoded", - "http 0.2.9", + "http 0.2.12", "json-patch", "k8s-openapi", "once_cell", "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -8956,12 +9234,12 @@ dependencies = [ "json-patch", "k8s-openapi", "kube-client", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project", "serde", "serde_json", "smallvec", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-util", "tracing", @@ -8992,7 +9270,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bf7a85fe66f9ff9cd74e169fdd2c94c6e1e74c412c99a73b4df3200b5d3760b2" dependencies = [ "kvdb", - "parking_lot 0.12.3", + "parking_lot 0.12.4", ] [[package]] @@ -9003,7 +9281,7 @@ checksum = "b644c70b92285f66bfc2032922a79000ea30af7bc2ab31902992a5dcb9b434f6" dependencies = [ "kvdb", "num_cpus", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "regex", "rocksdb", "smallvec", @@ -9020,13 +9298,13 @@ dependencies = [ [[package]] name = "landlock" -version = "0.3.0" +version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1530c5b973eeed4ac216af7e24baf5737645a6272e361f1fb95710678b67d9cc" +checksum = "9baa9eeb6e315942429397e617a190f4fdc696ef1ee0342939d641029cbb4ea7" dependencies = [ "enumflags2", "libc", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -9044,12 +9322,6 @@ version = "1.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "830d08ce1d1d941e6b30645f1a0eb5643013d835ce3779a5fc208261dbe10f55" -[[package]] -name = "leb128" -version = "0.2.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "884e2677b40cc8c339eaefcb701c32ef1fd2493d71118dc0ca4b6a736c93bd67" - [[package]] name = "leb128fmt" version = "0.1.0" @@ -9058,9 +9330,9 @@ checksum = "09edd9e8b54e49e587e4f6295a7d29c3ea94d469cb40ab8ca70b288248a81db2" [[package]] name = "libc" -version = "0.2.172" +version = "0.2.175" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d750af042f7ef4f724306de029d18836c26c1765a54a6a3f094cbd23a7267ffa" +checksum = "6a82ae493e598baaea5209805c49bbf2ea7de956d50d7da0da1164f9c6d28543" [[package]] name = "libflate" @@ -9084,20 +9356,19 @@ dependencies = [ [[package]] name = "libfuzzer-sys" -version = "0.4.7" +version = "0.4.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a96cfd5557eb82f2b83fed4955246c988d331975a002961b07c81584d107e7f7" +checksum = "5037190e1f70cbeef565bd267599242926f724d3b8a9f510fd7e0b540cfa4404" dependencies = [ "arbitrary", "cc", - "once_cell", ] [[package]] name = "libgit2-sys" -version = "0.18.0+1.9.0" +version = "0.18.2+1.9.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e1a117465e7e1597e8febea8bb0c410f1c7fb93b1e1cddf34363f8390367ffec" +checksum = "1c42fe03df2bd3c53a3a9c7317ad91d80c81cd1fb0caec8d7cc4cd2bfa10c222" dependencies = [ "cc", "libc", @@ -9107,25 +9378,25 @@ dependencies = [ [[package]] name = "libloading" -version = "0.7.4" +version = "0.8.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b67380fd3b2fbe7527a606e18729d21c6f3951633d0500574c4dc22d2d638b9f" +checksum = "07033963ba89ebaf1584d767badaa2e8fcec21aedea6b8c0346d487d49c28667" dependencies = [ "cfg-if", - "winapi", + "windows-targets 0.53.3", ] [[package]] name = "libm" -version = "0.2.8" +version = "0.2.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4ec2a862134d2a7d32d7983ddcdd1c4923530833c9f2ea1a44fc5fa473989058" +checksum = "f9fbbcab51052fe104eb5e5d351cf728d30a5be1fe14d9be8a3b097481fb97de" [[package]] name = "libnghttp2-sys" -version = "0.1.9+1.58.0" +version = "0.1.11+1.64.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b57e858af2798e167e709b9d969325b6d8e9d50232fcbc494d7d54f976854a64" +checksum = "1b6c24e48a7167cffa7119da39d577fa482e66c688a4aac016bee862e1a713c4" dependencies = [ "cc", "libc", @@ -9141,7 +9412,7 @@ dependencies = [ "either", "futures", "futures-timer", - "getrandom 0.2.10", + "getrandom 0.2.16", "libp2p-allow-block-list", "libp2p-connection-limits", "libp2p-core", @@ -9160,10 +9431,10 @@ dependencies = [ "libp2p-upnp", "libp2p-websocket", "libp2p-yamux", - "multiaddr 0.18.1", + "multiaddr 0.18.2", "pin-project", "rw-stream-sink", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -9201,17 +9472,17 @@ dependencies = [ "futures", "futures-timer", "libp2p-identity", - "multiaddr 0.18.1", - "multihash 0.19.1", + "multiaddr 0.18.2", + "multihash 0.19.3", "multistream-select", "once_cell", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project", "quick-protobuf", "rand 0.8.5", "rw-stream-sink", "smallvec", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", "unsigned-varint 0.8.0", "void", @@ -9226,10 +9497,10 @@ checksum = "97f37f30d5c7275db282ecd86e54f29dd2176bd3ac656f06abf43bedb21eb8bd" dependencies = [ "async-trait", "futures", - "hickory-resolver 0.24.2", + "hickory-resolver 0.24.4", "libp2p-core", "libp2p-identity", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "smallvec", "tracing", ] @@ -9248,29 +9519,29 @@ dependencies = [ "libp2p-core", "libp2p-identity", "libp2p-swarm", - "lru 0.12.3", + "lru 0.12.5", "quick-protobuf", "quick-protobuf-codec", "smallvec", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", "void", ] [[package]] name = "libp2p-identity" -version = "0.2.9" +version = "0.2.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "55cca1eb2bc1fd29f099f3daaab7effd01e1a54b7c577d0ed082521034d912e8" +checksum = "3104e13b51e4711ff5738caa1fb54467c8604c2e94d607e27745bcf709068774" dependencies = [ "bs58", "ed25519-dalek", "hkdf", - "multihash 0.19.1", + "multihash 0.19.3", "quick-protobuf", "rand 0.8.5", - "sha2 0.10.8", - "thiserror 1.0.65", + "sha2 0.10.9", + "thiserror 2.0.16", "tracing", "zeroize", ] @@ -9281,7 +9552,7 @@ version = "0.46.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ced237d0bd84bbebb7c2cad4c073160dacb4fe40534963c32ed6d4c6bb7702a3" dependencies = [ - "arrayvec 0.7.4", + "arrayvec 0.7.6", "asynchronous-codec 0.7.0", "bytes", "either", @@ -9295,9 +9566,9 @@ dependencies = [ "quick-protobuf", "quick-protobuf-codec", "rand 0.8.5", - "sha2 0.10.8", + "sha2 0.10.9", "smallvec", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", "uint 0.9.5", "void", @@ -9312,14 +9583,14 @@ checksum = "14b8546b6644032565eb29046b42744aee1e9f261ed99671b2c93fb140dba417" dependencies = [ "data-encoding", "futures", - "hickory-proto 0.24.1", + "hickory-proto 0.24.4", "if-watch", "libp2p-core", "libp2p-identity", "libp2p-swarm", "rand 0.8.5", "smallvec", - "socket2 0.5.9", + "socket2 0.5.10", "tokio", "tracing", "void", @@ -9355,15 +9626,15 @@ dependencies = [ "futures", "libp2p-core", "libp2p-identity", - "multiaddr 0.18.1", - "multihash 0.19.1", + "multiaddr 0.18.2", + "multihash 0.19.3", "once_cell", "quick-protobuf", "rand 0.8.5", - "sha2 0.10.8", + "sha2 0.10.9", "snow", "static_assertions", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", "x25519-dalek", "zeroize", @@ -9400,13 +9671,13 @@ dependencies = [ "libp2p-core", "libp2p-identity", "libp2p-tls", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "quinn", "rand 0.8.5", - "ring 0.17.8", - "rustls 0.23.18", - "socket2 0.5.9", - "thiserror 1.0.65", + "ring 0.17.14", + "rustls 0.23.31", + "socket2 0.5.10", + "thiserror 1.0.69", "tokio", "tracing", ] @@ -9444,7 +9715,7 @@ dependencies = [ "libp2p-core", "libp2p-identity", "libp2p-swarm-derive", - "lru 0.12.3", + "lru 0.12.5", "multistream-select", "once_cell", "rand 0.8.5", @@ -9462,9 +9733,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "206e0aa0ebe004d778d79fb0966aa0de996c19894e2c0605ba2f8524dd4443d8" dependencies = [ "heck 0.5.0", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -9479,7 +9750,7 @@ dependencies = [ "libc", "libp2p-core", "libp2p-identity", - "socket2 0.5.9", + "socket2 0.5.10", "tokio", "tracing", ] @@ -9495,10 +9766,10 @@ dependencies = [ "libp2p-core", "libp2p-identity", "rcgen", - "ring 0.17.8", - "rustls 0.23.18", - "rustls-webpki 0.101.4", - "thiserror 1.0.65", + "ring 0.17.14", + "rustls 0.23.31", + "rustls-webpki 0.101.7", + "thiserror 1.0.69", "x509-parser 0.16.0", "yasna", ] @@ -9530,14 +9801,14 @@ dependencies = [ "futures-rustls", "libp2p-core", "libp2p-identity", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project-lite", "rw-stream-sink", - "soketto 0.8.0", - "thiserror 1.0.65", + "soketto 0.8.1", + "thiserror 1.0.69", "tracing", "url", - "webpki-roots 0.25.2", + "webpki-roots 0.25.4", ] [[package]] @@ -9549,12 +9820,23 @@ dependencies = [ "either", "futures", "libp2p-core", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", "yamux 0.12.1", "yamux 0.13.6", ] +[[package]] +name = "libredox" +version = "0.1.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "391290121bad3d37fbddad76d8f5d1c1c314cfc646d143d7e07a3086ddff0ce3" +dependencies = [ + "bitflags 2.9.3", + "libc", + "redox_syscall 0.5.17", +] + [[package]] name = "librocksdb-sys" version = "0.11.0+8.1.1" @@ -9572,12 +9854,12 @@ dependencies = [ [[package]] name = "libsecp256k1" -version = "0.7.1" +version = "0.7.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "95b09eff1b35ed3b33b877ced3a691fc7a481919c7e29c53c906226fcf55e2a1" +checksum = "e79019718125edc905a079a70cfa5f3820bc76139fc91d6f9abc27ea2a887139" dependencies = [ "arrayref", - "base64 0.13.1", + "base64 0.22.1", "digest 0.9.0", "hmac-drbg", "libsecp256k1-core", @@ -9597,7 +9879,7 @@ checksum = "5be9b9bb642d8522a44d533eab56c16c738301965504753b03ad1de3425d5451" dependencies = [ "crunchy", "digest 0.9.0", - "subtle 2.5.0", + "subtle 2.6.1", ] [[package]] @@ -9631,9 +9913,9 @@ dependencies = [ [[package]] name = "libz-sys" -version = "1.1.12" +version = "1.1.22" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d97137b25e321a73eef1418d1d5d2eda4d77e12813f8e6dead84bc52c5870a7b" +checksum = "8b70e7a7df205e92a1a4cd9aaae7898dac0aa555503cc0a649494d0d60e7651d" dependencies = [ "cc", "libc", @@ -9643,9 +9925,9 @@ dependencies = [ [[package]] name = "link-cplusplus" -version = "1.0.9" +version = "1.0.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9d240c6f7e1ba3a28b0249f774e6a9dd0175054b52dfbb61b16eb8505c3785c9" +checksum = "4a6f6da007f968f9def0d65a05b187e2960183de70c160204ecfccf0ee330212" dependencies = [ "cc", ] @@ -9658,18 +9940,18 @@ checksum = "0717cef1bc8b636c6e1c1bbdefc09e6322da8a9321966e8928ef80d20f7f770f" [[package]] name = "linked_hash_set" -version = "0.1.4" +version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "47186c6da4d81ca383c7c47c1bfc80f4b95f4720514d860a5407aaf4233f9588" +checksum = "bae85b5be22d9843c80e5fc80e9b64c8a3b1f98f867c709956eca3efff4e92e2" dependencies = [ "linked-hash-map", ] [[package]] name = "linregress" -version = "0.5.2" +version = "0.5.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4de0b5f52a9f84544d268f5fabb71b38962d6aa3c6600b8bcd27d44ccf9c9c45" +checksum = "a9eda9dcf4f2a99787827661f312ac3219292549c2ee992bf9a6248ffb066bf7" dependencies = [ "nalgebra", ] @@ -9682,9 +9964,9 @@ checksum = "ef53942eb7bf7ff43a617b3e2c1c4a5ecf5944a7c1bc12d7ee39bbb15e5c1519" [[package]] name = "linux-raw-sys" -version = "0.4.14" +version = "0.4.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "78b3ae25bc7c8c38cec158d1f2757ee79e9b3740fbc7ccf0e59e4b08d793fa89" +checksum = "d26c52dbd32dccf2d10cac7725f8eae5296885fb5703b261f7d0a0739ec807ab" [[package]] name = "linux-raw-sys" @@ -9724,9 +10006,9 @@ dependencies = [ [[package]] name = "litemap" -version = "0.7.4" +version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4ee93343901ab17bd981295f2cf0026d4ad018c7c31ba84549a4ddbb47a45104" +checksum = "241eaef5fd12c88705a01fc1066c48c4b36e0dd4377dcdc7ec3942cea7a69956" [[package]] name = "litep2p" @@ -9748,18 +10030,18 @@ dependencies = [ "multiaddr 0.17.1", "multihash 0.17.0", "network-interface", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project", "prost 0.13.5", "prost-build", "rand 0.8.5", "serde", - "sha2 0.10.8", + "sha2 0.10.9", "simple-dns", "smallvec", "snow", - "socket2 0.5.9", - "thiserror 2.0.12", + "socket2 0.5.10", + "thiserror 2.0.16", "tokio", "tokio-stream", "tokio-tungstenite 0.27.0", @@ -9777,9 +10059,9 @@ dependencies = [ [[package]] name = "lock_api" -version = "0.4.10" +version = "0.4.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c1cc9717a20b1bb222f333e6a92fd32f7d8a18ddc5a3191a11af45dcbf4dcd16" +checksum = "96936507f153605bddfcda068dd804796c84324ed2510809e5b2a624c81da765" dependencies = [ "autocfg", "scopeguard", @@ -9787,9 +10069,9 @@ dependencies = [ [[package]] name = "log" -version = "0.4.22" +version = "0.4.27" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a7a70ba024b9dc04c27ea2f0c0548feb474ec5c54bba33a7f72f873a39d07b24" +checksum = "13dc2df351e3202783a1fe0d44375f7295ffb4049267b0f3018346dc122a1d94" dependencies = [ "serde", "value-bag", @@ -9805,22 +10087,22 @@ dependencies = [ "generator", "scoped-tls", "tracing", - "tracing-subscriber", + "tracing-subscriber 0.3.19", ] [[package]] name = "lru" -version = "0.11.0" +version = "0.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eedb2bdbad7e0634f83989bf596f497b070130daaa398ab22d84c39e266deec5" +checksum = "a4a83fb7698b3643a0e34f9ae6f2e8f0178c0fd42f8b59d493aa271ff3a5bf21" [[package]] name = "lru" -version = "0.12.3" +version = "0.12.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d3262e75e648fce39813cb56ac41f3c3e3f65217ebf3844d818d1f9398cfb0dc" +checksum = "234cf4f4a04dc1f57e24b96cc0cd600cf2af460d4161ac5ecdd0af8e1f3b2a38" dependencies = [ - "hashbrown 0.14.5", + "hashbrown 0.15.5", ] [[package]] @@ -9832,21 +10114,26 @@ dependencies = [ "linked-hash-map", ] +[[package]] +name = "lru-slab" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "112b39cec0b298b6c1999fee3e31427f74f676e4cb9879ed1a121b43661a4154" + [[package]] name = "lz4" -version = "1.24.0" +version = "1.28.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7e9e2dd86df36ce760a60f6ff6ad526f7ba1f14ba0356f8254fb6905e6494df1" +checksum = "a20b523e860d03443e98350ceaac5e71c6ba89aea7d960769ec3ce37f4de5af4" dependencies = [ - "libc", "lz4-sys", ] [[package]] name = "lz4-sys" -version = "1.9.4" +version = "1.11.1+lz4-1.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "57d27b317e207b10f69f5e75494119e391a96f48861ae870d1da6edac98ca900" +checksum = "6bd8c0d6c6ed0cd30b3652886bb8711dc4bb01d637a68105a3d5158039b418e6" dependencies = [ "cc", "libc", @@ -9854,9 +10141,9 @@ dependencies = [ [[package]] name = "mach2" -version = "0.4.2" +version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "19b955cdeb2a02b9117f121ce63aa52d08ade45de53e48fe6a38b39c10f6f709" +checksum = "d640282b302c0bb0a2a8e0233ead9035e3bed871f0b7e81fe4a1ec829765db44" dependencies = [ "libc", ] @@ -9867,9 +10154,9 @@ version = "0.1.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1b27834086c65ec3f9387b096d66e99f221cf081c2b738042aa252bcd41204e3" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -9881,7 +10168,7 @@ dependencies = [ "macro_magic_core", "macro_magic_macros", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -9893,9 +10180,9 @@ dependencies = [ "const-random", "derive-syn-parse", "macro_magic_core_macros", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -9904,9 +10191,9 @@ version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b02abfe41815b5bd98dbd4260173db2c116dda171dc0fe7838cb206333b83308" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -9917,7 +10204,7 @@ checksum = "73ea28ee64b88876bf45277ed9a5817c1817df061a74f2b988971a12570e5869" dependencies = [ "macro_magic_core", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -9926,12 +10213,6 @@ version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3e2e65a1a2e43cfcb47a895c4c8b10d1f4a61097f9f254f183aee60cad9c651d" -[[package]] -name = "match_cfg" -version = "0.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ffbee8634e0d45d258acb448e7eaab3fce7a0a467395d4d9f228e3c1f01fb2e4" - [[package]] name = "matchers" version = "0.1.0" @@ -9943,9 +10224,9 @@ dependencies = [ [[package]] name = "matrixmultiply" -version = "0.3.7" +version = "0.3.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "090126dc04f95dc0d1c1c91f61bdd474b3930ca064c1edc8a849da2c6cbe1e77" +checksum = "a06de3016e9fae57a36fd14dba131fccf49f74b40b7fbdb472f96e361ec71a08" dependencies = [ "autocfg", "rawpointer", @@ -9963,17 +10244,17 @@ dependencies = [ [[package]] name = "memchr" -version = "2.7.4" +version = "2.7.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "78ca9ab1a0babb1e7d5695e3530886289c18cf2f87ec19a575a0abdce112e3a3" +checksum = "32a282da65faaf38286cf3be983213fcf1d2e2a58700e808f83f4ea9a4804bc0" [[package]] name = "memfd" -version = "0.6.3" +version = "0.6.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ffc89ccdc6e10d6907450f753537ebc5c5d3460d2e4e62ea74bd571db62c0f9e" +checksum = "b2cffa4ad52c6f791f4f8b15f0c05f9824b2ced1160e88cc393d64fff9a8ac64" dependencies = [ - "rustix 0.37.23", + "rustix 0.38.44", ] [[package]] @@ -9987,31 +10268,22 @@ dependencies = [ [[package]] name = "memmap2" -version = "0.9.3" +version = "0.9.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "45fd3a57831bf88bc63f8cebc0cf956116276e97fef3966103e96416209f7c92" +checksum = "843a98750cd611cc2965a8213b53b43e715f13c37a9e096c6408e69990961db7" dependencies = [ "libc", ] -[[package]] -name = "memoffset" -version = "0.9.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5a634b1c61a95585bd15607c6ab0c4e5b226e695ff2800ba0cdccddf208c406c" -dependencies = [ - "autocfg", -] - [[package]] name = "memory-db" version = "0.34.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7e300c54e3239a86f9c61cc63ab0f03862eb40b1c6e065dc6fd6ceaeff6da93d" dependencies = [ - "foldhash", + "foldhash 0.1.5", "hash-db", - "hashbrown 0.15.3", + "hashbrown 0.15.5", ] [[package]] @@ -10020,7 +10292,7 @@ version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b3e3e3f549d27d2dc054372f320ddf68045a833fab490563ff70d4cf1b9d91ea" dependencies = [ - "array-bytes 9.1.2", + "array-bytes 9.3.0", "blake3", "frame-metadata 23.0.0", "parity-scale-codec", @@ -10052,7 +10324,7 @@ dependencies = [ "hex", "log", "num-traits", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "relay-utils", "sp-arithmetic", "sp-core 28.0.0", @@ -10096,23 +10368,22 @@ dependencies = [ [[package]] name = "miniz_oxide" -version = "0.7.1" +version = "0.8.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e7810e0be55b428ada41041c41f32c9f1a42817901b4ccf45fa3d4b6561e74c7" +checksum = "1fa76a2c86f704bdb222d66965fb3d63269ce38518b83cb0575fca855ebb6316" dependencies = [ - "adler", + "adler2", ] [[package]] name = "mio" -version = "1.0.2" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "80e04d1dcff3aae0704555fe5fee3bcfaf3d1fdf8a7e521d5b9d2b42acb52cec" +checksum = "78bed444cc8a2160f01cbcf811ef18cac863ad68ae8ca62092e8db51d51c761c" dependencies = [ - "hermit-abi", "libc", - "wasi 0.11.0+wasi-snapshot-preview1", - "windows-sys 0.52.0", + "wasi 0.11.1+wasi-snapshot-preview1", + "windows-sys 0.59.0", ] [[package]] @@ -10122,7 +10393,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "daa3eb39495d8e2e2947a1d862852c90cc6a4a8845f8b41c8829cb9fcc047f4a" dependencies = [ "arrayref", - "arrayvec 0.7.4", + "arrayvec 0.7.6", "bitflags 1.3.2", "blake2 0.10.6", "c2-chacha", @@ -10131,12 +10402,12 @@ dependencies = [ "hashlink 0.8.4", "lioness", "log", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", "rand_chacha 0.3.1", "rand_distr", - "subtle 2.5.0", - "thiserror 1.0.65", + "subtle 2.6.1", + "thiserror 1.0.69", "zeroize", ] @@ -10147,7 +10418,7 @@ dependencies = [ "futures", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-block-builder", "sc-client-api", "sc-offchain", @@ -10199,9 +10470,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "25ca3004c2efe9011bd4e461bd8256445052b9615405b4f7ea43fc8ca5c20898" dependencies = [ "cfg-if", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -10214,12 +10485,12 @@ dependencies = [ "crossbeam-epoch", "crossbeam-utils", "loom", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "portable-atomic", - "rustc_version 0.4.0", + "rustc_version 0.4.1", "smallvec", "tagptr", - "thiserror 1.0.65", + "thiserror 1.0.69", "uuid", ] @@ -10250,20 +10521,20 @@ dependencies = [ [[package]] name = "multiaddr" -version = "0.18.1" +version = "0.18.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8b852bc02a2da5feed68cd14fa50d0774b92790a5bdbfa932a813926c8472070" +checksum = "fe6351f60b488e04c1d21bc69e56b89cb3f5e8f5d22557d6e8031bdfd79b6961" dependencies = [ "arrayref", "byteorder", "data-encoding", "libp2p-identity", "multibase", - "multihash 0.19.1", + "multihash 0.19.3", "percent-encoding", "serde", "static_assertions", - "unsigned-varint 0.7.2", + "unsigned-varint 0.8.0", "url", ] @@ -10290,30 +10561,30 @@ dependencies = [ "core2", "digest 0.10.7", "multihash-derive", - "sha2 0.10.8", + "sha2 0.10.9", "sha3", "unsigned-varint 0.7.2", ] [[package]] name = "multihash" -version = "0.19.1" +version = "0.19.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "076d548d76a0e2a0d4ab471d0b1c36c577786dfc4471242035d97a12a735c492" +checksum = "6b430e7953c29dd6a09afc29ff0bb69c6e306329ee6794700aee27b76a1aea8d" dependencies = [ "core2", - "unsigned-varint 0.7.2", + "unsigned-varint 0.8.0", ] [[package]] name = "multihash-derive" -version = "0.8.0" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fc076939022111618a5026d3be019fd8b366e76314538ff9a1b59ffbcbf98bcd" +checksum = "1d6d4752e6230d8ef7adf7bd5d8c4b1f6561c1014c5ba9a37445ccefe18aa1db" dependencies = [ - "proc-macro-crate 1.3.1", + "proc-macro-crate 1.1.3", "proc-macro-error", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "syn 1.0.109", "synstructure 0.12.6", @@ -10321,9 +10592,9 @@ dependencies = [ [[package]] name = "multimap" -version = "0.8.3" +version = "0.10.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e5ce46fe64a9d73be07dcbe690a38ce1b293be448fd8ce1e6c1b8062c9f72c6a" +checksum = "1d87ecb2933e8aeadb3e3a02b828fed80a7528047e68b4f424523a0981a3a084" [[package]] name = "multistream-select" @@ -10341,13 +10612,12 @@ dependencies = [ [[package]] name = "nalgebra" -version = "0.32.3" +version = "0.33.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "307ed9b18cc2423f29e83f84fd23a8e73628727990181f18641a8b5dc2ab1caa" +checksum = "26aecdf64b707efd1310e3544d709c5c0ac61c13756046aaaba41be5c4f66a3b" dependencies = [ "approx", "matrixmultiply", - "nalgebra-macros", "num-complex", "num-rational", "num-traits", @@ -10355,17 +10625,6 @@ dependencies = [ "typenum", ] -[[package]] -name = "nalgebra-macros" -version = "0.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "91761aed67d03ad966ef783ae962ef9bbaca728d2dd7ceb7939ec110fffad998" -dependencies = [ - "proc-macro2 1.0.95", - "quote 1.0.40", - "syn 1.0.109", -] - [[package]] name = "names" version = "0.14.0" @@ -10383,9 +10642,9 @@ checksum = "6a51313c5820b0b02bd422f4b44776fbf47961755c74ce64afc73bfad10226c3" [[package]] name = "native-tls" -version = "0.2.12" +version = "0.2.14" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a8614eb2c83d59d1c8cc974dd3f920198647674a0a035e1af1fa58707e317466" +checksum = "87de3442987e9dbec73158d5c715e7ad9072fda936bb03d19d7fa10e00520f0e" dependencies = [ "libc", "log", @@ -10393,28 +10652,27 @@ dependencies = [ "openssl-probe", "openssl-sys", "schannel", - "security-framework", + "security-framework 2.11.1", "security-framework-sys", "tempfile", ] [[package]] name = "netlink-packet-core" -version = "0.4.2" +version = "0.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "345b8ab5bd4e71a2986663e88c56856699d060e78e152e6e9d7966fcd5491297" +checksum = "72724faf704479d67b388da142b186f916188505e7e0b26719019c525882eda4" dependencies = [ "anyhow", "byteorder", - "libc", "netlink-packet-utils", ] [[package]] name = "netlink-packet-route" -version = "0.12.0" +version = "0.17.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d9ea4302b9759a7a88242299225ea3688e63c85ea136371bb6cf94fd674efaab" +checksum = "053998cea5a306971f88580d0829e90f270f940befd7cf928da179d4187a5a66" dependencies = [ "anyhow", "bitflags 1.3.2", @@ -10433,29 +10691,28 @@ dependencies = [ "anyhow", "byteorder", "paste", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] name = "netlink-proto" -version = "0.10.0" +version = "0.11.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "65b4b14489ab424703c092062176d52ba55485a89c076b4f9db05092b7223aa6" +checksum = "72452e012c2f8d612410d89eea01e2d9b56205274abb35d53f60200b2ec41d60" dependencies = [ "bytes", "futures", "log", "netlink-packet-core", "netlink-sys", - "thiserror 1.0.65", - "tokio", + "thiserror 2.0.16", ] [[package]] name = "netlink-sys" -version = "0.8.5" +version = "0.8.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6471bf08e7ac0135876a9581bf3217ef0333c191c128d34878079f42ee150411" +checksum = "16c903aa70590cb93691bf97a767c8d1d6122d2cc9070433deb3bbf36ce8bd23" dependencies = [ "bytes", "futures", @@ -10466,21 +10723,21 @@ dependencies = [ [[package]] name = "network-interface" -version = "2.0.1" +version = "2.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c3329f515506e4a2de3aa6e07027a6758e22e0f0e8eaf64fa47261cec2282602" +checksum = "07709a6d4eba90ab10ec170a0530b3aafc81cb8a2d380e4423ae41fc55fe5745" dependencies = [ "cc", "libc", - "thiserror 1.0.65", + "thiserror 2.0.16", "winapi", ] [[package]] name = "nix" -version = "0.24.3" +version = "0.26.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fa52e972a9a719cecb6864fb88568781eb706bac2cd1d4f04a648542dbf78069" +checksum = "598beaf3cc6fdd9a5dfb1630c2800c7acd31df7aaf0f565796fba2b53ca1af1b" dependencies = [ "bitflags 1.3.2", "cfg-if", @@ -10493,7 +10750,7 @@ version = "0.27.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2eb04e9c688eff1c89d72b407f168cf79bb9e867a9d3323ed6c01519eb9cc053" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", "cfg-if", "libc", ] @@ -10504,7 +10761,19 @@ version = "0.29.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "71e2746dc3a24dd78b3cfcb7be93368c6de9963d30f43a6a73998a9cf4b17b46" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", + "cfg-if", + "cfg_aliases 0.2.1", + "libc", +] + +[[package]] +name = "nix" +version = "0.30.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74523f3a35e05aba87a1d978330aef40f67b0304ac79c1c00b294c9830543db6" +dependencies = [ + "bitflags 2.9.3", "cfg-if", "cfg_aliases 0.2.1", "libc", @@ -10526,10 +10795,10 @@ checksum = "43794a0ace135be66a25d3ae77d41b91615fb68ae937f904090203e81f755b65" name = "node-bench" version = "0.9.0-dev" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "async-trait", "clap", - "derive_more 0.99.17", + "derive_more 0.99.20", "fs_extra", "futures", "hash-db", @@ -10681,6 +10950,15 @@ dependencies = [ "minimal-lexical", ] +[[package]] +name = "nom" +version = "8.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "df9761775871bdef83bee530e60050f7e54b1105350d6884eb0fb4f46c2f9405" +dependencies = [ + "memchr", +] + [[package]] name = "nonempty" version = "0.7.0" @@ -10714,9 +10992,9 @@ dependencies = [ [[package]] name = "num" -version = "0.4.1" +version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b05180d69e3da0e530ba2a1dae5110317e49e3b7f3d41be227dc5f92e49ee7af" +checksum = "35bd024e8b2ff75562e5f34e7f4905839deb4b22955ef5e73d2fea1b9813cb23" dependencies = [ "num-bigint", "num-complex", @@ -10728,11 +11006,10 @@ dependencies = [ [[package]] name = "num-bigint" -version = "0.4.4" +version = "0.4.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "608e7659b5c3d7cba262d894801b9ec9d00de989e8a82bd4bef91d08da45cdc0" +checksum = "a5e44f723f1133c9deac646763579fdb3ac745e418f2a7af9cd0c431da1f20b9" dependencies = [ - "autocfg", "num-integer", "num-traits", ] @@ -10756,9 +11033,9 @@ dependencies = [ [[package]] name = "num-complex" -version = "0.4.4" +version = "0.4.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1ba157ca0885411de85d6ca030ba7e2a83a28636056c7c699b07c8b6f7383214" +checksum = "73f88a1307638156682bada9d7604135552957b7818057dcef22705b4d509495" dependencies = [ "num-traits", ] @@ -10775,9 +11052,9 @@ version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ed3955f1a9c7c0c15e092f9c887db08b1fc683305fdf6eb6684f22555355e202" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -10786,7 +11063,7 @@ version = "0.4.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a652d9771a63711fd3c3deb670acfbe5c30a4072e664d7a3bf5a9e1056ac72c3" dependencies = [ - "arrayvec 0.7.4", + "arrayvec 0.7.6", "itoa", ] @@ -10801,9 +11078,9 @@ dependencies = [ [[package]] name = "num-iter" -version = "0.1.43" +version = "0.1.45" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7d03e6c028c5dc5cac6e2dec0efda81fc887605bb3d884578bb6d6bf7514e252" +checksum = "1429034a0490724d0075ebb2bc9e875d6503c3cf69e235a8941aa757d83ef5bf" dependencies = [ "autocfg", "num-integer", @@ -10812,11 +11089,10 @@ dependencies = [ [[package]] name = "num-rational" -version = "0.4.1" +version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0638a1c9d0a3c0914158145bc76cff373a75a627e6ecbfb71cbe6f453a5a19b0" +checksum = "f83d14da390562dca69fc84082e73e548e1ad308d24accdedd2720017cb37824" dependencies = [ - "autocfg", "num-bigint", "num-integer", "num-traits", @@ -10834,14 +11110,36 @@ dependencies = [ [[package]] name = "num_cpus" -version = "1.16.0" +version = "1.17.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43" +checksum = "91df4bbde75afed763b708b7eee1e8e7651e02d97f6d5dd763e89367e957b23b" dependencies = [ - "hermit-abi", + "hermit-abi 0.5.2", "libc", ] +[[package]] +name = "num_enum" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a973b4e44ce6cad84ce69d797acf9a044532e4184c4f267913d1b546a0727b7a" +dependencies = [ + "num_enum_derive", + "rustversion", +] + +[[package]] +name = "num_enum_derive" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77e878c846a8abae00dd069496dbe8751b16ac1c3d6bd2a7283a938e8228f90d" +dependencies = [ + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", + "quote 1.0.40", + "syn 2.0.106", +] + [[package]] name = "num_threads" version = "0.1.7" @@ -10857,15 +11155,6 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "830b246a0e5f20af87141b25c173cd1b609bd7779a4617d6ec582abaf90870f3" -[[package]] -name = "object" -version = "0.32.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a6a622008b6e321afc04970976f62ee297fdbaa6f95318ca343e3eebb9648441" -dependencies = [ - "memchr", -] - [[package]] name = "object" version = "0.36.7" @@ -10873,18 +11162,18 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "62948e14d923ea95ea2c7c86c71013138b66525b86bdc08d2dcc262bdb497b87" dependencies = [ "crc32fast", - "hashbrown 0.15.3", + "hashbrown 0.15.5", "indexmap", "memchr", ] [[package]] name = "oid-registry" -version = "0.7.0" +version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1c958dd45046245b9c3c2547369bb634eb461670b2e7e0de552905801a648d1d" +checksum = "a8d8034d9489cdaf79228eb9f6a3b8d7bb32ba00d6645ebd48eef4077ceb5bd9" dependencies = [ - "asn1-rs 0.6.1", + "asn1-rs 0.6.2", ] [[package]] @@ -10893,7 +11182,7 @@ version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "12f40cff3dde1b6087cc5d5f5d4d65712f34016a03ed60e9c08dcc392736b5b7" dependencies = [ - "asn1-rs 0.7.0", + "asn1-rs 0.7.1", ] [[package]] @@ -10906,11 +11195,17 @@ dependencies = [ "portable-atomic", ] +[[package]] +name = "once_cell_polyfill" +version = "1.70.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a4895175b425cb1f87721b59f0f286c2092bd4af812243672510e1ac53e2e0ad" + [[package]] name = "oorandom" -version = "11.1.3" +version = "11.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0ab1bc2a289d34bd04a330323ac98a1b4bc82c9d9fcb1e66b63caa84da26b575" +checksum = "d6790f58c7ff633d8771f42965289203411a5e5c68388703c06e14f24770b41e" [[package]] name = "opaque-debug" @@ -10920,17 +11215,17 @@ checksum = "2839e79665f131bdb5782e51f2c6c9599c133c6098982a54c794358bf432529c" [[package]] name = "opaque-debug" -version = "0.3.0" +version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "624a8340c38c1b80fd549087862da4ba43e08858af025b236e509b6649fc13d5" +checksum = "c08d65885ee38876c4f86fa503fb49d7b507c2b62552df7c70b2fce627e06381" [[package]] name = "openssl" -version = "0.10.72" +version = "0.10.73" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fedfea7d58a1f73118430a55da6a286e7b044961736ce96a16a17068ea25e5da" +checksum = "8505734d46c8ab1e19a1dce3aef597ad87dcb4c37e7188231769bd6bd51cebf8" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", "cfg-if", "foreign-types", "libc", @@ -10945,22 +11240,22 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a948666b637a0f465e8564c73e89d4dde00d72d4d473cc972f390fc3dcee7d9c" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "openssl-probe" -version = "0.1.5" +version = "0.1.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ff011a302c396a5197692431fc1948019154afc178baf7d8e37367442a4601cf" +checksum = "d05e27ee213611ffe7d6348b942e8f942b37114c00cc03cec254295a4a17852e" [[package]] name = "openssl-sys" -version = "0.9.107" +version = "0.9.109" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8288979acd84749c744a9014b4382d42b8f7b2592847b5afb2ed29e5d16ede07" +checksum = "90096e2e47630d78b7d1c20952dc621f957103f8bc2c8359ec81290d75238571" dependencies = [ "cc", "libc", @@ -10987,7 +11282,7 @@ dependencies = [ "orchestra-proc-macro", "pin-project", "prioritized-metered-channel", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", ] @@ -11000,9 +11295,9 @@ dependencies = [ "expander", "indexmap", "itertools 0.11.0", - "petgraph", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "petgraph 0.6.5", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", "syn 1.0.109", ] @@ -11018,9 +11313,9 @@ dependencies = [ [[package]] name = "os_pipe" -version = "1.2.1" +version = "1.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5ffd2b0a5634335b135d5728d84c5e0fd726954b87111f7506a61c502280d982" +checksum = "db335f4760b14ead6290116f2427bf33a14d4f0617d49f78a246de10c1831224" dependencies = [ "libc", "windows-sys 0.59.0", @@ -11034,9 +11329,21 @@ checksum = "b15813163c1d831bf4a13c3610c05c0d03b39feb07f7e09fa234dac9b15aaf39" [[package]] name = "owo-colors" -version = "3.5.0" +version = "4.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c1b04fb49957986fdce4d6ee7a65027d55d4b6d2265e5848bbb507b58ccfdb6f" +checksum = "48dd4f4a2c8405440fd0462561f0e5806bd0f77e86f51c761481bdd4018b545e" + +[[package]] +name = "p256" +version = "0.13.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c9863ad85fa8f4460f9c48cb909d38a0d689dba1f6f6988a5e3e0d31071bcd4b" +dependencies = [ + "ecdsa", + "elliptic-curve", + "primeorder", + "sha2 0.10.9", +] [[package]] name = "pallet-ah-ops" @@ -11088,7 +11395,7 @@ dependencies = [ name = "pallet-alliance" version = "27.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "frame-benchmarking", "frame-support", "frame-system", @@ -11443,7 +11750,7 @@ dependencies = [ name = "pallet-beefy-mmr" version = "28.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "binary-merkle-tree", "frame-benchmarking", "frame-support", @@ -11585,7 +11892,6 @@ dependencies = [ "frame-benchmarking", "frame-support", "frame-system", - "log", "pallet-balances", "pallet-bridge-grandpa", "pallet-bridge-messages", @@ -11598,6 +11904,7 @@ dependencies = [ "sp-core 28.0.0", "sp-io", "sp-runtime", + "tracing", ] [[package]] @@ -11696,7 +12003,7 @@ dependencies = [ name = "pallet-contracts" version = "27.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "assert_matches", "environmental", "frame-benchmarking", @@ -11742,8 +12049,8 @@ dependencies = [ "parity-wasm", "sp-runtime", "tempfile", - "toml", - "twox-hash", + "toml 0.8.23", + "twox-hash 1.6.3", ] [[package]] @@ -11781,9 +12088,9 @@ dependencies = [ name = "pallet-contracts-proc-macro" version = "18.0.0" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -11955,7 +12262,7 @@ dependencies = [ "pallet-staking", "pallet-timestamp", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "scale-info", "sp-core 28.0.0", "sp-io", @@ -11976,7 +12283,7 @@ dependencies = [ "log", "pallet-balances", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", "scale-info", "sp-arithmetic", @@ -12001,7 +12308,7 @@ dependencies = [ "log", "pallet-balances", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", "scale-info", "sp-arithmetic", @@ -12861,9 +13168,9 @@ name = "pallet-revive" version = "0.1.0" dependencies = [ "alloy-core", - "array-bytes 6.2.2", + "array-bytes 6.2.3", "assert_matches", - "derive_more 0.99.17", + "derive_more 0.99.20", "environmental", "ethereum-standards", "ethereum-types", @@ -12892,6 +13199,7 @@ dependencies = [ "pretty_assertions", "rand 0.8.5", "rand_pcg", + "revm", "ripemd", "rlp 0.6.1", "scale-info", @@ -12909,7 +13217,7 @@ dependencies = [ "sp-runtime", "sp-tracing 16.0.0", "substrate-bn", - "subxt-signer 0.41.0", + "subxt-signer 0.43.0", ] [[package]] @@ -12918,7 +13226,7 @@ version = "0.1.0" dependencies = [ "anyhow", "clap", - "env_logger 0.11.3", + "env_logger 0.11.8", "futures", "git2", "hex", @@ -12944,9 +13252,9 @@ dependencies = [ "static_init", "substrate-cli-test-utils", "substrate-prometheus-endpoint", - "subxt 0.41.0", - "subxt-signer 0.41.0", - "thiserror 1.0.65", + "subxt 0.43.0", + "subxt-signer 0.43.0", + "thiserror 1.0.69", "tokio", ] @@ -12954,22 +13262,25 @@ dependencies = [ name = "pallet-revive-fixtures" version = "0.1.0" dependencies = [ + "alloy-core", "anyhow", "cargo_metadata", + "hex", "pallet-revive-uapi", "polkavm-linker 0.27.0", + "serde_json", "sp-core 28.0.0", "sp-io", - "toml", + "toml 0.8.23", ] [[package]] name = "pallet-revive-proc-macro" version = "0.1.0" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -13043,7 +13354,7 @@ dependencies = [ name = "pallet-sassafras" version = "0.3.5-dev" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "frame-benchmarking", "frame-support", "frame-system", @@ -13196,7 +13507,7 @@ name = "pallet-staking-async" version = "0.1.0" dependencies = [ "anyhow", - "env_logger 0.11.3", + "env_logger 0.11.8", "frame-benchmarking", "frame-election-provider-support", "frame-support", @@ -13523,11 +13834,11 @@ dependencies = [ name = "pallet-staking-reward-curve" version = "11.0.0" dependencies = [ - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", "sp-runtime", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -13698,7 +14009,7 @@ dependencies = [ name = "pallet-transaction-storage" version = "27.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "frame-benchmarking", "frame-support", "frame-system", @@ -14049,9 +14360,9 @@ checksum = "16b56e3a2420138bdb970f84dfb9c774aea80fa0e7371549eedec0d80c209c67" [[package]] name = "parity-db" -version = "0.4.12" +version = "0.4.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "59e9ab494af9e6e813c72170f0d3c1de1500990d62c97cc05cc7576f91aa402f" +checksum = "592a28a24b09c9dc20ac8afaa6839abc417c720afe42c12e1e4a9d6aa2508d2e" dependencies = [ "blake2 0.10.6", "crc32fast", @@ -14061,10 +14372,11 @@ dependencies = [ "log", "lz4", "memmap2 0.5.10", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", "siphasher 0.3.11", "snap", + "winapi", ] [[package]] @@ -14073,7 +14385,7 @@ version = "3.7.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "799781ae679d79a948e13d4824a40970bfa500058d245760dd857301059810fa" dependencies = [ - "arrayvec 0.7.4", + "arrayvec 0.7.6", "bitvec", "byte-slice-cast", "bytes", @@ -14090,10 +14402,10 @@ version = "3.7.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "34b4653168b563151153c9e4c08ebed57fb8262bebfa79711552fa983c623e7a" dependencies = [ - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -14121,12 +14433,12 @@ dependencies = [ [[package]] name = "parking_lot" -version = "0.12.3" +version = "0.12.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f1bf18183cf54e8d6059647fc3063646a1801cf30896933ec2311622cc4b9a27" +checksum = "70d58bf43669b5795d1576d0641cfb6fbb2057bf629506267a92807158584a13" dependencies = [ "lock_api", - "parking_lot_core 0.9.8", + "parking_lot_core 0.9.11", ] [[package]] @@ -14145,15 +14457,15 @@ dependencies = [ [[package]] name = "parking_lot_core" -version = "0.9.8" +version = "0.9.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "93f00c865fe7cabf650081affecd3871070f26767e7b2070a3ffae14c654b447" +checksum = "bc838d2a56b5b1a6c25f55575dfc605fabb63bb2365f6c2353ef9159aa69e4a5" dependencies = [ "cfg-if", "libc", - "redox_syscall 0.3.5", + "redox_syscall 0.5.17", "smallvec", - "windows-targets 0.48.5", + "windows-targets 0.52.6", ] [[package]] @@ -14170,7 +14482,7 @@ checksum = "346f04948ba92c43e8469c1ee6736c7563d71012b17d40745260fe106aac2166" dependencies = [ "base64ct", "rand_core 0.6.4", - "subtle 2.5.0", + "subtle 2.6.1", ] [[package]] @@ -14198,9 +14510,9 @@ checksum = "19b17cddbe7ec3f8bc800887bab5e717348c95ea2ca0b1bf0837fb964dc67099" [[package]] name = "pem" -version = "3.0.4" +version = "3.0.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8e459365e590736a54c3fa561947c84837534b8e9af6fc5bf781307e82658fae" +checksum = "38af38e8470ac9dee3ce1bae1af9c1671fffc44ddfd8bd1d0a3445bf349a8ef3" dependencies = [ "base64 0.22.1", "serde", @@ -14499,25 +14811,26 @@ dependencies = [ [[package]] name = "percent-encoding" -version = "2.3.1" +version = "2.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e" +checksum = "9b4f627cb1b25917193a259e49bdad08f671f8d9708acfd5fe0a8c1455d87220" [[package]] name = "pest" -version = "2.7.2" +version = "2.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1acb4a4365a13f749a93f1a094a7805e5cfa0955373a9de860d962eaa3a5fe5a" +checksum = "1db05f56d34358a8b1066f67cbb203ee3e7ed2ba674a6263a1d5ec6db2204323" dependencies = [ - "thiserror 1.0.65", + "memchr", + "thiserror 2.0.16", "ucd-trie", ] [[package]] name = "pest_derive" -version = "2.7.2" +version = "2.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "666d00490d4ac815001da55838c500eafb0320019bbaa44444137c48b443a853" +checksum = "bb056d9e8ea77922845ec74a1c4e8fb17e7c218cc4fc11a15c5d25e189aa40bc" dependencies = [ "pest", "pest_generator", @@ -14525,38 +14838,89 @@ dependencies = [ [[package]] name = "pest_generator" -version = "2.7.2" +version = "2.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "68ca01446f50dbda87c1786af8770d535423fa8a53aec03b8f4e3d7eb10e0929" +checksum = "87e404e638f781eb3202dc82db6760c8ae8a1eeef7fb3fa8264b2ef280504966" dependencies = [ "pest", "pest_meta", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "pest_meta" -version = "2.7.2" +version = "2.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "56af0a30af74d0445c0bf6d9d051c979b516a1a5af790d251daee76005420a48" +checksum = "edd1101f170f5903fde0914f899bb503d9ff5271d7ba76bbb70bea63690cc0d5" dependencies = [ - "once_cell", "pest", - "sha2 0.10.8", + "sha2 0.10.9", ] [[package]] name = "petgraph" -version = "0.6.4" +version = "0.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4c5cc86750666a3ed20bdaf5ca2a0344f9c67674cae0515bec2da16fbaa47db" +dependencies = [ + "fixedbitset 0.4.2", + "indexmap", +] + +[[package]] +name = "petgraph" +version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e1d3afd2628e69da2be385eb6f2fd57c8ac7977ceeff6dc166ff1657b0e386a9" +checksum = "3672b37090dbd86368a4145bc067582552b29c27377cad4e0a306c97f9bd7772" dependencies = [ - "fixedbitset", + "fixedbitset 0.5.7", "indexmap", ] +[[package]] +name = "phf" +version = "0.11.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1fd6780a80ae0c52cc120a26a1a42c1ae51b247a253e4e06113d23d2c2edd078" +dependencies = [ + "phf_macros", + "phf_shared", +] + +[[package]] +name = "phf_generator" +version = "0.11.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3c80231409c20246a13fddb31776fb942c38553c51e871f8cbd687a4cfb5843d" +dependencies = [ + "phf_shared", + "rand 0.8.5", +] + +[[package]] +name = "phf_macros" +version = "0.11.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f84ac04429c13a7ff43785d75ad27569f2951ce0ffd30a3321230db2fc727216" +dependencies = [ + "phf_generator", + "phf_shared", + "proc-macro2 1.0.101", + "quote 1.0.40", + "syn 2.0.106", +] + +[[package]] +name = "phf_shared" +version = "0.11.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "67eabc2ef2a60eb7faa00097bd1ffdb5bd28e62bf39990626a582201b7a754e5" +dependencies = [ + "siphasher 1.0.1", +] + [[package]] name = "pin-project" version = "1.1.10" @@ -14572,16 +14936,16 @@ version = "1.1.10" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6e918e4ff8c4549eb882f14b3a4bc8c8bc93de829416eacf579f1207a8fbf861" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "pin-project-lite" -version = "0.2.14" +version = "0.2.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bda66fc9667c18cb2758a2ac84d1167245054bcf85d5d1aaa6923f45801bdd02" +checksum = "3b3cff922bd51709b605d9ead9aa71031d81447142d828eb4a6eba76fe619f9b" [[package]] name = "pin-utils" @@ -14589,6 +14953,17 @@ version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184" +[[package]] +name = "piper" +version = "0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "96c8c490f422ef9a4efd2cb5b42b76c8613d7e7dfc1caf667b8a3350a5acc066" +dependencies = [ + "atomic-waker", + "fastrand 2.3.0", + "futures-io", +] + [[package]] name = "pkcs1" version = "0.7.5" @@ -14618,9 +14993,9 @@ checksum = "7edddbd0b52d732b21ad9a5fab5c704c14cd949e5e9a1ec5929a24fded1b904c" [[package]] name = "plotters" -version = "0.3.5" +version = "0.3.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d2c224ba00d7cadd4d5c660deaf2098e5e80e07846537c51f9cfa4be50c1fd45" +checksum = "5aeb6f403d7a4911efb1e33402027fc44f29b5bf6def3effcc22d7bb75f2b747" dependencies = [ "num-traits", "plotters-backend", @@ -14631,15 +15006,15 @@ dependencies = [ [[package]] name = "plotters-backend" -version = "0.3.5" +version = "0.3.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9e76628b4d3a7581389a35d5b6e2139607ad7c75b17aed325f210aa91f4a9609" +checksum = "df42e13c12958a16b3f7f4386b9ab1f3e7933914ecea48da7139435263a4172a" [[package]] name = "plotters-svg" -version = "0.3.5" +version = "0.3.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "38f6d39893cca0701371e3c27294f09797214b86f1fb951b89ade8ec04e2abab" +checksum = "51bae2ac328883f7acdfea3d66a7c35751187f870bc81f94563733a154d7a670" dependencies = [ "plotters-backend", ] @@ -14685,7 +15060,7 @@ dependencies = [ "rand_chacha 0.3.1", "rand_core 0.6.4", "sc-keystore", - "schnorrkel 0.11.4", + "schnorrkel 0.11.5", "sp-application-crypto", "sp-authority-discovery", "sp-core 28.0.0", @@ -14744,7 +15119,7 @@ dependencies = [ "sp-keyring", "sp-keystore", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -14774,7 +15149,7 @@ dependencies = [ "sp-core 28.0.0", "sp-keyring", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tracing-gum", ] @@ -14811,7 +15186,7 @@ dependencies = [ "sp-keyring", "sp-runtime", "substrate-build-script-utils", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -14841,7 +15216,7 @@ dependencies = [ "sp-keystore", "sp-runtime", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-util", "tracing-gum", @@ -14882,7 +15257,7 @@ dependencies = [ "sp-keyring", "sp-keystore", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -14898,7 +15273,7 @@ dependencies = [ "reed-solomon-novelpoly", "sp-core 28.0.0", "sp-trie", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -14909,7 +15284,7 @@ dependencies = [ "async-trait", "futures", "futures-timer", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-node-network-protocol", "polkadot-node-subsystem", "polkadot-node-subsystem-test-helpers", @@ -14942,7 +15317,7 @@ dependencies = [ "futures", "futures-timer", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-node-metrics", "polkadot-node-network-protocol", "polkadot-node-subsystem", @@ -14955,7 +15330,7 @@ dependencies = [ "sp-consensus", "sp-core 28.0.0", "sp-keyring", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -14977,7 +15352,7 @@ dependencies = [ "schnellru", "sp-core 28.0.0", "sp-keyring", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -14988,14 +15363,14 @@ dependencies = [ "assert_matches", "async-trait", "bitvec", - "derive_more 0.99.17", + "derive_more 0.99.20", "futures", "futures-timer", "itertools 0.11.0", "kvdb-memorydb", "merlin", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-node-primitives", "polkadot-node-subsystem", "polkadot-node-subsystem-test-helpers", @@ -15009,7 +15384,7 @@ dependencies = [ "rand_core 0.6.4", "sc-keystore", "schnellru", - "schnorrkel 0.11.4", + "schnorrkel 0.11.5", "sp-application-crypto", "sp-consensus", "sp-consensus-babe", @@ -15019,7 +15394,7 @@ dependencies = [ "sp-keystore", "sp-runtime", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15045,7 +15420,7 @@ dependencies = [ "rand 0.8.5", "rand_core 0.6.4", "sc-keystore", - "schnorrkel 0.11.4", + "schnorrkel 0.11.5", "sp-consensus", "sp-consensus-babe", "sp-core 28.0.0", @@ -15064,7 +15439,7 @@ dependencies = [ "futures-timer", "kvdb-memorydb", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-erasure-coding", "polkadot-node-primitives", "polkadot-node-subsystem", @@ -15076,7 +15451,7 @@ dependencies = [ "sp-core 28.0.0", "sp-keyring", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15104,7 +15479,7 @@ dependencies = [ "sp-keyring", "sp-keystore", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15119,7 +15494,7 @@ dependencies = [ "polkadot-primitives", "polkadot-primitives-test-helpers", "sp-keystore", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", "wasm-timer", ] @@ -15181,14 +15556,14 @@ dependencies = [ "futures-timer", "kvdb-memorydb", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-node-primitives", "polkadot-node-subsystem", "polkadot-node-subsystem-test-helpers", "polkadot-node-subsystem-util", "polkadot-primitives", "sp-core 28.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15216,7 +15591,7 @@ dependencies = [ "sp-keyring", "sp-keystore", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15232,7 +15607,7 @@ dependencies = [ "polkadot-primitives", "sp-blockchain", "sp-inherents", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15252,7 +15627,7 @@ dependencies = [ "rstest", "sp-core 28.0.0", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15272,7 +15647,7 @@ dependencies = [ "polkadot-primitives-test-helpers", "sp-application-crypto", "sp-keystore", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15281,7 +15656,7 @@ name = "polkadot-node-core-pvf" version = "7.0.0" dependencies = [ "always-assert", - "array-bytes 6.2.2", + "array-bytes 6.2.3", "assert_matches", "criterion", "futures", @@ -15313,7 +15688,7 @@ dependencies = [ "tempfile", "test-parachain-adder", "test-parachain-halt", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tracing-gum", ] @@ -15362,7 +15737,7 @@ dependencies = [ "sp-io", "sp-tracing 16.0.0", "tempfile", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15431,7 +15806,7 @@ dependencies = [ "futures", "futures-timer", "http-body-util", - "hyper 1.6.0", + "hyper 1.7.0", "hyper-util", "parity-scale-codec", "polkadot-primitives", @@ -15453,7 +15828,7 @@ dependencies = [ "async-channel 1.9.0", "async-trait", "bitvec", - "derive_more 0.99.17", + "derive_more 0.99.20", "fatality", "futures", "hex", @@ -15467,7 +15842,7 @@ dependencies = [ "sc-network-types", "sp-runtime", "strum 0.26.3", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15483,14 +15858,14 @@ dependencies = [ "polkadot-parachain-primitives", "polkadot-primitives", "sc-keystore", - "schnorrkel 0.11.4", + "schnorrkel 0.11.5", "serde", "sp-application-crypto", "sp-consensus-babe", "sp-consensus-slots", "sp-keystore", "sp-maybe-compressed-blob", - "thiserror 1.0.65", + "thiserror 1.0.69", "zstd 0.12.4", ] @@ -15508,7 +15883,7 @@ version = "1.0.0" dependencies = [ "async-trait", "futures", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-erasure-coding", "polkadot-node-primitives", "polkadot-node-subsystem", @@ -15528,7 +15903,7 @@ name = "polkadot-node-subsystem-types" version = "7.0.0" dependencies = [ "async-trait", - "derive_more 0.99.17", + "derive_more 0.99.20", "fatality", "futures", "orchestra", @@ -15547,7 +15922,7 @@ dependencies = [ "sp-consensus-babe", "sp-runtime", "substrate-prometheus-endpoint", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -15562,7 +15937,7 @@ dependencies = [ "kvdb-shared-tests", "parity-db", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-erasure-coding", "polkadot-node-metrics", "polkadot-node-network-protocol", @@ -15580,7 +15955,7 @@ dependencies = [ "sp-core 28.0.0", "sp-keystore", "tempfile", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -15679,7 +16054,7 @@ dependencies = [ "substrate-frame-rpc-system", "substrate-prometheus-endpoint", "substrate-state-trie-migration-rpc", - "subxt-metadata 0.41.0", + "subxt-metadata 0.43.0", "tokio", "wait-timeout", ] @@ -15750,7 +16125,7 @@ name = "polkadot-parachain-primitives" version = "6.0.0" dependencies = [ "bounded-collections 0.3.2", - "derive_more 0.99.17", + "derive_more 0.99.20", "parity-scale-codec", "polkadot-core-primitives", "scale-info", @@ -15785,7 +16160,7 @@ dependencies = [ "sp-runtime", "sp-staking", "sp-std 14.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -16525,7 +16900,7 @@ dependencies = [ "pallet-transaction-payment-rpc-runtime-api", "parity-db", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "polkadot-approval-distribution", "polkadot-availability-bitfield-distribution", "polkadot-availability-distribution", @@ -16613,7 +16988,7 @@ dependencies = [ "staging-xcm", "substrate-prometheus-endpoint", "tempfile", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", "westend-runtime", "westend-runtime-constants", @@ -16649,7 +17024,7 @@ dependencies = [ "sp-keyring", "sp-keystore", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing-gum", ] @@ -16894,7 +17269,7 @@ version = "0.1.0" dependencies = [ "anyhow", "cumulus-zombienet-sdk-helpers", - "env_logger 0.11.3", + "env_logger 0.11.8", "log", "parity-scale-codec", "polkadot-primitives", @@ -16957,9 +17332,9 @@ dependencies = [ [[package]] name = "polkavm-common" -version = "0.9.0" +version = "0.18.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1d9428a5cfcc85c5d7b9fc4b6a18c4b802d0173d768182a51cc7751640f08b92" +checksum = "31ff33982a807d8567645d4784b9b5d7ab87bcb494f534a57cadd9012688e102" [[package]] name = "polkavm-common" @@ -16984,11 +17359,11 @@ dependencies = [ [[package]] name = "polkavm-derive" -version = "0.9.1" +version = "0.18.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ae8c4bea6f3e11cd89bb18bcdddac10bd9a24015399bd1c485ad68a985a19606" +checksum = "c2eb703f3b6404c13228402e98a5eae063fd16b8f58afe334073ec105ee4117e" dependencies = [ - "polkavm-derive-impl-macro 0.9.0", + "polkavm-derive-impl-macro 0.18.0", ] [[package]] @@ -17011,14 +17386,14 @@ dependencies = [ [[package]] name = "polkavm-derive-impl" -version = "0.9.0" +version = "0.18.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5c4fdfc49717fb9a196e74a5d28e0bc764eb394a2c803eb11133a31ac996c60c" +checksum = "2f2116a92e6e96220a398930f4c8a6cda1264206f3e2034fc9982bfd93f261f7" dependencies = [ - "polkavm-common 0.9.0", - "proc-macro2 1.0.95", + "polkavm-common 0.18.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -17028,9 +17403,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6069dc7995cde6e612b868a02ce48b54397c6d2582bd1b97b63aabbe962cd779" dependencies = [ "polkavm-common 0.26.0", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -17040,19 +17415,19 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8abdd1210d96b1dda9ac21199ec469448fd628cea102e2ff0e0df1667c4c3b5f" dependencies = [ "polkavm-common 0.27.0", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "polkavm-derive-impl-macro" -version = "0.9.0" +version = "0.18.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8ba81f7b5faac81e528eb6158a6f3c9e0bb1008e0ffa19653bc8dea925ecb429" +checksum = "48c16669ddc7433e34c1007d31080b80901e3e8e523cb9d4b441c3910cf9294b" dependencies = [ - "polkavm-derive-impl 0.9.0", - "syn 2.0.98", + "polkavm-derive-impl 0.18.1", + "syn 2.0.106", ] [[package]] @@ -17062,7 +17437,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "581d34cafec741dc5ffafbb341933c205b6457f3d76257a9d99fb56687219c91" dependencies = [ "polkavm-derive-impl 0.26.0", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -17072,7 +17447,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8a45173d70138aa1879892c50777ed0d8b0c8556f7678372f09fa1d89bbbddb4" dependencies = [ "polkavm-derive-impl 0.27.0", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -17082,10 +17457,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "beb896023e5bd89bba40311797d8d42490fa4a1fd5256c74820753c5722d1e67" dependencies = [ "dirs", - "gimli 0.31.1", + "gimli", "hashbrown 0.14.5", "log", - "object 0.36.7", + "object", "polkavm-common 0.26.0", "regalloc2 0.9.3", "rustc-demangle", @@ -17098,10 +17473,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "99fe3704d21e96c5d1e6a1b1a43ac57f9dce110d3331fbf8299e9f57d5884066" dependencies = [ "dirs", - "gimli 0.31.1", + "gimli", "hashbrown 0.14.5", "log", - "object 0.36.7", + "object", "polkavm-common 0.27.0", "regalloc2 0.9.3", "rustc-demangle", @@ -17137,16 +17512,16 @@ dependencies = [ [[package]] name = "polling" -version = "3.4.0" +version = "3.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "30054e72317ab98eddd8561db0f6524df3367636884b7b21b703e4b280a84a14" +checksum = "b5bd19146350fe804f7cb2669c851c03d69da628803dab0d98018142aaa5d829" dependencies = [ "cfg-if", "concurrent-queue", + "hermit-abi 0.5.2", "pin-project-lite", - "rustix 0.38.42", - "tracing", - "windows-sys 0.52.0", + "rustix 1.0.8", + "windows-sys 0.60.2", ] [[package]] @@ -17156,27 +17531,36 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8159bd90725d2df49889a078b54f4f79e87f1f8a8444194cdca81d38f5393abf" dependencies = [ "cpufeatures", - "opaque-debug 0.3.0", + "opaque-debug 0.3.1", "universal-hash", ] [[package]] name = "polyval" -version = "0.6.1" +version = "0.6.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d52cff9d1d4dee5fe6d03729099f4a310a41179e0a10dbf542039873f2e826fb" +checksum = "9d1fe60d06143b2430aa532c94cfe9e29783047f06c0d7fd359a9a51b729fa25" dependencies = [ "cfg-if", "cpufeatures", - "opaque-debug 0.3.0", + "opaque-debug 0.3.1", "universal-hash", ] [[package]] name = "portable-atomic" -version = "1.11.0" +version = "1.11.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f84267b20a16ea918e43c6a88433c2d54fa145c92a811b5b047ccbe153674483" + +[[package]] +name = "portable-atomic-util" +version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "350e9b48cbc6b0e028b0473b114454c6316e57336ee184ceab6e53f72c178b3e" +checksum = "d8a2f0d8d040d7848a709caf78912debcc3f33ee4b3cac47d73d1e1069e83507" +dependencies = [ + "portable-atomic", +] [[package]] name = "portpicker" @@ -17199,6 +17583,15 @@ dependencies = [ "serde", ] +[[package]] +name = "potential_utf" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e5a7c30837279ca13e7c867e9e40053bc68740f988cb07f7ca6df43cc734b585" +dependencies = [ + "zerovec", +] + [[package]] name = "powerfmt" version = "0.2.0" @@ -17218,42 +17611,44 @@ dependencies = [ "log", "nix 0.27.1", "once_cell", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "smallvec", "symbolic-demangle", "tempfile", - "thiserror 2.0.12", + "thiserror 2.0.16", ] [[package]] name = "ppv-lite86" -version = "0.2.17" +version = "0.2.21" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5b40af805b3121feab8a3c29f04d8ad262fa8e0561883e7653e024ae4479e6de" +checksum = "85eae3c4ed2f50dcfe72643da4befc30deadb458a9b590d720cde2f2b1e97da9" +dependencies = [ + "zerocopy", +] [[package]] name = "predicates" -version = "3.0.3" +version = "3.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "09963355b9f467184c04017ced4a2ba2d75cbcb4e7462690d388233253d4b1a9" +checksum = "a5d19ee57562043d37e82899fade9a22ebab7be9cef5026b07fda9cdd4293573" dependencies = [ "anstyle", "difflib", - "itertools 0.10.5", "predicates-core", ] [[package]] name = "predicates-core" -version = "1.0.6" +version = "1.0.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b794032607612e7abeb4db69adb4e33590fa6cf1149e95fd7cb00e634b92f174" +checksum = "727e462b119fe9c93fd0eb1429a5f7647394014cf3c04ab2c0350eeb09095ffa" [[package]] name = "predicates-tree" -version = "1.0.9" +version = "1.0.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "368ba315fb8c5052ab692e68a0eefec6ec57b23a36959c14496f0b0df2c0cecf" +checksum = "72dd2d6d381dfb73a193c7fca536518d7caee39fc8503f74e7dc0be0531b425c" dependencies = [ "predicates-core", "termtree", @@ -17261,9 +17656,9 @@ dependencies = [ [[package]] name = "pretty_assertions" -version = "1.4.0" +version = "1.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "af7cee1a6c8a5b9208b3cb1061f10c0cb689087b3d8ce85fb9d2dd7a29b6ba66" +checksum = "3ae130e2f271fbc2ac3a40fb1d07180839cdbbe443c7a27e1e3c13c5cac0116d" dependencies = [ "diff", "yansi", @@ -17271,12 +17666,21 @@ dependencies = [ [[package]] name = "prettyplease" -version = "0.2.12" +version = "0.2.37" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6c64d9ba0963cdcea2e1b2230fbae2bab30eb25a174be395c41e764bfb65dd62" +checksum = "479ca8adacdd7ce8f1fb39ce9ecccbfe93a3f1344b3d0d97f20bc0196208f62b" dependencies = [ - "proc-macro2 1.0.95", - "syn 2.0.98", + "proc-macro2 1.0.101", + "syn 2.0.106", +] + +[[package]] +name = "primeorder" +version = "0.13.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "353e1ca18966c16d9deb1c69278edbc5f194139612772bd9537af60ac231e1e6" +dependencies = [ + "elliptic-curve", ] [[package]] @@ -17313,31 +17717,31 @@ checksum = "a172e6cc603231f2cf004232eabcecccc0da53ba576ab286ef7baa0cfc7927ad" dependencies = [ "coarsetime", "crossbeam-queue", - "derive_more 0.99.17", + "derive_more 0.99.20", "futures", "futures-timer", "nanorand", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", ] [[package]] name = "proc-macro-crate" -version = "1.3.1" +version = "1.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7f4c021e1093a56626774e81216a4ce732a735e5bad4868a03f3ed65ca0c3919" +checksum = "e17d47ce914bf4de440332250b0edd23ce48c005f59fab39d3335866b114f11a" dependencies = [ - "once_cell", - "toml_edit 0.19.15", + "thiserror 1.0.69", + "toml 0.5.11", ] [[package]] name = "proc-macro-crate" -version = "3.1.0" +version = "3.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6d37c51ca738a55da99dc0c4a34860fd675453b8b36209178c2249bb13651284" +checksum = "edce586971a4dfaa28950c6f18ed55e0406c1ab88bbce2c6f6293a7aaba73d35" dependencies = [ - "toml_edit 0.21.0", + "toml_edit 0.22.27", ] [[package]] @@ -17347,7 +17751,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "da25490ff9892aab3fcf7c36f08cfb902dd3e71ca0f9f9517bea02a73a5ce38c" dependencies = [ "proc-macro-error-attr", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "syn 1.0.109", "version_check", @@ -17359,7 +17763,7 @@ version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a1be40180e52ecc98ad80b184934baf3d0d29f979574e439af5a55274b35f869" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "version_check", ] @@ -17370,7 +17774,7 @@ version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "96de42df36bb9bba5542fe9f1a054b8cc87e172759a1868aa05c1f3acc89dfc5" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", ] @@ -17381,26 +17785,20 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "11ec05c52be0a07b08061f7dd003e7d7092e0472bc731b4af7bb1ef876109802" dependencies = [ "proc-macro-error-attr2", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] -[[package]] -name = "proc-macro-hack" -version = "0.5.20+deprecated" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dc375e1527247fe1a97d8b7156678dfe7c1af2fc075c9a4db3690ecd2a148068" - [[package]] name = "proc-macro-warning" -version = "1.0.0" +version = "1.84.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9b698b0b09d40e9b7c1a47b132d66a8b54bcd20583d9b6d06e4535e383b4405c" +checksum = "75eea531cfcd120e0851a3f8aed42c4841f78c889eefafd96339c72677ae42c3" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -17414,9 +17812,9 @@ dependencies = [ [[package]] name = "proc-macro2" -version = "1.0.95" +version = "1.0.101" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "02b3e5e68a3a1a02aad3ec490a98007cbc13c37cbe84a3cd7b8e406d76e7f778" +checksum = "89ae43fd86e4158d6db51ad8e2b80f313af9cc74f5c0e03ccb87de09998732de" dependencies = [ "unicode-ident", ] @@ -17427,13 +17825,13 @@ version = "0.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "731e0d9356b0c25f16f33b5be79b1c57b562f141ebfcdb0ad8ac2c13a24293b4" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", "chrono", "flate2", "hex", "lazy_static", "procfs-core", - "rustix 0.38.42", + "rustix 0.38.44", ] [[package]] @@ -17442,23 +17840,23 @@ version = "0.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2d3554923a69f4ce04c4a754260c338f505ce22642d3830e049a399fc2059a29" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", "chrono", "hex", ] [[package]] name = "prometheus" -version = "0.13.3" +version = "0.13.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "449811d15fbdf5ceb5c1144416066429cf82316e2ec8ce0c1f6f8a02e7bbcf8c" +checksum = "3d33c28a30771f7f96db69893f78b857f7450d7e0237e9c8fc6427a81bae7ed1" dependencies = [ "cfg-if", "fnv", "lazy_static", "memchr", - "parking_lot 0.12.3", - "thiserror 1.0.65", + "parking_lot 0.12.4", + "thiserror 1.0.69", ] [[package]] @@ -17469,7 +17867,7 @@ checksum = "504ee9ff529add891127c4827eb481bd69dc0ebc72e9a682e187db4caa60c3ca" dependencies = [ "dtoa", "itoa", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "prometheus-client-derive-encode", ] @@ -17479,38 +17877,38 @@ version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "440f724eba9f6996b75d63681b0a92b06947f1457076d503a4d2e2c8f56442b8" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "prometheus-parse" -version = "0.2.4" +version = "0.2.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0c2aa5feb83bf4b2c8919eaf563f51dbab41183de73ba2353c0e03cd7b6bd892" +checksum = "811031bea65e5a401fb2e1f37d802cca6601e204ac463809a3189352d13b78a5" dependencies = [ "chrono", - "itertools 0.10.5", + "itertools 0.12.1", "once_cell", "regex", ] [[package]] name = "proptest" -version = "1.6.0" +version = "1.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "14cae93065090804185d3b75f0bf93b8eeda30c7a9b4a33d3bdb3988d6229e50" +checksum = "6fcdab19deb5195a31cf7726a210015ff1496ba1464fd42cb4f537b8b01b471f" dependencies = [ "bit-set", "bit-vec", - "bitflags 2.6.0", + "bitflags 2.9.3", "lazy_static", "num-traits", - "rand 0.8.5", - "rand_chacha 0.3.1", + "rand 0.9.2", + "rand_chacha 0.9.0", "rand_xorshift", - "regex-syntax 0.8.5", + "regex-syntax 0.8.6", "rusty-fork", "tempfile", "unarray", @@ -17548,22 +17946,21 @@ dependencies = [ [[package]] name = "prost-build" -version = "0.13.2" +version = "0.13.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f8650aabb6c35b860610e9cff5dc1af886c9e25073b7b1712a68972af4281302" +checksum = "be769465445e8c1474e9c5dac2018218498557af32d9ed057325ec9a41ae81bf" dependencies = [ - "bytes", "heck 0.5.0", - "itertools 0.13.0", + "itertools 0.14.0", "log", "multimap", "once_cell", - "petgraph", + "petgraph 0.7.1", "prettyplease", "prost 0.13.5", "prost-types", "regex", - "syn 2.0.98", + "syn 2.0.106", "tempfile", ] @@ -17575,7 +17972,7 @@ checksum = "e5d2d8d10f3c6ded6da8b05b5fb3b8a5082514344d56c9f871412d29b4e075b4" dependencies = [ "anyhow", "itertools 0.10.5", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "syn 1.0.109", ] @@ -17588,9 +17985,9 @@ checksum = "81bddcdb20abf9501610992b6759a4c888aef7d1a7247ef75e2404275ac24af1" dependencies = [ "anyhow", "itertools 0.12.1", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -17601,16 +17998,16 @@ checksum = "8a56d757972c98b346a9b766e3f02746cde6dd1cd1d1d563472929fdd74bec4d" dependencies = [ "anyhow", "itertools 0.14.0", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "prost-types" -version = "0.13.2" +version = "0.13.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "60caa6738c7369b940c3d49246a8d1749323674c65cb13010134f5c9bad5b519" +checksum = "52c2c1bf36ddb1a1c396b3601a3cec27c2462e45f07c386894ec3ccf5332bd16" dependencies = [ "prost 0.13.5", ] @@ -17633,9 +18030,9 @@ version = "35.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "938543690519c20c3a480d20a8efcc8e69abeb44093ab1df4e7c1f81f26c677a" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -17651,35 +18048,33 @@ dependencies = [ "prost 0.11.9", "reqwest", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", "url", "winapi", ] [[package]] name = "pyroscope_pprofrs" -version = "0.2.8" +version = "0.2.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "614a25777053da6bdca9d84a67892490b5a57590248dbdee3d7bf0716252af70" +checksum = "50da7a8950c542357de489aa9ee628f46322b1beaac1f4fa3313bcdebe85b4ea" dependencies = [ "log", "pprof2", "pyroscope", - "thiserror 1.0.65", ] [[package]] name = "quanta" -version = "0.11.1" +version = "0.12.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a17e662a7a8291a865152364c20c7abc5e60486ab2001e8ec10b24862de0b9ab" +checksum = "f3ab5a9d756f0d97bdc89019bd2e4ea098cf9cde50ee7564dde6b81ccc8f06c7" dependencies = [ "crossbeam-utils", "libc", - "mach2", "once_cell", "raw-cpuid", - "wasi 0.11.0+wasi-snapshot-preview1", + "wasi 0.11.1+wasi-snapshot-preview1", "web-sys", "winapi", ] @@ -17708,7 +18103,7 @@ dependencies = [ "asynchronous-codec 0.7.0", "bytes", "quick-protobuf", - "thiserror 1.0.65", + "thiserror 1.0.69", "unsigned-varint 0.8.0", ] @@ -17720,7 +18115,7 @@ checksum = "5253a3a0d56548d5b0be25414171dc780cc6870727746d05bd2bde352eee96c5" dependencies = [ "ahash", "hashbrown 0.13.2", - "parking_lot 0.12.3", + "parking_lot 0.12.4", ] [[package]] @@ -17736,51 +18131,58 @@ dependencies = [ [[package]] name = "quinn" -version = "0.11.5" +version = "0.11.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8c7c5fdde3cdae7203427dc4f0a68fe0ed09833edc525a03456b153b79828684" +checksum = "626214629cda6781b6dc1d316ba307189c85ba657213ce642d9c77670f8202c8" dependencies = [ "bytes", + "cfg_aliases 0.2.1", "futures-io", "pin-project-lite", "quinn-proto", "quinn-udp", "rustc-hash 2.1.1", - "rustls 0.23.18", - "socket2 0.5.9", - "thiserror 1.0.65", + "rustls 0.23.31", + "socket2 0.5.10", + "thiserror 2.0.16", "tokio", "tracing", + "web-time", ] [[package]] name = "quinn-proto" -version = "0.11.8" +version = "0.11.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fadfaed2cd7f389d0161bb73eeb07b7b78f8691047a6f3e73caaeae55310a4a6" +checksum = "49df843a9161c85bb8aae55f101bc0bac8bcafd637a620d9122fd7e0b2f7422e" dependencies = [ "bytes", - "rand 0.8.5", - "ring 0.17.8", + "getrandom 0.3.3", + "lru-slab", + "rand 0.9.2", + "ring 0.17.14", "rustc-hash 2.1.1", - "rustls 0.23.18", + "rustls 0.23.31", + "rustls-pki-types", "slab", - "thiserror 1.0.65", + "thiserror 2.0.16", "tinyvec", "tracing", + "web-time", ] [[package]] name = "quinn-udp" -version = "0.5.4" +version = "0.5.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8bffec3605b73c6f1754535084a85229fa8a30f86014e6c81aeec4abb68b0285" +checksum = "fcebb1209ee276352ef14ff8732e24cc2b02bbac986cd74a4c81bcb2f9881970" dependencies = [ + "cfg_aliases 0.2.1", "libc", "once_cell", - "socket2 0.5.9", + "socket2 0.5.10", "tracing", - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] @@ -17798,9 +18200,15 @@ version = "1.0.40" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1885c039570dc00dcb4ff087a89e185fd56bae234ddc7f056a945bf36467248d" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", ] +[[package]] +name = "r-efi" +version = "5.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "69cdb34c158ceb288df11e18b4bd39de994f6657d83847bdffdbd7f346754b0f" + [[package]] name = "radium" version = "0.7.0" @@ -17820,14 +18228,13 @@ dependencies = [ [[package]] name = "rand" -version = "0.9.0" +version = "0.9.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3779b94aeb87e8bd4e834cee3650289ee9e0d5677f976ecdb6d219e5f4f6cd94" +checksum = "6db2770f06117d490610c7488547d543617b21bfa07796d7a12f6f1bd53850d1" dependencies = [ "rand_chacha 0.9.0", - "rand_core 0.9.1", + "rand_core 0.9.3", "serde", - "zerocopy 0.8.20", ] [[package]] @@ -17847,7 +18254,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d3022b5f1df60f26e1ffddd6c66e8aa15de382ae63b3a0c1bfc0e4d3e3f325cb" dependencies = [ "ppv-lite86", - "rand_core 0.9.1", + "rand_core 0.9.3", ] [[package]] @@ -17856,18 +18263,17 @@ version = "0.6.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c" dependencies = [ - "getrandom 0.2.10", + "getrandom 0.2.16", ] [[package]] name = "rand_core" -version = "0.9.1" +version = "0.9.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a88e0da7a2c97baa202165137c158d0a2e824ac465d13d81046727b34cb247d3" +checksum = "99d9a13982dcf210057a8a78572b2217b667c3beacbf3a0d8b454f6f82837d38" dependencies = [ - "getrandom 0.3.1", + "getrandom 0.3.3", "serde", - "zerocopy 0.8.20", ] [[package]] @@ -17891,20 +18297,20 @@ dependencies = [ [[package]] name = "rand_xorshift" -version = "0.3.0" +version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d25bf25ec5ae4a3f1b92f929810509a2f53d7dca2f50b794ff57e3face536c8f" +checksum = "513962919efc330f829edb2535844d1b912b0fbe2ca165d613e4e8788bb05a5a" dependencies = [ - "rand_core 0.6.4", + "rand_core 0.9.3", ] [[package]] name = "raw-cpuid" -version = "10.7.0" +version = "11.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6c297679cb867470fa8c9f67dbba74a78d78e3e98d7cf2b08d6d71540f797332" +checksum = "c6df7ab838ed27997ba19a4664507e6f82b41fe6e20be42929332156e5e85146" dependencies = [ - "bitflags 1.3.2", + "bitflags 2.9.3", ] [[package]] @@ -17915,9 +18321,9 @@ checksum = "60a357793950651c4ed0f3f52338f53b2f809f32d83a07f72909fa13e4c6c1e3" [[package]] name = "rayon" -version = "1.10.0" +version = "1.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b418a60154510ca1a002a752ca9714984e21e4241e804d32555251faf8b78ffa" +checksum = "368f01d005bf8fd9b1206fb6fa653e6c4a81ceb1466406b81792d87c5677a58f" dependencies = [ "either", "rayon-core", @@ -17925,9 +18331,9 @@ dependencies = [ [[package]] name = "rayon-core" -version = "1.12.1" +version = "1.13.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1465873a3dfdaa8ae7cb14b4383657caab0b3e8a0aa9ae8e04b044854c8dfce2" +checksum = "22e18b0f0062d30d4230b2e85ff77fdfe4326feb054b9783a3460d8435c8ab91" dependencies = [ "crossbeam-deque", "crossbeam-utils", @@ -17976,31 +18382,22 @@ dependencies = [ [[package]] name = "redox_syscall" -version = "0.3.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "567664f262709473930a4bf9e51bf2ebf3348f2e748ccc50dea20646858f8f29" -dependencies = [ - "bitflags 1.3.2", -] - -[[package]] -name = "redox_syscall" -version = "0.5.8" +version = "0.5.17" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "03a862b389f93e68874fbf580b9de08dd02facb9a788ebadaf4a3fd33cf58834" +checksum = "5407465600fb0548f1442edf71dd20683c6ed326200ace4b1ef0763521bb3b77" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", ] [[package]] name = "redox_users" -version = "0.4.3" +version = "0.4.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b033d837a7cf162d7993aded9304e30a83213c648b6e389db233191f891e5c2b" +checksum = "ba009ff324d1fc1b900bd1fdb31564febe58a8ccc8a6fdbb93b543d33b13ca43" dependencies = [ - "getrandom 0.2.10", - "redox_syscall 0.2.16", - "thiserror 1.0.65", + "getrandom 0.2.16", + "libredox", + "thiserror 1.0.69", ] [[package]] @@ -18009,30 +18406,30 @@ version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "87413ebb313323d431e85d0afc5a68222aaed972843537cbfe5f061cf1b4bcab" dependencies = [ - "derive_more 0.99.17", + "derive_more 0.99.20", "fs-err", "static_init", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] name = "ref-cast" -version = "1.0.23" +version = "1.0.24" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ccf0a6f84d5f1d581da8b41b47ec8600871962f2a528115b542b362d4b744931" +checksum = "4a0ae411dbe946a674d89546582cea4ba2bb8defac896622d6496f14c23ba5cf" dependencies = [ "ref-cast-impl", ] [[package]] name = "ref-cast-impl" -version = "1.0.23" +version = "1.0.24" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bcc303e793d3734489387d205e9b186fac9c6cfacedd98cbb2e8a5943595f3e6" +checksum = "1165225c21bff1f3bbce98f5a1f889949bc902d3575308cc7b0de30b4f6d27c7" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -18056,7 +18453,7 @@ checksum = "5216b1837de2149f8bc8e6d5f88a9326b63b8c836ed58ce4a0a29ec736a59734" dependencies = [ "allocator-api2", "bumpalo", - "hashbrown 0.15.3", + "hashbrown 0.15.5", "log", "rustc-hash 2.1.1", "smallvec", @@ -18064,14 +18461,14 @@ dependencies = [ [[package]] name = "regex" -version = "1.11.1" +version = "1.11.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b544ef1b4eac5dc2db33ea63606ae9ffcfac26c1416a2806ae0bf5f56b201191" +checksum = "23d7fd106d8c02486a8d64e778353d1cffe08ce79ac2e82f540c86d0facf6912" dependencies = [ "aho-corasick", "memchr", - "regex-automata 0.4.8", - "regex-syntax 0.8.5", + "regex-automata 0.4.10", + "regex-syntax 0.8.6", ] [[package]] @@ -18085,19 +18482,13 @@ dependencies = [ [[package]] name = "regex-automata" -version = "0.3.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fed1ceff11a1dddaee50c9dc8e4938bd106e9d89ae372f192311e7da498e3b69" - -[[package]] -name = "regex-automata" -version = "0.4.8" +version = "0.4.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "368758f23274712b504848e9d5a6f010445cc8b87a7cdb4d7cbee666c1288da3" +checksum = "6b9458fa0bfeeac22b5ca447c63aaf45f28439a709ccd244698632f9aa6394d6" dependencies = [ "aho-corasick", "memchr", - "regex-syntax 0.8.5", + "regex-syntax 0.8.6", ] [[package]] @@ -18108,15 +18499,15 @@ checksum = "f162c6dd7b008981e4d40210aca20b4bd0f9b60ca9271061b07f78537722f2e1" [[package]] name = "regex-syntax" -version = "0.8.5" +version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2b15c43186be67a4fd63bee50d0303afffcef381492ebe2c5d87f324e1b8815c" +checksum = "caf4aa5b0f434c91fe5c7f1ecb6a5ece2130b02ad2a590589dda5146df959001" [[package]] name = "relative-path" -version = "1.9.2" +version = "1.9.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e898588f33fdd5b9420719948f9f2a32c922a246964576f71ba7f24f80610fbc" +checksum = "ba39f3699c378cd8970968dcbff9c43159ea4cfbd88d43c00b22f2ef10a435d2" [[package]] name = "relay-substrate-client" @@ -18154,7 +18545,7 @@ dependencies = [ "sp-trie", "sp-version", "staging-xcm", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -18172,13 +18563,13 @@ dependencies = [ "jsonpath_lib", "log", "num-traits", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "serde_json", "sp-runtime", "sp-tracing 16.0.0", "substrate-prometheus-endpoint", "sysinfo", - "thiserror 1.0.65", + "thiserror 1.0.69", "time", "tokio", ] @@ -18200,9 +18591,9 @@ dependencies = [ [[package]] name = "reqwest" -version = "0.12.9" +version = "0.12.23" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a77c62af46e79de0a562e1a9849205ffcb7fc1238876e9bd743357570e04046f" +checksum = "d429f34c8092b2d42c7c93cec323bb4adeb7c67698f70839adec842ec10c7ceb" dependencies = [ "base64 0.22.1", "bytes", @@ -18210,52 +18601,45 @@ dependencies = [ "futures-channel", "futures-core", "futures-util", - "h2 0.4.5", - "http 1.1.0", - "http-body 1.0.0", + "h2 0.4.12", + "http 1.3.1", + "http-body 1.0.1", "http-body-util", - "hyper 1.6.0", - "hyper-rustls 0.27.3", + "hyper 1.7.0", + "hyper-rustls 0.27.7", "hyper-tls", "hyper-util", - "ipnet", "js-sys", "log", "mime", "native-tls", - "once_cell", "percent-encoding", "pin-project-lite", "quinn", - "rustls 0.23.18", - "rustls-pemfile 2.0.0", + "rustls 0.23.31", "rustls-pki-types", "serde", "serde_json", "serde_urlencoded", "sync_wrapper", - "system-configuration 0.6.1", "tokio", "tokio-native-tls", - "tokio-rustls 0.26.0", + "tokio-rustls 0.26.2", + "tower 0.5.2", + "tower-http 0.6.6", "tower-service", "url", "wasm-bindgen", "wasm-bindgen-futures", "web-sys", - "webpki-roots 0.26.3", - "windows-registry", + "webpki-roots 1.0.2", ] [[package]] name = "resolv-conf" -version = "0.7.0" +version = "0.7.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "52e44394d2086d010551b14b53b1f24e31647570cd1deb0379e2c21b329aba00" -dependencies = [ - "hostname", - "quick-error", -] +checksum = "95325155c684b1c89f7765e30bc1c42e4a6da51ca513615660cb8a62ef9a88e3" [[package]] name = "revive-dev-node" @@ -18274,13 +18658,202 @@ dependencies = [ name = "revive-dev-runtime" version = "0.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "parity-scale-codec", "polkadot-sdk 0.1.0", "scale-info", "serde_json", ] +[[package]] +name = "revm" +version = "27.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5e6bf82101a1ad8a2b637363a37aef27f88b4efc8a6e24c72bf5f64923dc5532" +dependencies = [ + "revm-bytecode", + "revm-context", + "revm-context-interface", + "revm-database", + "revm-database-interface", + "revm-handler", + "revm-inspector", + "revm-interpreter", + "revm-precompile", + "revm-primitives", + "revm-state", +] + +[[package]] +name = "revm-bytecode" +version = "6.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "66c52031b73cae95d84cd1b07725808b5fd1500da3e5e24574a3b2dc13d9f16d" +dependencies = [ + "bitvec", + "phf", + "revm-primitives", + "serde", +] + +[[package]] +name = "revm-context" +version = "8.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9cd508416a35a4d8a9feaf5ccd06ac6d6661cd31ee2dc0252f9f7316455d71f9" +dependencies = [ + "cfg-if", + "derive-where", + "revm-bytecode", + "revm-context-interface", + "revm-database-interface", + "revm-primitives", + "revm-state", + "serde", +] + +[[package]] +name = "revm-context-interface" +version = "9.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dc90302642d21c8f93e0876e201f3c5f7913c4fcb66fb465b0fd7b707dfe1c79" +dependencies = [ + "alloy-eip2930", + "alloy-eip7702", + "auto_impl", + "either", + "revm-database-interface", + "revm-primitives", + "revm-state", + "serde", +] + +[[package]] +name = "revm-database" +version = "7.0.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "39a276ed142b4718dcf64bc9624f474373ed82ef20611025045c3fb23edbef9c" +dependencies = [ + "alloy-eips", + "revm-bytecode", + "revm-database-interface", + "revm-primitives", + "revm-state", + "serde", +] + +[[package]] +name = "revm-database-interface" +version = "7.0.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8c523c77e74eeedbac5d6f7c092e3851dbe9c7fec6f418b85992bd79229db361" +dependencies = [ + "auto_impl", + "either", + "revm-primitives", + "revm-state", + "serde", +] + +[[package]] +name = "revm-handler" +version = "8.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1529c8050e663be64010e80ec92bf480315d21b1f2dbf65540028653a621b27d" +dependencies = [ + "auto_impl", + "derive-where", + "revm-bytecode", + "revm-context", + "revm-context-interface", + "revm-database-interface", + "revm-interpreter", + "revm-precompile", + "revm-primitives", + "revm-state", + "serde", +] + +[[package]] +name = "revm-inspector" +version = "8.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f78db140e332489094ef314eaeb0bd1849d6d01172c113ab0eb6ea8ab9372926" +dependencies = [ + "auto_impl", + "either", + "revm-context", + "revm-database-interface", + "revm-handler", + "revm-interpreter", + "revm-primitives", + "revm-state", + "serde", + "serde_json", +] + +[[package]] +name = "revm-interpreter" +version = "24.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ff9d7d9d71e8a33740b277b602165b6e3d25fff091ba3d7b5a8d373bf55f28a7" +dependencies = [ + "revm-bytecode", + "revm-context-interface", + "revm-primitives", + "serde", +] + +[[package]] +name = "revm-precompile" +version = "25.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4cee3f336b83621294b4cfe84d817e3eef6f3d0fce00951973364cc7f860424d" +dependencies = [ + "ark-bls12-381 0.5.0", + "ark-bn254", + "ark-ec 0.5.0", + "ark-ff 0.5.0", + "ark-serialize 0.5.0", + "arrayref", + "aurora-engine-modexp", + "c-kzg", + "cfg-if", + "k256", + "libsecp256k1", + "once_cell", + "p256", + "revm-primitives", + "ripemd", + "rug", + "secp256k1 0.31.1", + "sha2 0.10.9", +] + +[[package]] +name = "revm-primitives" +version = "20.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5aa29d9da06fe03b249b6419b33968ecdf92ad6428e2f012dc57bcd619b5d94e" +dependencies = [ + "alloy-primitives", + "num_enum", + "once_cell", + "serde", +] + +[[package]] +name = "revm-state" +version = "7.0.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f64fbacb86008394aaebd3454f9643b7d5a782bd251135e17c5b33da592d84d" +dependencies = [ + "bitflags 2.9.3", + "revm-bytecode", + "revm-primitives", + "serde", +] + [[package]] name = "rfc6979" version = "0.4.0" @@ -18288,7 +18861,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f8dd2a808d456c4a54e300a23e9f5a67e122c3024119acbfd73e3bf664491cb2" dependencies = [ "hmac 0.12.1", - "subtle 2.5.0", + "subtle 2.6.1", ] [[package]] @@ -18308,15 +18881,14 @@ dependencies = [ [[package]] name = "ring" -version = "0.17.8" +version = "0.17.14" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c17fa4cb658e3583423e915b9f3acc01cceaee1860e33d59ebae66adc3a2dc0d" +checksum = "a4689e6c2294d81e88dc6261c768b63bc4fcdb852be6d1352498b114f61383b7" dependencies = [ "cc", "cfg-if", - "getrandom 0.2.10", + "getrandom 0.2.16", "libc", - "spin 0.9.8", "untrusted 0.9.0", "windows-sys 0.52.0", ] @@ -18585,20 +19157,20 @@ checksum = "afab94fb28594581f62d981211a9a4d53cc8130bbcbbb89a0440d9b8e81a7746" [[package]] name = "rpassword" -version = "7.2.0" +version = "7.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6678cf63ab3491898c0d021b493c94c9b221d91295294a2a5746eacbe5928322" +checksum = "66d4c8b64f049c6721ec8ccec37ddfc3d641c4a7fca57e8f2a89de509c73df39" dependencies = [ "libc", "rtoolbox", - "winapi", + "windows-sys 0.59.0", ] [[package]] name = "rsa" -version = "0.9.5" +version = "0.9.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "af6c4b23d99685a1408194da11270ef8e9809aff951cc70ec9b17350b087e474" +checksum = "78928ac1ed176a5ca1d17e578a1825f3d81ca54cf41053a592584b020cfd691b" dependencies = [ "const-oid", "digest 0.10.7", @@ -18610,7 +19182,7 @@ dependencies = [ "rand_core 0.6.4", "signature", "spki", - "subtle 2.5.0", + "subtle 2.6.1", "zeroize", ] @@ -18623,7 +19195,7 @@ dependencies = [ "futures", "futures-timer", "rstest_macros", - "rustc_version 0.4.0", + "rustc_version 0.4.1", ] [[package]] @@ -18634,45 +19206,60 @@ checksum = "d428f8247852f894ee1be110b375111b586d4fa431f6c46e64ba5a0dcccbe605" dependencies = [ "cfg-if", "glob", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "regex", "relative-path", - "rustc_version 0.4.0", - "syn 2.0.98", + "rustc_version 0.4.1", + "syn 2.0.106", "unicode-ident", ] [[package]] name = "rtnetlink" -version = "0.10.1" +version = "0.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "322c53fd76a18698f1c27381d58091de3a043d356aa5bd0d510608b565f469a0" +checksum = "7a552eb82d19f38c3beed3f786bd23aa434ceb9ac43ab44419ca6d67a7e186c0" dependencies = [ "futures", "log", + "netlink-packet-core", "netlink-packet-route", + "netlink-packet-utils", "netlink-proto", - "nix 0.24.3", - "thiserror 1.0.65", + "netlink-sys", + "nix 0.26.4", + "thiserror 1.0.69", "tokio", ] [[package]] name = "rtoolbox" -version = "0.0.1" +version = "0.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "034e22c514f5c0cb8a10ff341b9b048b5ceb21591f31c8f44c43b960f9b3524a" +checksum = "a7cc970b249fbe527d6e02e0a227762c9108b2f49d81094fe357ffc6d14d7f6f" dependencies = [ "libc", - "winapi", + "windows-sys 0.52.0", +] + +[[package]] +name = "rug" +version = "1.28.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "58ad2e973fe3c3214251a840a621812a4f40468da814b1a3d6947d433c2af11f" +dependencies = [ + "az", + "gmp-mpfr-sys", + "libc", + "libm", ] [[package]] name = "ruint" -version = "1.15.0" +version = "1.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "11256b5fe8c68f56ac6f39ef0720e592f33d2367a4782740d9c9142e889c7fb4" +checksum = "9ecb38f82477f20c5c3d62ef52d7c4e536e38ea9b73fb570a20c5cae0e14bcf6" dependencies = [ "alloy-rlp", "ark-ff 0.3.0", @@ -18687,7 +19274,7 @@ dependencies = [ "primitive-types 0.12.2", "proptest", "rand 0.8.5", - "rand 0.9.0", + "rand 0.9.2", "rlp 0.5.2", "ruint-macro", "serde", @@ -18703,9 +19290,9 @@ checksum = "48fd7bd8a6377e15ad9d42a8ec25371b94ddc67abe7c8b9127bec79bebaaae18" [[package]] name = "rustc-demangle" -version = "0.1.23" +version = "0.1.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76" +checksum = "56f7d92ca342cea22a06f2121d944b4fd82af56988c270852495420f961d4ace" [[package]] name = "rustc-hash" @@ -18745,11 +19332,11 @@ dependencies = [ [[package]] name = "rustc_version" -version = "0.4.0" +version = "0.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366" +checksum = "cfcb3a22ef46e85b45de6ee7e79d063319ebb6594faafcf1c225ea92ab6e9b92" dependencies = [ - "semver 1.0.18", + "semver 1.0.26", ] [[package]] @@ -18758,14 +19345,14 @@ version = "4.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "faf0c4a6ece9950b9abdb62b1cfcf2a68b3b67a10ba445b3bb85be2a293d0632" dependencies = [ - "nom", + "nom 7.1.3", ] [[package]] name = "rustix" -version = "0.37.23" +version = "0.37.28" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4d69718bf81c6127a49dc64e44a742e8bb9213c0ff8869a22c308f84c1d4ab06" +checksum = "519165d378b97752ca44bbe15047d5d3409e875f39327546b42ac81d7e18c1b6" dependencies = [ "bitflags 1.3.2", "errno", @@ -18777,14 +19364,14 @@ dependencies = [ [[package]] name = "rustix" -version = "0.38.42" +version = "0.38.44" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f93dc38ecbab2eb790ff964bb77fa94faf256fd3e73285fd7ba0903b76bedb85" +checksum = "fdb5bc1ae2baa591800df16c9ca78619bf65c0488b41b96ccec5d11220d8c154" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", "errno", "libc", - "linux-raw-sys 0.4.14", + "linux-raw-sys 0.4.15", "windows-sys 0.59.0", ] @@ -18794,37 +19381,37 @@ version = "1.0.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "11181fbabf243db407ef8df94a6ce0b2f9a733bd8be4ad02b4eda9602296cac8" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", "errno", "libc", "linux-raw-sys 0.9.4", - "windows-sys 0.59.0", + "windows-sys 0.60.2", ] [[package]] name = "rustls" -version = "0.21.7" +version = "0.21.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cd8d6c9f025a446bc4d18ad9632e69aec8f287aa84499ee335599fabd20c3fd8" +checksum = "3f56a14d1f48b391359b22f731fd4bd7e43c97f3c50eee276f3aa09c94784d3e" dependencies = [ "log", - "ring 0.16.20", - "rustls-webpki 0.101.4", + "ring 0.17.14", + "rustls-webpki 0.101.7", "sct", ] [[package]] name = "rustls" -version = "0.23.18" +version = "0.23.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9c9cc1d47e243d655ace55ed38201c19ae02c148ae56412ab8750e8f0166ab7f" +checksum = "c0ebcbd2f03de0fc1122ad9bb24b127a5a6cd51d72604a3f3c50ac459762b6cc" dependencies = [ "log", "once_cell", - "ring 0.17.8", + "ring 0.17.14", "rustls-pki-types", - "rustls-webpki 0.102.8", - "subtle 2.5.0", + "rustls-webpki 0.103.4", + "subtle 2.6.1", "zeroize", ] @@ -18835,115 +19422,95 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a9aace74cb666635c918e9c12bc0d348266037aa8eb599b5cba565709a8dff00" dependencies = [ "openssl-probe", - "rustls-pemfile 1.0.3", - "schannel", - "security-framework", -] - -[[package]] -name = "rustls-native-certs" -version = "0.7.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8f1fb85efa936c42c6d5fc28d2629bb51e4b2f4b8a5211e297d599cc5a093792" -dependencies = [ - "openssl-probe", - "rustls-pemfile 2.0.0", - "rustls-pki-types", + "rustls-pemfile", "schannel", - "security-framework", + "security-framework 2.11.1", ] [[package]] name = "rustls-native-certs" -version = "0.8.0" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fcaf18a4f2be7326cd874a5fa579fae794320a0f388d365dca7e480e55f83f8a" +checksum = "7fcff2dd52b58a8d98a70243663a0d234c4e2b79235637849d15913394a247d3" dependencies = [ "openssl-probe", - "rustls-pemfile 2.0.0", "rustls-pki-types", "schannel", - "security-framework", + "security-framework 3.3.0", ] [[package]] name = "rustls-pemfile" -version = "1.0.3" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2d3987094b1d07b653b7dfdc3f70ce9a1da9c51ac18c1b06b662e4f9a0e9f4b2" +checksum = "1c74cae0a4cf6ccbbf5f359f08efdf8ee7e1dc532573bf0db71968cb56b1448c" dependencies = [ "base64 0.21.7", ] [[package]] -name = "rustls-pemfile" -version = "2.0.0" +name = "rustls-pki-types" +version = "1.12.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "35e4980fa29e4c4b212ffb3db068a564cbf560e51d3944b7c88bd8bf5bec64f4" +checksum = "229a4a4c221013e7e1f1a043678c5cc39fe5171437c88fb47151a21e6f5b5c79" dependencies = [ - "base64 0.21.7", - "rustls-pki-types", + "web-time", + "zeroize", ] -[[package]] -name = "rustls-pki-types" -version = "1.10.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "16f1201b3c9a7ee8039bcadc17b7e605e2945b27eee7631788c1bd2b0643674b" - [[package]] name = "rustls-platform-verifier" -version = "0.3.1" +version = "0.5.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b5f0d26fa1ce3c790f9590868f0109289a044acb954525f933e2aa3b871c157d" +checksum = "19787cda76408ec5404443dc8b31795c87cd8fec49762dc75fa727740d34acc1" dependencies = [ - "core-foundation", + "core-foundation 0.10.1", "core-foundation-sys", "jni", "log", "once_cell", - "rustls 0.23.18", - "rustls-native-certs 0.7.0", + "rustls 0.23.31", + "rustls-native-certs 0.8.1", "rustls-platform-verifier-android", - "rustls-webpki 0.102.8", - "security-framework", + "rustls-webpki 0.103.4", + "security-framework 3.3.0", "security-framework-sys", - "webpki-roots 0.26.3", - "winapi", + "webpki-root-certs 0.26.11", + "windows-sys 0.59.0", ] [[package]] name = "rustls-platform-verifier-android" -version = "0.1.0" +version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "84e217e7fdc8466b5b35d30f8c0a30febd29173df4a3a0c2115d306b9c4117ad" +checksum = "f87165f0995f63a9fbeea62b64d10b4d9d8e78ec6d7d51fb2125fda7bb36788f" [[package]] name = "rustls-webpki" -version = "0.101.4" +version = "0.101.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7d93931baf2d282fff8d3a532bbfd7653f734643161b87e3e01e59a04439bf0d" +checksum = "8b6275d1ee7a1cd780b64aca7726599a1dbc893b1e64144529e55c3c2f745765" dependencies = [ - "ring 0.16.20", - "untrusted 0.7.1", + "ring 0.17.14", + "untrusted 0.9.0", ] [[package]] name = "rustls-webpki" -version = "0.102.8" +version = "0.103.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "64ca1bc8749bd4cf37b5ce386cc146580777b4e8572c7b97baf22c83f444bee9" +checksum = "0a17884ae0c1b773f1ccd2bd4a8c72f16da897310a98b0e84bf349ad5ead92fc" dependencies = [ - "ring 0.17.8", + "ring 0.17.14", "rustls-pki-types", "untrusted 0.9.0", ] [[package]] name = "rustversion" -version = "1.0.17" +version = "1.0.22" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "955d28af4278de8121b7ebeb796b6a45735dc01436d898801014aced2773a3d6" +checksum = "b39cdef0fa800fc44525c84ccb54a029961a8215f9619753635a9c0d2538d46d" [[package]] name = "rusty-fork" @@ -18965,7 +19532,7 @@ checksum = "ac3ffab8f9715a0d455df4bbb9d21e91135aab3cd3ca187af0cd0c3c3f868fdc" dependencies = [ "byteorder", "thiserror-core", - "twox-hash", + "twox-hash 1.6.3", ] [[package]] @@ -18975,9 +19542,15 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5174a470eeb535a721ae9fdd6e291c2411a906b96592182d05217591d5c5cf7b" dependencies = [ "byteorder", - "derive_more 0.99.17", + "derive_more 0.99.20", ] +[[package]] +name = "ruzstd" +version = "0.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3640bec8aad418d7d03c72ea2de10d5c646a598f9883c7babc160d91e3c1b26c" + [[package]] name = "rw-stream-sink" version = "0.4.0" @@ -18991,9 +19564,9 @@ dependencies = [ [[package]] name = "ryu" -version = "1.0.15" +version = "1.0.20" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1ad4cc8da4ef723ed60bced201181d83791ad433213d8c24efffda1eec85d741" +checksum = "28d3b2b1366ec20994f1fd18c3c594f05c5dd4bc44d8bb0c1c632c8d6829481f" [[package]] name = "safe-mix" @@ -19006,9 +19579,9 @@ dependencies = [ [[package]] name = "safe_arch" -version = "0.7.1" +version = "0.7.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f398075ce1e6a179b46f51bd88d0598b92b00d3551f1a2d4ac49e771b56ac354" +checksum = "96b02de82ddbe1b636e6170c21be622223aea188ef2e139be0a5b219ec215323" dependencies = [ "bytemuck", ] @@ -19038,7 +19611,7 @@ dependencies = [ "log", "sp-core 28.0.0", "sp-wasm-interface 20.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -19073,7 +19646,7 @@ dependencies = [ "substrate-prometheus-endpoint", "substrate-test-runtime-client", "tempfile", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -19084,7 +19657,7 @@ dependencies = [ "futures", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-block-builder", "sc-client-api", "sc-proposer-metrics", @@ -19122,10 +19695,10 @@ dependencies = [ name = "sc-chain-spec" version = "28.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "clap", "docify", - "memmap2 0.9.3", + "memmap2 0.9.8", "parity-scale-codec", "pretty_assertions", "regex", @@ -19154,17 +19727,17 @@ dependencies = [ name = "sc-chain-spec-derive" version = "11.0.0" dependencies = [ - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "sc-cli" version = "0.36.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "chrono", "clap", "fdlimit", @@ -19200,7 +19773,7 @@ dependencies = [ "sp-tracing 16.0.0", "sp-version", "tempfile", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -19212,7 +19785,7 @@ dependencies = [ "futures", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-executor", "sc-transaction-pool-api", "sc-utils", @@ -19234,7 +19807,7 @@ dependencies = [ name = "sc-client-db" version = "0.35.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "criterion", "hash-db", "kitchensink-runtime", @@ -19245,7 +19818,7 @@ dependencies = [ "log", "parity-db", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", "sc-client-api", "sc-state-db", @@ -19272,7 +19845,7 @@ dependencies = [ "futures", "log", "mockall", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-client-api", "sc-network-types", "sc-utils", @@ -19284,7 +19857,7 @@ dependencies = [ "sp-state-machine", "sp-test-primitives", "substrate-prometheus-endpoint", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -19295,7 +19868,7 @@ dependencies = [ "futures", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-block-builder", "sc-client-api", "sc-consensus", @@ -19321,7 +19894,7 @@ dependencies = [ "substrate-prometheus-endpoint", "substrate-test-runtime-client", "tempfile", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -19337,7 +19910,7 @@ dependencies = [ "num-rational", "num-traits", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-block-builder", "sc-client-api", "sc-consensus", @@ -19363,7 +19936,7 @@ dependencies = [ "sp-tracing 16.0.0", "substrate-prometheus-endpoint", "substrate-test-runtime-client", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -19389,7 +19962,7 @@ dependencies = [ "sp-keystore", "sp-runtime", "substrate-test-runtime-client", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -19397,13 +19970,13 @@ dependencies = [ name = "sc-consensus-beefy" version = "13.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "async-channel 1.9.0", "async-trait", "futures", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-block-builder", "sc-client-api", "sc-consensus", @@ -19427,7 +20000,7 @@ dependencies = [ "sp-tracing 16.0.0", "substrate-prometheus-endpoint", "substrate-test-runtime-client", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "wasm-timer", ] @@ -19440,7 +20013,7 @@ dependencies = [ "jsonrpsee", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-consensus-beefy", "sc-rpc", "serde", @@ -19449,7 +20022,7 @@ dependencies = [ "sp-core 28.0.0", "sp-runtime", "substrate-test-runtime-client", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -19470,7 +20043,7 @@ name = "sc-consensus-grandpa" version = "0.19.0" dependencies = [ "ahash", - "array-bytes 6.2.2", + "array-bytes 6.2.3", "assert_matches", "async-trait", "dyn-clone", @@ -19480,7 +20053,7 @@ dependencies = [ "futures-timer", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", "sc-block-builder", "sc-chain-spec", @@ -19510,7 +20083,7 @@ dependencies = [ "sp-tracing 16.0.0", "substrate-prometheus-endpoint", "substrate-test-runtime-client", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -19534,7 +20107,7 @@ dependencies = [ "sp-keyring", "sp-runtime", "substrate-test-runtime-client", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -19572,7 +20145,7 @@ dependencies = [ "substrate-prometheus-endpoint", "substrate-test-runtime-client", "substrate-test-runtime-transaction-pool", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -19585,7 +20158,7 @@ dependencies = [ "futures-timer", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-client-api", "sc-consensus", "sp-api", @@ -19597,7 +20170,7 @@ dependencies = [ "sp-inherents", "sp-runtime", "substrate-prometheus-endpoint", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -19627,12 +20200,12 @@ dependencies = [ name = "sc-executor" version = "0.32.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "assert_matches", "criterion", "num_cpus", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "paste", "sc-executor-common", "sc-executor-polkavm", @@ -19657,7 +20230,7 @@ dependencies = [ "substrate-test-runtime", "tempfile", "tracing", - "tracing-subscriber", + "tracing-subscriber 0.3.19", "wat", ] @@ -19669,7 +20242,7 @@ dependencies = [ "sc-allocator", "sp-maybe-compressed-blob", "sp-wasm-interface 20.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "wasm-instrument", ] @@ -19691,7 +20264,7 @@ dependencies = [ "cargo_metadata", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "paste", "rustix 1.0.8", "sc-allocator", @@ -19724,22 +20297,22 @@ dependencies = [ name = "sc-keystore" version = "25.0.0" dependencies = [ - "array-bytes 6.2.2", - "parking_lot 0.12.3", + "array-bytes 6.2.3", + "parking_lot 0.12.4", "serde_json", "sp-application-crypto", "sp-core 28.0.0", "sp-keystore", "tempfile", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] name = "sc-mixnet" version = "0.4.0" dependencies = [ - "array-bytes 6.2.2", - "arrayvec 0.7.4", + "array-bytes 6.2.3", + "arrayvec 0.7.6", "blake2 0.10.6", "bytes", "futures", @@ -19747,7 +20320,7 @@ dependencies = [ "log", "mixnet", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-client-api", "sc-network", "sc-network-types", @@ -19758,14 +20331,14 @@ dependencies = [ "sp-keystore", "sp-mixnet", "sp-runtime", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] name = "sc-network" version = "0.34.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "assert_matches", "async-channel 1.9.0", "async-trait", @@ -19785,7 +20358,7 @@ dependencies = [ "mockall", "multistream-select", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "partial_sort", "pin-project", "prost 0.12.6", @@ -19811,7 +20384,7 @@ dependencies = [ "substrate-test-runtime", "substrate-test-runtime-client", "tempfile", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-stream", "tokio-util", @@ -19857,7 +20430,7 @@ dependencies = [ name = "sc-network-light" version = "0.33.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "async-channel 1.9.0", "futures", "log", @@ -19870,14 +20443,14 @@ dependencies = [ "sp-blockchain", "sp-core 28.0.0", "sp-runtime", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] name = "sc-network-statement" version = "0.16.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "async-channel 1.9.0", "futures", "log", @@ -19896,7 +20469,7 @@ dependencies = [ name = "sc-network-sync" version = "0.33.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "async-channel 1.9.0", "async-trait", "fork-tree", @@ -19926,7 +20499,7 @@ dependencies = [ "sp-tracing 16.0.0", "substrate-prometheus-endpoint", "substrate-test-runtime-client", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-stream", ] @@ -19941,7 +20514,7 @@ dependencies = [ "futures-timer", "libp2p", "log", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", "sc-block-builder", "sc-client-api", @@ -19967,7 +20540,7 @@ dependencies = [ name = "sc-network-transactions" version = "0.33.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "futures", "log", "parity-scale-codec", @@ -19992,13 +20565,13 @@ dependencies = [ "libp2p-kad", "litep2p", "log", - "multiaddr 0.18.1", - "multihash 0.19.1", + "multiaddr 0.18.2", + "multihash 0.19.3", "quickcheck", "rand 0.8.5", "serde", "serde_with", - "thiserror 1.0.65", + "thiserror 1.0.69", "zeroize", ] @@ -20012,15 +20585,15 @@ dependencies = [ "futures", "futures-timer", "http-body-util", - "hyper 1.6.0", - "hyper-rustls 0.27.3", + "hyper 1.7.0", + "hyper-rustls 0.27.7", "hyper-util", "num_cpus", "once_cell", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", - "rustls 0.23.18", + "rustls 0.23.31", "sc-block-builder", "sc-client-api", "sc-client-db", @@ -20060,7 +20633,7 @@ dependencies = [ "jsonrpsee", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pretty_assertions", "sc-block-builder", "sc-chain-spec", @@ -20105,7 +20678,7 @@ dependencies = [ "sp-rpc", "sp-runtime", "sp-version", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -20116,9 +20689,9 @@ dependencies = [ "forwarded-header-value", "futures", "governor", - "http 1.1.0", + "http 1.3.1", "http-body-util", - "hyper 1.6.0", + "hyper 1.7.0", "ip_network", "jsonrpsee", "log", @@ -20127,7 +20700,7 @@ dependencies = [ "serde_json", "substrate-prometheus-endpoint", "tokio", - "tower", + "tower 0.4.13", "tower-http 0.5.2", ] @@ -20135,7 +20708,7 @@ dependencies = [ name = "sc-rpc-spec-v2" version = "0.34.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "assert_matches", "async-trait", "futures", @@ -20145,7 +20718,7 @@ dependencies = [ "jsonrpsee", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pretty_assertions", "rand 0.8.5", "sc-block-builder", @@ -20172,7 +20745,7 @@ dependencies = [ "substrate-test-runtime", "substrate-test-runtime-client", "substrate-test-runtime-transaction-pool", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-stream", ] @@ -20203,8 +20776,8 @@ dependencies = [ "sp-state-machine", "sp-version", "sp-wasm-interface 20.0.0", - "subxt 0.41.0", - "thiserror 1.0.65", + "subxt 0.43.0", + "thiserror 1.0.69", ] [[package]] @@ -20219,7 +20792,7 @@ dependencies = [ "jsonrpsee", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project", "rand 0.8.5", "sc-chain-spec", @@ -20266,7 +20839,7 @@ dependencies = [ "substrate-test-runtime", "substrate-test-runtime-client", "tempfile", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tracing", "tracing-futures", @@ -20276,13 +20849,13 @@ dependencies = [ name = "sc-service-test" version = "2.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "async-channel 1.9.0", "fdlimit", "futures", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-block-builder", "sc-client-api", "sc-client-db", @@ -20313,7 +20886,7 @@ version = "0.30.0" dependencies = [ "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sp-core 28.0.0", ] @@ -20323,7 +20896,7 @@ version = "10.0.0" dependencies = [ "log", "parity-db", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-client-api", "sc-keystore", "sp-api", @@ -20345,7 +20918,7 @@ dependencies = [ "fs4", "log", "sp-core 28.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -20364,14 +20937,14 @@ dependencies = [ "serde_json", "sp-blockchain", "sp-runtime", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] name = "sc-sysinfo" version = "27.0.0" dependencies = [ - "derive_more 0.99.17", + "derive_more 0.99.20", "futures", "libc", "log", @@ -20395,13 +20968,13 @@ dependencies = [ "futures", "libp2p", "log", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project", "rand 0.8.5", "sc-utils", "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", "wasm-timer", ] @@ -20416,7 +20989,7 @@ dependencies = [ "libc", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "regex", "rustc-hash 1.1.0", "sc-client-api", @@ -20428,20 +21001,20 @@ dependencies = [ "sp-rpc", "sp-runtime", "sp-tracing 16.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", "tracing-log", - "tracing-subscriber", + "tracing-subscriber 0.3.19", ] [[package]] name = "sc-tracing-proc-macro" version = "11.0.0" dependencies = [ - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -20454,14 +21027,14 @@ dependencies = [ "chrono", "criterion", "cumulus-zombienet-sdk-helpers", - "env_logger 0.11.3", + "env_logger 0.11.8", "futures", "futures-timer", "indexmap", "itertools 0.11.0", "linked-hash-map", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rstest", "sc-block-builder", "sc-client-api", @@ -20482,11 +21055,11 @@ dependencies = [ "substrate-test-runtime-client", "substrate-test-runtime-transaction-pool", "substrate-txtesttool", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-stream", "tracing", - "tracing-subscriber", + "tracing-subscriber 0.3.19", "zombienet-configuration", "zombienet-sdk", ] @@ -20505,7 +21078,7 @@ dependencies = [ "sp-blockchain", "sp-core 28.0.0", "sp-runtime", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -20516,7 +21089,7 @@ dependencies = [ "futures", "futures-timer", "log", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "prometheus", "sp-arithmetic", "tokio-test", @@ -20573,7 +21146,7 @@ dependencies = [ "scale-decode-derive 0.16.0", "scale-type-resolver", "smallvec", - "thiserror 2.0.12", + "thiserror 2.0.16", ] [[package]] @@ -20583,9 +21156,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5ed9401effa946b493f9f84dc03714cca98119b230497df6f3df6b84a2b03648" dependencies = [ "darling", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -20595,9 +21168,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2f4b54a1211260718b92832b661025d1f1a4b6930fbadd6908e00edd265fa5f7" dependencies = [ "darling", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -20627,7 +21200,7 @@ dependencies = [ "scale-encode-derive 0.10.0", "scale-type-resolver", "smallvec", - "thiserror 2.0.12", + "thiserror 2.0.16", ] [[package]] @@ -20637,10 +21210,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "102fbc6236de6c53906c0b262f12c7aa69c2bdc604862c12728f5f4d370bc137" dependencies = [ "darling", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -20650,10 +21223,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "78a3993a13b4eafa89350604672c8757b7ea84c7c5947d4b3691e3169c96379b" dependencies = [ "darling", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -20676,10 +21249,10 @@ version = "2.11.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c6630024bf739e2179b91fb424b28898baf819414262c5d376677dbff1fe7ebf" dependencies = [ - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -20698,11 +21271,11 @@ version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0dc4c70c7fea2eef1740f0081d3fe385d8bee1eef11e9272d3bec7dc8e5438e0" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "scale-info", - "syn 2.0.98", - "thiserror 1.0.65", + "syn 2.0.106", + "thiserror 1.0.69", ] [[package]] @@ -20711,11 +21284,11 @@ version = "0.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "05c61b6b706a3eaad63b506ab50a1d2319f817ae01cf753adcc3f055f9f0fcd6" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "scale-info", - "syn 2.0.98", - "thiserror 2.0.12", + "syn 2.0.106", + "thiserror 2.0.16", ] [[package]] @@ -20753,48 +21326,73 @@ dependencies = [ "scale-encode 0.10.0", "scale-type-resolver", "serde", - "thiserror 2.0.12", + "thiserror 2.0.16", "yap 0.12.0", ] [[package]] name = "schannel" -version = "0.1.22" +version = "0.1.27" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0c3733bf4cf7ea0880754e19cb5a462007c4a8c1914bff372ccc95b464f1df88" +checksum = "1f29ebaa345f945cec9fbbc532eb307f0fdad8161f281b6369539c8d84876b3d" dependencies = [ - "windows-sys 0.48.0", + "windows-sys 0.59.0", +] + +[[package]] +name = "schemars" +version = "0.8.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3fbf2ae1b8bc8e02df939598064d22402220cd5bbcca1c76f7d6a310974d5615" +dependencies = [ + "dyn-clone", + "schemars_derive 0.8.22", + "serde", + "serde_json", ] [[package]] name = "schemars" -version = "0.8.13" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "763f8cd0d4c71ed8389c90cb8100cba87e763bd01a8e614d4f0af97bcd50a161" +checksum = "82d20c4491bc164fa2f6c5d44565947a52ad80b9505d8e36f8d54c27c739fcd0" dependencies = [ "dyn-clone", - "schemars_derive", + "ref-cast", + "schemars_derive 1.0.4", "serde", "serde_json", ] [[package]] name = "schemars_derive" -version = "0.8.13" +version = "0.8.22" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ec0f696e21e10fa546b7ffb1c9672c6de8fbc7a81acf59524386d8639bf12737" +checksum = "32e265784ad618884abaea0600a9adf15393368d840e0222d101a072f3f7534d" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "serde_derive_internals", - "syn 1.0.109", + "syn 2.0.106", +] + +[[package]] +name = "schemars_derive" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "33d020396d1d138dc19f1165df7545479dcd58d93810dc5d646a16e55abefa80" +dependencies = [ + "proc-macro2 1.0.101", + "quote 1.0.40", + "serde_derive_internals", + "syn 2.0.106", ] [[package]] name = "schnellru" -version = "0.2.3" +version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c9a8ef13a93c54d20580de1e5c413e624e53121d42fc7e2c11d10ef7f8b02367" +checksum = "356285bbf17bea63d9e52e96bd18f039672ac92b55b8cb997d6162a2a37d1649" dependencies = [ "ahash", "cfg-if", @@ -20808,7 +21406,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "844b7645371e6ecdf61ff246ba1958c29e802881a749ae3fb1993675d210d28d" dependencies = [ "arrayref", - "arrayvec 0.7.4", + "arrayvec 0.7.6", "curve25519-dalek-ng", "merlin", "rand_core 0.6.4", @@ -20820,20 +21418,20 @@ dependencies = [ [[package]] name = "schnorrkel" -version = "0.11.4" +version = "0.11.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8de18f6d8ba0aad7045f5feae07ec29899c1112584a38509a84ad7b04451eaa0" +checksum = "6e9fcb6c2e176e86ec703e22560d99d65a5ee9056ae45a08e13e84ebf796296f" dependencies = [ "aead", "arrayref", - "arrayvec 0.7.4", + "arrayvec 0.7.6", "curve25519-dalek", "getrandom_or_panic", "merlin", "rand_core 0.6.4", "serde_bytes", - "sha2 0.10.8", - "subtle 2.5.0", + "sha2 0.10.9", + "subtle 2.6.1", "zeroize", ] @@ -20851,9 +21449,9 @@ checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49" [[package]] name = "scratch" -version = "1.0.7" +version = "1.0.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a3cf7c11c38cb994f3d40e8a8cde3bbd1f72a435e4c49e85d6553d8312306152" +checksum = "d68f2ec51b097e4c1a75b681a8bec621909b5e91f15bb7b840c4f2f7b01148b2" [[package]] name = "scrypt" @@ -20864,17 +21462,17 @@ dependencies = [ "password-hash", "pbkdf2", "salsa20", - "sha2 0.10.8", + "sha2 0.10.9", ] [[package]] name = "sct" -version = "0.7.0" +version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d53dcdb7c9f8158937a7981b48accfd39a43af418591a5d008c7b22b5e1b7ca4" +checksum = "da046153aa2352493d6cb7da4b6e5c0c057d8a1d0a9aa8560baffdd945acd414" dependencies = [ - "ring 0.16.20", - "untrusted 0.7.1", + "ring 0.17.14", + "untrusted 0.9.0", ] [[package]] @@ -20888,7 +21486,7 @@ dependencies = [ "generic-array 0.14.7", "pkcs8", "serdect", - "subtle 2.5.0", + "subtle 2.6.1", "zeroize", ] @@ -20901,6 +21499,15 @@ dependencies = [ "libc", ] +[[package]] +name = "secp256k1" +version = "0.27.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "25996b82292a7a57ed3508f052cfff8640d38d32018784acd714758b43da9c8f" +dependencies = [ + "secp256k1-sys 0.8.2", +] + [[package]] name = "secp256k1" version = "0.28.2" @@ -20922,10 +21529,30 @@ dependencies = [ ] [[package]] -name = "secp256k1-sys" -version = "0.9.2" +name = "secp256k1" +version = "0.31.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e5d1746aae42c19d583c3c1a8c646bfad910498e2051c551a7f2e3c0c9fbb7eb" +checksum = "2c3c81b43dc2d8877c216a3fccf76677ee1ebccd429566d3e67447290d0c42b2" +dependencies = [ + "bitcoin_hashes 0.14.0", + "rand 0.9.2", + "secp256k1-sys 0.11.0", +] + +[[package]] +name = "secp256k1-sys" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4473013577ec77b4ee3668179ef1186df3146e2cf2d927bd200974c6fe60fd99" +dependencies = [ + "cc", +] + +[[package]] +name = "secp256k1-sys" +version = "0.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e5d1746aae42c19d583c3c1a8c646bfad910498e2051c551a7f2e3c0c9fbb7eb" dependencies = [ "cc", ] @@ -20939,6 +21566,15 @@ dependencies = [ "cc", ] +[[package]] +name = "secp256k1-sys" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dcb913707158fadaf0d8702c2db0e857de66eb003ccfdda5924b5f5ac98efb38" +dependencies = [ + "cc", +] + [[package]] name = "secrecy" version = "0.8.0" @@ -20960,23 +21596,35 @@ dependencies = [ [[package]] name = "security-framework" -version = "2.11.0" +version = "2.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c627723fd09706bacdb5cf41499e95098555af3c3c29d014dc3c458ef6be11c0" +checksum = "897b2245f0b511c87893af39b033e5ca9cce68824c4d7e7630b5a1d339658d02" dependencies = [ - "bitflags 2.6.0", - "core-foundation", + "bitflags 2.9.3", + "core-foundation 0.9.4", + "core-foundation-sys", + "libc", + "security-framework-sys", +] + +[[package]] +name = "security-framework" +version = "3.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "80fb1d92c5028aa318b4b8bd7302a5bfcf48be96a37fc6fc790f806b0004ee0c" +dependencies = [ + "bitflags 2.9.3", + "core-foundation 0.10.1", "core-foundation-sys", "libc", - "num-bigint", "security-framework-sys", ] [[package]] name = "security-framework-sys" -version = "2.11.0" +version = "2.14.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "317936bbbd05227752583946b9e66d7ce3b489f84e11a94a510b4437fef407d7" +checksum = "49db231d56a190491cb4aeda9527f1ad45345af50b0851622a7adb8c03b01c32" dependencies = [ "core-foundation-sys", "libc", @@ -21006,14 +21654,14 @@ version = "0.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f301af10236f6df4160f7c3f04eec6dbc70ace82d23326abad5edee88801c6b6" dependencies = [ - "semver-parser 0.10.2", + "semver-parser 0.10.3", ] [[package]] name = "semver" -version = "1.0.18" +version = "1.0.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b0293b4b29daaf487284529cc2f5675b8e57c61f70167ba415a463651fd6a918" +checksum = "56e6fa9c48d24d85fb3de5ad847117517440f6beceb7798af16b4a87d616b8d0" dependencies = [ "serde", ] @@ -21026,9 +21674,9 @@ checksum = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3" [[package]] name = "semver-parser" -version = "0.10.2" +version = "0.10.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "00b0bef5b7f9e0df16536d3961cfb6e84331c065b4066afb39768d0e319411f7" +checksum = "9900206b54a3527fdc7b8a938bffd94a568bac4f4aa8113b209df75a09c0dec2" dependencies = [ "pest", ] @@ -21069,9 +21717,9 @@ dependencies = [ [[package]] name = "serde_bytes" -version = "0.11.12" +version = "0.11.17" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ab33ec92f677585af6d88c65593ae2375adde54efdbf16d597f2cbc7a6d368ff" +checksum = "8437fd221bde2d4ca316d61b90e337e9e702b3820b87d63caa9ba6c02bd06d96" dependencies = [ "serde", ] @@ -21082,20 +21730,20 @@ version = "1.0.219" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5b0276cf7f2c73365f7157c8123c21cd9a50fbbd844757af28ca1f5925fc2a00" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "serde_derive_internals" -version = "0.26.0" +version = "0.29.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "85bf8229e7920a9f636479437026331ce11aa132b4dde37d121944a44d6e5f3c" +checksum = "18d26a20a969b9e3fdf2fc2d9f21eda6c40e2de84c9408bb5d3b05d499aae711" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 1.0.109", + "syn 2.0.106", ] [[package]] @@ -21109,9 +21757,9 @@ dependencies = [ [[package]] name = "serde_json" -version = "1.0.132" +version = "1.0.143" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d726bfaff4b320266d395898905d0eba0345aae23b54aee3a737e260fd46db03" +checksum = "d401abef1d108fbd9cbaebc3e46611f4b1021f714a0597a71f41ee463f5f4a5a" dependencies = [ "indexmap", "itoa", @@ -21122,9 +21770,18 @@ dependencies = [ [[package]] name = "serde_spanned" -version = "0.6.7" +version = "0.6.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bf41e0cfaf7226dca15e8197172c295a782857fcb97fad1808a166870dee75a3" +dependencies = [ + "serde", +] + +[[package]] +name = "serde_spanned" +version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eb5b1b31579f3811bf615c144393417496f152e12ac8b7663bf664f4a815306d" +checksum = "40734c41988f7306bb04f0ecf60ec0f3f1caa34290e4e8ea471dcd3346483b83" dependencies = [ "serde", ] @@ -21143,9 +21800,9 @@ dependencies = [ [[package]] name = "serde_with" -version = "3.12.0" +version = "3.14.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d6b6f7f2fcb69f747921f79f3926bd1e203fce4fef62c268dd3abfb6d86029aa" +checksum = "f2c45cd61fefa9db6f254525d46e392b852e0e61d9a1fd36e5bd183450a556d5" dependencies = [ "base64 0.22.1", "chrono", @@ -21159,14 +21816,14 @@ dependencies = [ [[package]] name = "serde_with_macros" -version = "3.12.0" +version = "3.14.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8d00caa5193a3c8362ac2b73be6b9e768aa5a4b2f721d8f4b339600c3cb51f8e" +checksum = "de90945e6565ce0d9a25098082ed4ee4002e047cb59892c318d66821e14bb30f" dependencies = [ "darling", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -21202,7 +21859,7 @@ dependencies = [ "cfg-if", "cpufeatures", "digest 0.9.0", - "opaque-debug 0.3.0", + "opaque-debug 0.3.1", ] [[package]] @@ -21226,14 +21883,14 @@ dependencies = [ "cfg-if", "cpufeatures", "digest 0.9.0", - "opaque-debug 0.3.0", + "opaque-debug 0.3.1", ] [[package]] name = "sha2" -version = "0.10.8" +version = "0.10.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "793db75ad2bcafc3ffa7c68b215fee268f537982cd901d132f89c6343f3a3dc8" +checksum = "a7507d819769d01a365ab707794a4084392c824f54a7a6a7862f8c3d0892b283" dependencies = [ "cfg-if", "cpufeatures", @@ -21262,9 +21919,9 @@ dependencies = [ [[package]] name = "sharded-slab" -version = "0.1.4" +version = "0.1.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "900fba806f70c630b0a382d0d825e17a0f19fcd059a2ade1ff237bcddf446b31" +checksum = "f40ca3c46823713e0d4209592e8d6e826aa57e928f09752619fc696c499637f6" dependencies = [ "lazy_static", ] @@ -21275,30 +21932,20 @@ version = "1.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0fda2ff0d084019ba4d7c6f371c95d8fd75ce3524c3cb8fb653a3023f6323e64" -[[package]] -name = "signal-hook" -version = "0.3.17" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8621587d4798caf8eb44879d42e56b9a93ea5dcd315a6487c357130095b62801" -dependencies = [ - "libc", - "signal-hook-registry", -] - [[package]] name = "signal-hook-registry" -version = "1.4.1" +version = "1.4.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d8229b473baa5980ac72ef434c4415e70c4b5e71b423043adb4ba059f89c99a1" +checksum = "b2a4719bff48cee6b39d12c020eeb490953ad2443b7055bd0b21fca26bd8c28b" dependencies = [ "libc", ] [[package]] name = "signature" -version = "2.1.0" +version = "2.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5e1788eed21689f9cf370582dfc467ef36ed9c707f073528ddafa8d83e3b8500" +checksum = "77549399552de45a898a580c1b41d445bf730df867cc44e6c0233bbc4b8329de" dependencies = [ "digest 0.10.7", "rand_core 0.6.4", @@ -21306,9 +21953,9 @@ dependencies = [ [[package]] name = "simba" -version = "0.8.1" +version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "061507c94fc6ab4ba1c9a0305018408e312e17c041eb63bef8aa726fa33aceae" +checksum = "b3a386a501cd104797982c15ae17aafe8b9261315b5d07e3ec803f2ea26be0fa" dependencies = [ "approx", "num-complex", @@ -21323,7 +21970,7 @@ version = "0.9.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "dee851d0e5e7af3721faea1843e8015e820a234f81fda3dea9247e15bac9a86a" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", ] [[package]] @@ -21346,12 +21993,9 @@ checksum = "56199f7ddabf13fe5074ce809e7d3f42b42ae711800501b5b16ea82ad029c39d" [[package]] name = "slab" -version = "0.4.9" +version = "0.4.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8f92a496fb766b417c996b9c5e57daf2f7ad3b0bebe1ccfca4856390e3d3bb67" -dependencies = [ - "autocfg", -] +checksum = "7a2ae44ef20feb57a68b23d846850f861394c2e02dc425a50098ae8c90267589" [[package]] name = "slice-group-by" @@ -21371,9 +22015,9 @@ dependencies = [ [[package]] name = "slotmap" -version = "1.0.6" +version = "1.0.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e1e08e261d0e8f5c43123b7adf3e4ca1690d655377ac93a03b2c9d3e98de1342" +checksum = "dbff4acf519f630b3a3ddcfaea6c06b42174d9a44bc70c620e9ed1649d58b82a" dependencies = [ "version_check", ] @@ -21391,9 +22035,9 @@ dependencies = [ [[package]] name = "smallvec" -version = "1.15.0" +version = "1.15.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8917285742e9f3e1683f0a9c4e6b57960b7314d0b08d30d1ecd426713ee2eee9" +checksum = "67b1b7a3b5fe4f1376887184045fcf45c69e92af734b7aaddc05fb777b6fbd03" dependencies = [ "serde", ] @@ -21409,8 +22053,8 @@ dependencies = [ "async-fs 1.6.0", "async-io 1.13.0", "async-lock 2.8.0", - "async-net 1.7.0", - "async-process 1.7.0", + "async-net 1.8.0", + "async-process 1.8.1", "blocking", "futures-lite 1.13.0", ] @@ -21421,24 +22065,15 @@ version = "2.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a33bd3e260892199c3ccfc487c88b2da2265080acb316cd920da72fdfd7c599f" dependencies = [ - "async-channel 2.3.0", + "async-channel 2.5.0", "async-executor", - "async-fs 2.1.2", - "async-io 2.3.3", - "async-lock 3.4.0", + "async-fs 2.1.3", + "async-io 2.5.0", + "async-lock 3.4.1", "async-net 2.0.0", - "async-process 2.3.0", + "async-process 2.4.0", "blocking", - "futures-lite 2.3.0", -] - -[[package]] -name = "smol_str" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "74212e6bbe9a4352329b2f68ba3130c15a3f26fe88ff22dbdc6cdd58fa85e99c" -dependencies = [ - "serde", + "futures-lite 2.6.1", ] [[package]] @@ -21447,7 +22082,7 @@ version = "0.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c0bb30cf57b7b5f6109ce17c3164445e2d6f270af2cb48f6e4d31c2967c9a9f5" dependencies = [ - "arrayvec 0.7.4", + "arrayvec 0.7.6", "async-lock 2.8.0", "atomic-take", "base64 0.21.7", @@ -21456,7 +22091,7 @@ dependencies = [ "bs58", "chacha20", "crossbeam-queue", - "derive_more 0.99.17", + "derive_more 0.99.20", "ed25519-zebra", "either", "event-listener 2.5.3", @@ -21470,7 +22105,7 @@ dependencies = [ "libsecp256k1", "merlin", "no-std-net", - "nom", + "nom 7.1.3", "num-bigint", "num-rational", "num-traits", @@ -21483,13 +22118,13 @@ dependencies = [ "schnorrkel 0.10.2", "serde", "serde_json", - "sha2 0.10.8", + "sha2 0.10.9", "sha3", "siphasher 0.3.11", "slab", "smallvec", "soketto 0.7.1", - "twox-hash", + "twox-hash 1.6.3", "wasmi 0.31.2", "x25519-dalek", "zeroize", @@ -21501,8 +22136,8 @@ version = "0.18.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "966e72d77a3b2171bb7461d0cb91f43670c63558c62d7cf42809cae6c8b6b818" dependencies = [ - "arrayvec 0.7.4", - "async-lock 3.4.0", + "arrayvec 0.7.6", + "async-lock 3.4.1", "atomic-take", "base64 0.22.1", "bip39", @@ -21510,12 +22145,12 @@ dependencies = [ "bs58", "chacha20", "crossbeam-queue", - "derive_more 0.99.17", + "derive_more 0.99.20", "ed25519-zebra", "either", - "event-listener 5.3.1", + "event-listener 5.4.1", "fnv", - "futures-lite 2.3.0", + "futures-lite 2.6.1", "futures-util", "hashbrown 0.14.5", "hex", @@ -21524,7 +22159,7 @@ dependencies = [ "libm", "libsecp256k1", "merlin", - "nom", + "nom 7.1.3", "num-bigint", "num-rational", "num-traits", @@ -21534,21 +22169,75 @@ dependencies = [ "rand 0.8.5", "rand_chacha 0.3.1", "ruzstd 0.6.0", - "schnorrkel 0.11.4", + "schnorrkel 0.11.5", "serde", "serde_json", - "sha2 0.10.8", + "sha2 0.10.9", "sha3", "siphasher 1.0.1", "slab", "smallvec", - "soketto 0.8.0", - "twox-hash", + "soketto 0.8.1", + "twox-hash 1.6.3", "wasmi 0.32.3", "x25519-dalek", "zeroize", ] +[[package]] +name = "smoldot" +version = "0.19.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e16e5723359f0048bf64bfdfba64e5732a56847d42c4fd3fe56f18280c813413" +dependencies = [ + "arrayvec 0.7.6", + "async-lock 3.4.1", + "atomic-take", + "base64 0.22.1", + "bip39", + "blake2-rfc", + "bs58", + "chacha20", + "crossbeam-queue", + "derive_more 2.0.1", + "ed25519-zebra", + "either", + "event-listener 5.4.1", + "fnv", + "futures-lite 2.6.1", + "futures-util", + "hashbrown 0.15.5", + "hex", + "hmac 0.12.1", + "itertools 0.14.0", + "libm", + "libsecp256k1", + "merlin", + "nom 8.0.0", + "num-bigint", + "num-rational", + "num-traits", + "pbkdf2", + "pin-project", + "poly1305", + "rand 0.8.5", + "rand_chacha 0.3.1", + "ruzstd 0.8.1", + "schnorrkel 0.11.5", + "serde", + "serde_json", + "sha2 0.10.9", + "sha3", + "siphasher 1.0.1", + "slab", + "smallvec", + "soketto 0.8.1", + "twox-hash 2.1.1", + "wasmi 0.40.0", + "x25519-dalek", + "zeroize", +] + [[package]] name = "smoldot-light" version = "0.9.0" @@ -21559,7 +22248,7 @@ dependencies = [ "async-lock 2.8.0", "base64 0.21.7", "blake2-rfc", - "derive_more 0.99.17", + "derive_more 0.99.20", "either", "event-listener 2.5.3", "fnv", @@ -21570,9 +22259,9 @@ dependencies = [ "hex", "itertools 0.11.0", "log", - "lru 0.11.0", + "lru 0.11.1", "no-std-net", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project", "rand 0.8.5", "rand_chacha 0.3.1", @@ -21591,24 +22280,24 @@ version = "0.16.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2a33b06891f687909632ce6a4e3fd7677b24df930365af3d0bcb078310129f3f" dependencies = [ - "async-channel 2.3.0", - "async-lock 3.4.0", + "async-channel 2.5.0", + "async-lock 3.4.1", "base64 0.22.1", "blake2-rfc", "bs58", - "derive_more 0.99.17", + "derive_more 0.99.20", "either", - "event-listener 5.3.1", + "event-listener 5.4.1", "fnv", "futures-channel", - "futures-lite 2.3.0", + "futures-lite 2.6.1", "futures-util", "hashbrown 0.14.5", "hex", "itertools 0.13.0", "log", - "lru 0.12.3", - "parking_lot 0.12.3", + "lru 0.12.5", + "parking_lot 0.12.4", "pin-project", "rand 0.8.5", "rand_chacha 0.3.1", @@ -21621,11 +22310,47 @@ dependencies = [ "zeroize", ] +[[package]] +name = "smoldot-light" +version = "0.17.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1bba9e591716567d704a8252feeb2f1261a286e1e2cbdd4e49e9197c34a14e2" +dependencies = [ + "async-channel 2.5.0", + "async-lock 3.4.1", + "base64 0.22.1", + "blake2-rfc", + "bs58", + "derive_more 2.0.1", + "either", + "event-listener 5.4.1", + "fnv", + "futures-channel", + "futures-lite 2.6.1", + "futures-util", + "hashbrown 0.15.5", + "hex", + "itertools 0.14.0", + "log", + "lru 0.12.5", + "parking_lot 0.12.4", + "pin-project", + "rand 0.8.5", + "rand_chacha 0.3.1", + "serde", + "serde_json", + "siphasher 1.0.1", + "slab", + "smol 2.0.2", + "smoldot 0.19.4", + "zeroize", +] + [[package]] name = "snap" -version = "1.1.0" +version = "1.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5e9f0ab6ef7eb7353d9119c170a436d1bf248eea575ac42d19d12f4e34130831" +checksum = "1b6b67fb9a61334225b5b790716f609cd58395f895b3fe8b328786812a40bc3b" [[package]] name = "snow" @@ -21638,10 +22363,10 @@ dependencies = [ "chacha20poly1305", "curve25519-dalek", "rand_core 0.6.4", - "ring 0.17.8", - "rustc_version 0.4.0", - "sha2 0.10.8", - "subtle 2.5.0", + "ring 0.17.14", + "rustc_version 0.4.1", + "sha2 0.10.9", + "subtle 2.6.1", ] [[package]] @@ -21746,7 +22471,7 @@ dependencies = [ name = "snowbridge-merkle-tree" version = "0.2.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "hex", "hex-literal", "parity-scale-codec", @@ -22175,9 +22900,9 @@ dependencies = [ [[package]] name = "socket2" -version = "0.4.9" +version = "0.4.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "64a4a911eed85daf18834cfaa86a79b7d266ff93ff5ba14005426219480ed662" +checksum = "9f7916fc008ca5542385b89a3d3ce689953c143e9304a9bf8beec1de48994c0d" dependencies = [ "libc", "winapi", @@ -22185,14 +22910,24 @@ dependencies = [ [[package]] name = "socket2" -version = "0.5.9" +version = "0.5.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4f5fd57c80058a56cf5c777ab8a126398ece8e442983605d280a44ce79d0edef" +checksum = "e22376abed350d73dd1cd119b57ffccad95b4e585a7cda43e286245ce23c0678" dependencies = [ "libc", "windows-sys 0.52.0", ] +[[package]] +name = "socket2" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "233504af464074f9d066d7b5416c5f9b894a5862a6506e306f7b816cdd6f1807" +dependencies = [ + "libc", + "windows-sys 0.59.0", +] + [[package]] name = "soketto" version = "0.7.1" @@ -22210,14 +22945,14 @@ dependencies = [ [[package]] name = "soketto" -version = "0.8.0" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "37468c595637c10857701c990f93a40ce0e357cedb0953d1c26c8d8027f9bb53" +checksum = "2e859df029d160cb88608f5d7df7fb4753fd20fdfb4de5644f3d8b8440841721" dependencies = [ "base64 0.22.1", "bytes", "futures", - "http 1.1.0", + "http 1.3.1", "httparse", "log", "rand 0.8.5", @@ -22324,7 +23059,7 @@ dependencies = [ "sp-test-primitives", "sp-trie", "sp-version", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -22335,10 +23070,10 @@ dependencies = [ "assert_matches", "blake2 0.10.6", "expander", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -22442,7 +23177,7 @@ version = "28.0.0" dependencies = [ "futures", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "schnellru", "sp-api", "sp-consensus", @@ -22450,7 +23185,7 @@ dependencies = [ "sp-database", "sp-runtime", "sp-state-machine", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", ] @@ -22464,7 +23199,7 @@ dependencies = [ "sp-inherents", "sp-runtime", "sp-state-machine", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -22503,7 +23238,7 @@ dependencies = [ name = "sp-consensus-beefy" version = "13.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "parity-scale-codec", "scale-info", "serde", @@ -22575,7 +23310,7 @@ name = "sp-core" version = "28.0.0" dependencies = [ "ark-vrf", - "array-bytes 6.2.2", + "array-bytes 6.2.3", "bitflags 1.3.2", "blake2 0.10.6", "bounded-collections 0.3.2", @@ -22594,18 +23329,18 @@ dependencies = [ "merlin", "parity-bip39", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "paste", "primitive-types 0.13.1", "rand 0.8.5", "regex", "scale-info", - "schnorrkel 0.11.4", + "schnorrkel 0.11.5", "secp256k1 0.28.2", "secrecy 0.8.0", "serde", "serde_json", - "sha2 0.10.8", + "sha2 0.10.9", "sp-crypto-hashing 0.1.0", "sp-debug-derive 14.0.0", "sp-externalities 0.25.0", @@ -22613,7 +23348,7 @@ dependencies = [ "sp-storage 19.0.0", "ss58-registry", "substrate-bip39 0.4.7", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", "w3f-bls", "zeroize", @@ -22621,14 +23356,15 @@ dependencies = [ [[package]] name = "sp-core" -version = "35.0.0" +version = "36.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4532774405a712a366a98080cbb4daa28c38ddff0ec595902ad6ee6a78a809f8" +checksum = "1cdbb58c21e6b27f2aadf3ff0c8b20a8ead13b9dfe63f46717fd59334517f3b4" dependencies = [ - "array-bytes 6.2.2", + "ark-vrf", + "array-bytes 6.2.3", "bitflags 1.3.2", "blake2 0.10.6", - "bounded-collections 0.2.3", + "bounded-collections 0.2.4", "bs58", "dyn-clonable", "ed25519-zebra", @@ -22643,24 +23379,24 @@ dependencies = [ "merlin", "parity-bip39", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "paste", "primitive-types 0.13.1", "rand 0.8.5", "scale-info", - "schnorrkel 0.11.4", + "schnorrkel 0.11.5", "secp256k1 0.28.2", "secrecy 0.8.0", "serde", "sp-crypto-hashing 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", "sp-debug-derive 14.0.0 (registry+https://github.com/rust-lang/crates.io-index)", "sp-externalities 0.30.0", - "sp-runtime-interface 29.0.0", + "sp-runtime-interface 29.0.1", "sp-std 14.0.0 (registry+https://github.com/rust-lang/crates.io-index)", "sp-storage 22.0.0", "ss58-registry", "substrate-bip39 0.6.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", "w3f-bls", "zeroize", @@ -22716,10 +23452,10 @@ dependencies = [ "byteorder", "criterion", "digest 0.10.7", - "sha2 0.10.8", + "sha2 0.10.9", "sha3", "sp-crypto-hashing-proc-macro", - "twox-hash", + "twox-hash 1.6.3", ] [[package]] @@ -22731,9 +23467,9 @@ dependencies = [ "blake2b_simd", "byteorder", "digest 0.10.7", - "sha2 0.10.8", + "sha2 0.10.9", "sha3", - "twox-hash", + "twox-hash 1.6.3", ] [[package]] @@ -22742,7 +23478,7 @@ version = "0.1.0" dependencies = [ "quote 1.0.40", "sp-crypto-hashing 0.1.0", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -22750,16 +23486,16 @@ name = "sp-database" version = "10.0.0" dependencies = [ "kvdb", - "parking_lot 0.12.3", + "parking_lot 0.12.4", ] [[package]] name = "sp-debug-derive" version = "14.0.0" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -22768,9 +23504,9 @@ version = "14.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "48d09fa0a5f7299fb81ee25ae3853d26200f7a348148aed6de76be905c007dbe" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -22814,7 +23550,7 @@ dependencies = [ "parity-scale-codec", "scale-info", "sp-runtime", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -22856,7 +23592,7 @@ name = "sp-keystore" version = "0.34.0" dependencies = [ "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sp-core 28.0.0", "sp-externalities 0.25.0", ] @@ -22865,7 +23601,7 @@ dependencies = [ name = "sp-maybe-compressed-blob" version = "11.0.0" dependencies = [ - "thiserror 1.0.65", + "thiserror 1.0.69", "zstd 0.12.4", ] @@ -22892,7 +23628,7 @@ dependencies = [ name = "sp-mmr-primitives" version = "26.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "log", "parity-scale-codec", "polkadot-ckb-merkle-mountain-range", @@ -22902,7 +23638,7 @@ dependencies = [ "sp-core 28.0.0", "sp-debug-derive 14.0.0", "sp-runtime", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -23014,20 +23750,20 @@ dependencies = [ [[package]] name = "sp-runtime-interface" -version = "29.0.0" +version = "29.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "51e83d940449837a8b2a01b4d877dd22d896fd14d3d3ade875787982da994a33" +checksum = "e99db36a7aff44c335f5d5b36c182a3e0cac61de2fefbe2eeac6af5fb13f63bf" dependencies = [ "bytes", "impl-trait-for-tuples", "parity-scale-codec", - "polkavm-derive 0.9.1", + "polkavm-derive 0.18.0", "primitive-types 0.13.1", "sp-externalities 0.30.0", "sp-runtime-interface-proc-macro 18.0.0", "sp-std 14.0.0 (registry+https://github.com/rust-lang/crates.io-index)", "sp-storage 22.0.0", - "sp-tracing 17.0.1", + "sp-tracing 17.1.0", "sp-wasm-interface 21.0.1", "static_assertions", ] @@ -23038,10 +23774,10 @@ version = "17.0.0" dependencies = [ "Inflector", "expander", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -23052,10 +23788,10 @@ checksum = "0195f32c628fee3ce1dfbbf2e7e52a30ea85f3589da9fe62a8b816d70fc06294" dependencies = [ "Inflector", "expander", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -23125,12 +23861,12 @@ name = "sp-state-machine" version = "0.35.0" dependencies = [ "arbitrary", - "array-bytes 6.2.2", + "array-bytes 6.2.3", "assert_matches", "hash-db", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pretty_assertions", "rand 0.8.5", "smallvec", @@ -23139,7 +23875,7 @@ dependencies = [ "sp-panic-handler", "sp-runtime", "sp-trie", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", "trie-db", ] @@ -23155,7 +23891,7 @@ dependencies = [ "parity-scale-codec", "rand 0.8.5", "scale-info", - "sha2 0.10.8", + "sha2 0.10.9", "sp-api", "sp-application-crypto", "sp-core 28.0.0", @@ -23163,7 +23899,7 @@ dependencies = [ "sp-externalities 0.25.0", "sp-runtime", "sp-runtime-interface 24.0.0", - "thiserror 1.0.65", + "thiserror 1.0.69", "x25519-dalek", ] @@ -23221,7 +23957,7 @@ dependencies = [ "parity-scale-codec", "sp-inherents", "sp-runtime", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -23232,19 +23968,19 @@ dependencies = [ "regex", "tracing", "tracing-core", - "tracing-subscriber", + "tracing-subscriber 0.3.19", ] [[package]] name = "sp-tracing" -version = "17.0.1" +version = "17.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cf641a1d17268c8fcfdb8e0fa51a79c2d4222f4cfda5f3944dbdbc384dced8d5" +checksum = "6147a5b8c98b9ed4bf99dc033fab97a468b4645515460974c8784daeb7c35433" dependencies = [ "parity-scale-codec", "tracing", "tracing-core", - "tracing-subscriber", + "tracing-subscriber 0.3.19", ] [[package]] @@ -23273,15 +24009,15 @@ name = "sp-trie" version = "29.0.0" dependencies = [ "ahash", - "array-bytes 6.2.2", + "array-bytes 6.2.3", "criterion", - "foldhash", + "foldhash 0.1.5", "hash-db", - "hashbrown 0.15.3", + "hashbrown 0.15.5", "memory-db", "nohash-hasher", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "rand 0.8.5", "scale-info", "schnellru", @@ -23289,7 +24025,7 @@ dependencies = [ "sp-externalities 0.25.0", "sp-runtime", "substrate-prometheus-endpoint", - "thiserror 1.0.65", + "thiserror 1.0.69", "tracing", "trie-bench", "trie-db", @@ -23310,7 +24046,7 @@ dependencies = [ "sp-runtime", "sp-std 14.0.0", "sp-version-proc-macro", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -23319,10 +24055,10 @@ version = "13.0.0" dependencies = [ "parity-scale-codec", "proc-macro-warning", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "sp-version", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -23355,7 +24091,7 @@ dependencies = [ "bounded-collections 0.3.2", "parity-scale-codec", "scale-info", - "schemars", + "schemars 0.8.22", "serde", "smallvec", "sp-arithmetic", @@ -23389,30 +24125,29 @@ dependencies = [ ] [[package]] -name = "spki" -version = "0.7.2" +name = "spinning_top" +version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9d1e996ef02c474957d681f1b05213dfb0abab947b446a62d37770b23500184a" +checksum = "d96d2d1d716fb500937168cc09353ffdc7a012be8475ac7308e1bdf0e3923300" dependencies = [ - "base64ct", - "der", + "lock_api", ] [[package]] -name = "sqlformat" -version = "0.2.6" +name = "spki" +version = "0.7.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7bba3a93db0cc4f7bdece8bb09e77e2e785c20bfebf79eb8340ed80708048790" +checksum = "d91ed6c858b01f942cd56b37a94b3e0a1798290327d1236e4d9cf4eaca44d29d" dependencies = [ - "nom", - "unicode_categories", + "base64ct", + "der", ] [[package]] name = "sqlx" -version = "0.8.2" +version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "93334716a037193fac19df402f8571269c84a00852f6a7066b5d2616dcd64d3e" +checksum = "1fefb893899429669dcdd979aff487bd78f4064e5e7907e4269081e0ef7d97dc" dependencies = [ "sqlx-core", "sqlx-macros", @@ -23423,37 +24158,32 @@ dependencies = [ [[package]] name = "sqlx-core" -version = "0.8.2" +version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d4d8060b456358185f7d50c55d9b5066ad956956fddec42ee2e8567134a8936e" +checksum = "ee6798b1838b6a0f69c007c133b8df5866302197e404e8b6ee8ed3e3a5e68dc6" dependencies = [ - "atoi", - "byteorder", + "base64 0.22.1", "bytes", "crc", "crossbeam-queue", "either", - "event-listener 5.3.1", - "futures-channel", + "event-listener 5.4.1", "futures-core", "futures-intrusive", "futures-io", "futures-util", - "hashbrown 0.14.5", - "hashlink 0.9.1", - "hex", + "hashbrown 0.15.5", + "hashlink 0.10.0", "indexmap", "log", "memchr", "once_cell", - "paste", "percent-encoding", "serde", "serde_json", - "sha2 0.10.8", + "sha2 0.10.9", "smallvec", - "sqlformat", - "thiserror 1.0.65", + "thiserror 2.0.16", "tokio", "tokio-stream", "tracing", @@ -23462,52 +24192,51 @@ dependencies = [ [[package]] name = "sqlx-macros" -version = "0.8.2" +version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cac0692bcc9de3b073e8d747391827297e075c7710ff6276d9f7a1f3d58c6657" +checksum = "a2d452988ccaacfbf5e0bdbc348fb91d7c8af5bee192173ac3636b5fb6e6715d" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "sqlx-core", "sqlx-macros-core", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "sqlx-macros-core" -version = "0.8.2" +version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1804e8a7c7865599c9c79be146dc8a9fd8cc86935fa641d3ea58e5f0688abaa5" +checksum = "19a9c1841124ac5a61741f96e1d9e2ec77424bf323962dd894bdb93f37d5219b" dependencies = [ "dotenvy", "either", "heck 0.5.0", "hex", "once_cell", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "serde", "serde_json", - "sha2 0.10.8", + "sha2 0.10.9", "sqlx-core", "sqlx-mysql", "sqlx-postgres", "sqlx-sqlite", - "syn 2.0.98", - "tempfile", + "syn 2.0.106", "tokio", "url", ] [[package]] name = "sqlx-mysql" -version = "0.8.2" +version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "64bb4714269afa44aef2755150a0fc19d756fb580a67db8885608cf02f47d06a" +checksum = "aa003f0038df784eb8fecbbac13affe3da23b45194bd57dba231c8f48199c526" dependencies = [ "atoi", "base64 0.22.1", - "bitflags 2.6.0", + "bitflags 2.9.3", "byteorder", "bytes", "crc", @@ -23532,31 +24261,30 @@ dependencies = [ "rsa", "serde", "sha1", - "sha2 0.10.8", + "sha2 0.10.9", "smallvec", "sqlx-core", "stringprep", - "thiserror 1.0.65", + "thiserror 2.0.16", "tracing", "whoami", ] [[package]] name = "sqlx-postgres" -version = "0.8.2" +version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6fa91a732d854c5d7726349bb4bb879bb9478993ceb764247660aee25f67c2f8" +checksum = "db58fcd5a53cf07c184b154801ff91347e4c30d17a3562a635ff028ad5deda46" dependencies = [ "atoi", "base64 0.22.1", - "bitflags 2.6.0", + "bitflags 2.9.3", "byteorder", "crc", "dotenvy", "etcetera", "futures-channel", "futures-core", - "futures-io", "futures-util", "hex", "hkdf", @@ -23570,20 +24298,20 @@ dependencies = [ "rand 0.8.5", "serde", "serde_json", - "sha2 0.10.8", + "sha2 0.10.9", "smallvec", "sqlx-core", "stringprep", - "thiserror 1.0.65", + "thiserror 2.0.16", "tracing", "whoami", ] [[package]] name = "sqlx-sqlite" -version = "0.8.2" +version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d5b2cf34a45953bfd3daaf3db0f7a7878ab9b7a6b91b422d24a7a9e4c857b680" +checksum = "c2d12fe70b2c1b4401038055f90f151b78208de1f9f89a7dbfd41587a10c3eea" dependencies = [ "atoi", "flume", @@ -23598,23 +24326,24 @@ dependencies = [ "serde", "serde_urlencoded", "sqlx-core", + "thiserror 2.0.16", "tracing", "url", ] [[package]] name = "ss58-registry" -version = "1.43.0" +version = "1.51.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5e6915280e2d0db8911e5032a5c275571af6bdded2916abd691a659be25d3439" +checksum = "19409f13998e55816d1c728395af0b52ec066206341d939e22e7766df9b494b8" dependencies = [ "Inflector", "num-format", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "serde", "serde_json", - "unicode-xid 0.2.4", + "unicode-xid 0.2.6", ] [[package]] @@ -23635,7 +24364,7 @@ version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f07d54c4d01a1713eb363b55ba51595da15f6f1211435b71466460da022aa140" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "syn 1.0.109", ] @@ -23665,7 +24394,7 @@ dependencies = [ name = "staging-node-cli" version = "3.0.0-dev" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "assert_cmd", "clap", "clap_complete", @@ -23687,11 +24416,11 @@ dependencies = [ "scale-info", "serde", "serde_json", - "soketto 0.8.0", + "soketto 0.8.1", "sp-keyring", "staging-node-inspect", "substrate-cli-test-utils", - "subxt-signer 0.41.0", + "subxt-signer 0.43.0", "tempfile", "tokio", "tokio-util", @@ -23712,7 +24441,7 @@ dependencies = [ "sp-io", "sp-runtime", "sp-statement-store", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -23735,7 +24464,7 @@ version = "2.0.0" name = "staging-xcm" version = "7.0.1" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "bounded-collections 0.3.2", "derive-where", "environmental", @@ -23744,7 +24473,7 @@ dependencies = [ "impl-trait-for-tuples", "parity-scale-codec", "scale-info", - "schemars", + "schemars 0.8.22", "serde", "sp-io", "sp-runtime", @@ -23813,28 +24542,28 @@ checksum = "a2eb9349b6444b326872e140eb1cf5e7c522154d69e7a0ffb0fb81c06b37543f" [[package]] name = "static_init" -version = "1.0.3" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8a2a1c578e98c1c16fc3b8ec1328f7659a500737d7a0c6d625e73e830ff9c1f6" +checksum = "8bae1df58c5fea7502e8e352ec26b5579f6178e1fdb311e088580c980dee25ed" dependencies = [ "bitflags 1.3.2", - "cfg_aliases 0.1.1", + "cfg_aliases 0.2.1", "libc", - "parking_lot 0.11.2", - "parking_lot_core 0.8.6", + "parking_lot 0.12.4", + "parking_lot_core 0.9.11", "static_init_macro", "winapi", ] [[package]] name = "static_init_macro" -version = "1.0.2" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "70a2595fc3aa78f2d0e45dd425b22282dd863273761cc77780914b2cf3003acf" +checksum = "1389c88ddd739ec6d3f8f83343764a0e944cd23cfbf126a9796a714b0b6edd6f" dependencies = [ "cfg_aliases 0.1.1", "memchr", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "syn 1.0.109", ] @@ -23892,7 +24621,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1e385be0d24f186b4ce2f9982191e7101bb737312ad61c1f2f984f34bcf85d59" dependencies = [ "heck 0.4.1", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "rustversion", "syn 1.0.109", @@ -23905,10 +24634,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4c6bee85a5a24955dc440386795aa378cd9cf82acd5f764469152d2270e581be" dependencies = [ "heck 0.5.0", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "rustversion", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -23927,8 +24656,8 @@ dependencies = [ "parity-bip39", "pbkdf2", "rustc-hex", - "schnorrkel 0.11.4", - "sha2 0.10.8", + "schnorrkel 0.11.5", + "sha2 0.10.9", "zeroize", ] @@ -23940,8 +24669,8 @@ checksum = "ca58ffd742f693dc13d69bdbb2e642ae239e0053f6aab3b104252892f856700a" dependencies = [ "hmac 0.12.1", "pbkdf2", - "schnorrkel 0.11.4", - "sha2 0.10.8", + "schnorrkel 0.11.5", + "sha2 0.10.9", "zeroize", ] @@ -24025,11 +24754,11 @@ name = "substrate-prometheus-endpoint" version = "0.17.0" dependencies = [ "http-body-util", - "hyper 1.6.0", + "hyper 1.7.0", "hyper-util", "log", "prometheus", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", ] @@ -24072,7 +24801,7 @@ dependencies = [ "sp-runtime", "sp-trie", "strum 0.26.3", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -24109,7 +24838,7 @@ dependencies = [ name = "substrate-test-client" version = "2.0.1" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "async-trait", "futures", "parity-scale-codec", @@ -24133,7 +24862,7 @@ dependencies = [ name = "substrate-test-runtime" version = "2.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "frame-executive", "frame-metadata-hash-extension", "frame-support", @@ -24209,13 +24938,13 @@ dependencies = [ "futures", "log", "parity-scale-codec", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "sc-transaction-pool", "sc-transaction-pool-api", "sp-blockchain", "sp-runtime", "substrate-test-runtime-client", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -24239,28 +24968,28 @@ dependencies = [ "hex", "jsonrpsee", "parity-scale-codec", - "parking_lot 0.12.3", - "rand 0.9.0", + "parking_lot 0.12.4", + "rand 0.9.2", "serde", "serde_json", "subxt 0.41.0", "subxt-core 0.41.0", - "subxt-rpcs", + "subxt-rpcs 0.41.0", "subxt-signer 0.41.0", "termplot", - "thiserror 2.0.12", + "thiserror 2.0.16", "time", "tokio", "tokio-util", "tracing", - "tracing-subscriber", + "tracing-subscriber 0.3.19", ] [[package]] name = "substrate-wasm-builder" version = "17.0.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "build-helper", "cargo_metadata", "console", @@ -24280,7 +25009,7 @@ dependencies = [ "sp-version", "strum 0.26.3", "tempfile", - "toml", + "toml 0.8.23", "walkdir", "wasm-opt", ] @@ -24293,9 +25022,9 @@ checksum = "2d67a5a62ba6e01cb2192ff309324cb4875d0c451d55fe2319433abe7a05a8ee" [[package]] name = "subtle" -version = "2.5.0" +version = "2.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "81cdd64d312baedb58e21336b31bc043b77e01cc99033ce76ef539f78e965ebc" +checksum = "13c2bddecc57b384dee18652358fb23172facb8a2c51ccc10d74c157bdea3292" [[package]] name = "subtle-ng" @@ -24316,7 +25045,6 @@ dependencies = [ "futures", "hex", "impl-serde", - "jsonrpsee", "parity-scale-codec", "polkadot-sdk 0.7.0", "primitive-types 0.13.1", @@ -24327,16 +25055,12 @@ dependencies = [ "scale-value 0.17.0", "serde", "serde_json", - "subxt-core 0.38.0", - "subxt-lightclient 0.38.0", - "subxt-macro 0.38.0", - "subxt-metadata 0.38.0", - "thiserror 1.0.65", - "tokio", - "tokio-util", + "subxt-core 0.38.1", + "subxt-macro 0.38.1", + "subxt-metadata 0.38.1", + "thiserror 1.0.69", "tracing", "url", - "wasm-bindgen-futures", "web-time", ] @@ -24367,8 +25091,45 @@ dependencies = [ "subxt-lightclient 0.41.0", "subxt-macro 0.41.0", "subxt-metadata 0.41.0", - "subxt-rpcs", - "thiserror 2.0.12", + "subxt-rpcs 0.41.0", + "thiserror 2.0.16", + "tokio", + "tokio-util", + "tracing", + "url", + "wasm-bindgen-futures", + "web-time", +] + +[[package]] +name = "subxt" +version = "0.43.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74791ddeaaa6de42e7cc8a715c83eb73303f513f90af701fd07eb2caad92ed84" +dependencies = [ + "async-trait", + "derive-where", + "either", + "frame-metadata 23.0.0", + "futures", + "hex", + "jsonrpsee", + "parity-scale-codec", + "primitive-types 0.13.1", + "scale-bits 0.7.0", + "scale-decode 0.16.0", + "scale-encode 0.10.0", + "scale-info", + "scale-value 0.18.0", + "serde", + "serde_json", + "sp-crypto-hashing 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "subxt-core 0.43.0", + "subxt-lightclient 0.43.0", + "subxt-macro 0.43.0", + "subxt-metadata 0.43.0", + "subxt-rpcs 0.43.0", + "thiserror 2.0.16", "tokio", "tokio-util", "tracing", @@ -24379,19 +25140,19 @@ dependencies = [ [[package]] name = "subxt-codegen" -version = "0.38.0" +version = "0.38.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3cfcfb7d9589f3df0ac87c4988661cf3fb370761fcb19f2fd33104cc59daf22a" +checksum = "6550ef451c77db6e3bc7c56fb6fe1dca9398a2c8fc774b127f6a396a769b9c5b" dependencies = [ "heck 0.5.0", "parity-scale-codec", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "scale-info", "scale-typegen 0.9.0", - "subxt-metadata 0.38.0", - "syn 2.0.98", - "thiserror 1.0.65", + "subxt-metadata 0.38.1", + "syn 2.0.106", + "thiserror 1.0.69", ] [[package]] @@ -24402,30 +25163,47 @@ checksum = "324c52c09919fec8c22a4b572a466878322e99fe14a9e3d50d6c3700a226ec25" dependencies = [ "heck 0.5.0", "parity-scale-codec", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "scale-info", "scale-typegen 0.11.1", "subxt-metadata 0.41.0", - "syn 2.0.98", - "thiserror 2.0.12", + "syn 2.0.106", + "thiserror 2.0.16", ] [[package]] -name = "subxt-core" -version = "0.38.0" +name = "subxt-codegen" +version = "0.43.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7ea28114366780d23684bd55ab879cd04c9d4cbba3b727a3854a3eca6bf29a1a" +checksum = "1728caecd9700391e78cc30dc298221d6f5ca0ea28258a452aa76b0b7c229842" dependencies = [ - "base58", - "blake2 0.10.6", - "derive-where", - "frame-decode 0.5.1", - "frame-metadata 17.0.0", - "hashbrown 0.14.5", - "hex", - "impl-serde", - "keccak-hash", + "heck 0.5.0", + "parity-scale-codec", + "proc-macro2 1.0.101", + "quote 1.0.40", + "scale-info", + "scale-typegen 0.11.1", + "subxt-metadata 0.43.0", + "syn 2.0.106", + "thiserror 2.0.16", +] + +[[package]] +name = "subxt-core" +version = "0.38.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb7a1bc6c9c1724971636a66e3225a7253cdb35bb6efb81524a6c71c04f08c59" +dependencies = [ + "base58", + "blake2 0.10.6", + "derive-where", + "frame-decode 0.5.1", + "frame-metadata 17.0.0", + "hashbrown 0.14.5", + "hex", + "impl-serde", + "keccak-hash", "parity-scale-codec", "polkadot-sdk 0.7.0", "primitive-types 0.13.1", @@ -24436,7 +25214,7 @@ dependencies = [ "scale-value 0.17.0", "serde", "serde_json", - "subxt-metadata 0.38.0", + "subxt-metadata 0.38.1", "tracing", ] @@ -24466,22 +25244,52 @@ dependencies = [ "serde_json", "sp-crypto-hashing 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", "subxt-metadata 0.41.0", - "thiserror 2.0.12", + "thiserror 2.0.16", + "tracing", +] + +[[package]] +name = "subxt-core" +version = "0.43.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "25338dd11ae34293b8d0c5807064f2e00194ba1bd84cccfa694030c8d185b941" +dependencies = [ + "base58", + "blake2 0.10.6", + "derive-where", + "frame-decode 0.8.3", + "frame-metadata 23.0.0", + "hashbrown 0.14.5", + "hex", + "impl-serde", + "keccak-hash", + "parity-scale-codec", + "primitive-types 0.13.1", + "scale-bits 0.7.0", + "scale-decode 0.16.0", + "scale-encode 0.10.0", + "scale-info", + "scale-value 0.18.0", + "serde", + "serde_json", + "sp-crypto-hashing 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "subxt-metadata 0.43.0", + "thiserror 2.0.16", "tracing", ] [[package]] name = "subxt-lightclient" -version = "0.38.0" +version = "0.41.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "534d4b725183a9fa09ce0e0f135674473297fdd97dee4d683f41117f365ae997" +checksum = "ce07c2515b2e63b85ec3043fe4461b287af0615d4832c2fe6e81ba780b906bc0" dependencies = [ "futures", "futures-util", "serde", "serde_json", "smoldot-light 0.16.2", - "thiserror 1.0.65", + "thiserror 2.0.16", "tokio", "tokio-stream", "tracing", @@ -24489,16 +25297,16 @@ dependencies = [ [[package]] name = "subxt-lightclient" -version = "0.41.0" +version = "0.43.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ce07c2515b2e63b85ec3043fe4461b287af0615d4832c2fe6e81ba780b906bc0" +checksum = "9097ef356e534ce0b6a50b95233512afc394347b971a4f929c4830adc52bbc6f" dependencies = [ "futures", "futures-util", "serde", "serde_json", - "smoldot-light 0.16.2", - "thiserror 2.0.12", + "smoldot-light 0.17.2", + "thiserror 2.0.16", "tokio", "tokio-stream", "tracing", @@ -24506,18 +25314,18 @@ dependencies = [ [[package]] name = "subxt-macro" -version = "0.38.0" +version = "0.38.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "228db9a5c95a6d8dc6152b4d6cdcbabc4f60821dd3f482a4f8791e022b7caadb" +checksum = "7819c5e09aae0319981ee853869f2fcd1fac4db8babd0d004c17161297aadc05" dependencies = [ "darling", "parity-scale-codec", "proc-macro-error2", "quote 1.0.40", "scale-typegen 0.9.0", - "subxt-codegen 0.38.0", - "subxt-utils-fetchmetadata 0.38.0", - "syn 2.0.98", + "subxt-codegen 0.38.1", + "subxt-utils-fetchmetadata 0.38.1", + "syn 2.0.106", ] [[package]] @@ -24533,14 +25341,31 @@ dependencies = [ "scale-typegen 0.11.1", "subxt-codegen 0.41.0", "subxt-utils-fetchmetadata 0.41.0", - "syn 2.0.98", + "syn 2.0.106", +] + +[[package]] +name = "subxt-macro" +version = "0.43.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "69516e8ff0e9340a0f21b8398da7f997571af4734ee81deada5150a2668c8443" +dependencies = [ + "darling", + "parity-scale-codec", + "proc-macro-error2", + "quote 1.0.40", + "scale-typegen 0.11.1", + "subxt-codegen 0.43.0", + "subxt-metadata 0.43.0", + "subxt-utils-fetchmetadata 0.43.0", + "syn 2.0.106", ] [[package]] name = "subxt-metadata" -version = "0.38.0" +version = "0.38.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ee13e6862eda035557d9a2871955306aff540d2b89c06e0a62a1136a700aed28" +checksum = "aacd4e7484fef58deaa2dcb32d94753a864b208a668c0dd0c28be1d8abeeadb2" dependencies = [ "frame-decode 0.5.1", "frame-metadata 17.0.0", @@ -24562,7 +25387,22 @@ dependencies = [ "parity-scale-codec", "scale-info", "sp-crypto-hashing 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "thiserror 2.0.12", + "thiserror 2.0.16", +] + +[[package]] +name = "subxt-metadata" +version = "0.43.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2c134068711c0c46906abc0e6e4911204420331530738e18ca903a5469364d9f" +dependencies = [ + "frame-decode 0.8.3", + "frame-metadata 23.0.0", + "hashbrown 0.14.5", + "parity-scale-codec", + "scale-info", + "sp-crypto-hashing 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "thiserror 2.0.16", ] [[package]] @@ -24572,7 +25412,6 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4ba7494d250d65dc3439365ac5e8e0fbb9c3992e6e84b7aa01d69e082249b8b8" dependencies = [ "derive-where", - "finito", "frame-metadata 20.0.0", "futures", "hex", @@ -24584,7 +25423,32 @@ dependencies = [ "serde_json", "subxt-core 0.41.0", "subxt-lightclient 0.41.0", - "thiserror 2.0.12", + "thiserror 2.0.16", + "tokio-util", + "tracing", + "url", +] + +[[package]] +name = "subxt-rpcs" +version = "0.43.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "25de7727144780d780a6a7d78bbfd28414b8adbab68b05e87329c367d7705be4" +dependencies = [ + "derive-where", + "finito", + "frame-metadata 23.0.0", + "futures", + "hex", + "impl-serde", + "jsonrpsee", + "parity-scale-codec", + "primitive-types 0.13.1", + "serde", + "serde_json", + "subxt-core 0.43.0", + "subxt-lightclient 0.43.0", + "thiserror 2.0.16", "tokio", "tokio-util", "tracing", @@ -24593,36 +25457,39 @@ dependencies = [ [[package]] name = "subxt-signer" -version = "0.38.0" +version = "0.41.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1e7a336d6a1f86f126100a4a717be58352de4c8214300c4f7807f974494efdb9" +checksum = "4a2370298a210ed1df26152db7209a85e0ed8cfbce035309c3b37f7b61755377" dependencies = [ "base64 0.22.1", + "bip32", "bip39", "cfg-if", "crypto_secretbox", "hex", "hmac 0.12.1", + "keccak-hash", "parity-scale-codec", "pbkdf2", - "polkadot-sdk 0.7.0", "regex", - "schnorrkel 0.11.4", + "schnorrkel 0.11.5", "scrypt", "secp256k1 0.30.0", "secrecy 0.10.3", "serde", "serde_json", - "sha2 0.10.8", - "subxt-core 0.38.0", + "sha2 0.10.9", + "sp-crypto-hashing 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", + "subxt-core 0.41.0", + "thiserror 2.0.16", "zeroize", ] [[package]] name = "subxt-signer" -version = "0.41.0" +version = "0.43.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4a2370298a210ed1df26152db7209a85e0ed8cfbce035309c3b37f7b61755377" +checksum = "9a9bd240ae819f64ac6898d7ec99a88c8b838dba2fb9d83b843feb70e77e34c8" dependencies = [ "base64 0.22.1", "bip32", @@ -24635,28 +25502,28 @@ dependencies = [ "parity-scale-codec", "pbkdf2", "regex", - "schnorrkel 0.11.4", + "schnorrkel 0.11.5", "scrypt", "secp256k1 0.30.0", "secrecy 0.10.3", "serde", "serde_json", - "sha2 0.10.8", + "sha2 0.10.9", "sp-crypto-hashing 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", - "subxt-core 0.41.0", - "thiserror 2.0.12", + "subxt-core 0.43.0", + "thiserror 2.0.16", "zeroize", ] [[package]] name = "subxt-utils-fetchmetadata" -version = "0.38.0" +version = "0.38.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3082b17a86e3c3fe45d858d94d68f6b5247caace193dad6201688f24db8ba9bb" +checksum = "a3c53bc3eeaacc143a2f29ace4082edd2edaccab37b69ad20befba9fb00fdb3d" dependencies = [ "hex", "parity-scale-codec", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] @@ -24667,20 +25534,31 @@ checksum = "fc868b55fe2303788dc7703457af390111940c3da4714b510983284501780ed5" dependencies = [ "hex", "parity-scale-codec", - "thiserror 2.0.12", + "thiserror 2.0.16", +] + +[[package]] +name = "subxt-utils-fetchmetadata" +version = "0.43.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8c4fb8fd6b16ecd3537a29d70699f329a68c1e47f70ed1a46d64f76719146563" +dependencies = [ + "hex", + "parity-scale-codec", + "thiserror 2.0.16", ] [[package]] name = "sval" -version = "2.6.1" +version = "2.14.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8b031320a434d3e9477ccf9b5756d57d4272937b8d22cb88af80b7633a1b78b1" +checksum = "7cc9739f56c5d0c44a5ed45473ec868af02eb896af8c05f616673a31e1d1bb09" [[package]] name = "sval_buffer" -version = "2.6.1" +version = "2.14.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6bf7e9412af26b342f3f2cc5cc4122b0105e9d16eb76046cd14ed10106cf6028" +checksum = "f39b07436a8c271b34dad5070c634d1d3d76d6776e938ee97b4a66a5e8003d0b" dependencies = [ "sval", "sval_ref", @@ -24688,18 +25566,18 @@ dependencies = [ [[package]] name = "sval_dynamic" -version = "2.6.1" +version = "2.14.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a0ef628e8a77a46ed3338db8d1b08af77495123cc229453084e47cd716d403cf" +checksum = "ffcb072d857431bf885580dacecf05ed987bac931230736739a79051dbf3499b" dependencies = [ "sval", ] [[package]] name = "sval_fmt" -version = "2.6.1" +version = "2.14.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7dc09e9364c2045ab5fa38f7b04d077b3359d30c4c2b3ec4bae67a358bd64326" +checksum = "3f214f427ad94a553e5ca5514c95c6be84667cbc5568cce957f03f3477d03d5c" dependencies = [ "itoa", "ryu", @@ -24708,53 +25586,63 @@ dependencies = [ [[package]] name = "sval_json" -version = "2.6.1" +version = "2.14.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ada6f627e38cbb8860283649509d87bc4a5771141daa41c78fd31f2b9485888d" +checksum = "389ed34b32e638dec9a99c8ac92d0aa1220d40041026b625474c2b6a4d6f4feb" dependencies = [ "itoa", "ryu", "sval", ] +[[package]] +name = "sval_nested" +version = "2.14.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "14bae8fcb2f24fee2c42c1f19037707f7c9a29a0cda936d2188d48a961c4bb2a" +dependencies = [ + "sval", + "sval_buffer", + "sval_ref", +] + [[package]] name = "sval_ref" -version = "2.6.1" +version = "2.14.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "703ca1942a984bd0d9b5a4c0a65ab8b4b794038d080af4eb303c71bc6bf22d7c" +checksum = "2a4eaea3821d3046dcba81d4b8489421da42961889902342691fb7eab491d79e" dependencies = [ "sval", ] [[package]] name = "sval_serde" -version = "2.6.1" +version = "2.14.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "830926cd0581f7c3e5d51efae4d35c6b6fc4db583842652891ba2f1bed8db046" +checksum = "172dd4aa8cb3b45c8ac8f3b4111d644cd26938b0643ede8f93070812b87fb339" dependencies = [ "serde", "sval", - "sval_buffer", - "sval_fmt", + "sval_nested", ] [[package]] name = "symbolic-common" -version = "12.14.1" +version = "12.16.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "66135c8273581acaab470356f808a1c74a707fe7ec24728af019d7247e089e71" +checksum = "9da12f8fecbbeaa1ee62c1d50dc656407e007c3ee7b2a41afce4b5089eaef15e" dependencies = [ "debugid", - "memmap2 0.9.3", + "memmap2 0.9.8", "stable_deref_trait", "uuid", ] [[package]] name = "symbolic-demangle" -version = "12.14.1" +version = "12.16.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "42bcacd080282a72e795864660b148392af7babd75691d5ae9a3b77e29c98c77" +checksum = "6fd35afe0ef9d35d3dcd41c67ddf882fc832a387221338153b7cd685a105495c" dependencies = [ "cpp_demangle", "rustc-demangle", @@ -24778,39 +25666,39 @@ version = "1.0.109" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "unicode-ident", ] [[package]] name = "syn" -version = "2.0.98" +version = "2.0.106" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "36147f1a48ae0ec2b5b3bc5b537d267457555a10dc06f3dbc8cb11ba3006d3b1" +checksum = "ede7c438028d4436d71104916910f5bb611972c5cfd7f89b8300a8186e6fada6" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "unicode-ident", ] [[package]] name = "syn-solidity" -version = "1.1.2" +version = "1.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1b5d879005cc1b5ba4e18665be9e9501d9da3a9b95f625497c4cb7ee082b532e" +checksum = "a0b198d366dbec045acfcd97295eb653a7a2b40e4dc764ef1e79aafcad439d3c" dependencies = [ "paste", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "sync_wrapper" -version = "1.0.1" +version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a7065abeca94b6a8a577f9bd45aa0867a2238b74e8eb67cf10d492bc39351394" +checksum = "0bf256ce5efdfa370213c1dabab5935a12e49f2c58d15e9eac2870d3b4f27263" dependencies = [ "futures-core", ] @@ -24821,28 +25709,28 @@ version = "0.12.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f36bdaa60a83aca3921b5259d5400cbf5e90fc51931376a9bd4a0eb79aa7210f" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "syn 1.0.109", - "unicode-xid 0.2.4", + "unicode-xid 0.2.6", ] [[package]] name = "synstructure" -version = "0.13.1" +version = "0.13.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c8af7666ab7b6390ab78131fb5b0fce11d6b7a6951602017c35fa82800708971" +checksum = "728a70f3dbaf5bab7f0c4b1ac8d7ae5ea60a4b5549c8a5914361c99147a709d2" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "sysinfo" -version = "0.30.5" +version = "0.30.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1fb4f3438c8f6389c864e61221cbc97e9bca98b4daf39a5beb7bea660f528bb2" +checksum = "0a5b4ddaee55fb2bea2bf0e5000747e5f5c0de765e5a5ff87f4cd106439f4bb3" dependencies = [ "cfg-if", "core-foundation-sys", @@ -24853,36 +25741,15 @@ dependencies = [ "windows 0.52.0", ] -[[package]] -name = "system-configuration" -version = "0.5.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ba3a3adc5c275d719af8cb4272ea1c4a6d668a777f37e115f6d11ddbc1c8e0e7" -dependencies = [ - "bitflags 1.3.2", - "core-foundation", - "system-configuration-sys 0.5.0", -] - [[package]] name = "system-configuration" version = "0.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3c879d448e9d986b661742763247d3693ed13609438cf3d006f51f5368a5ba6b" dependencies = [ - "bitflags 2.6.0", - "core-foundation", - "system-configuration-sys 0.6.0", -] - -[[package]] -name = "system-configuration-sys" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a75fb188eb626b924683e3b95e3a48e63551fcfb51949de2f06a9d91dbee93c9" -dependencies = [ - "core-foundation-sys", - "libc", + "bitflags 2.9.3", + "core-foundation 0.9.4", + "system-configuration-sys", ] [[package]] @@ -24909,9 +25776,9 @@ checksum = "55937e1799185b12863d447f42597ed69d9928686b8d88a1df17376a097d8369" [[package]] name = "tar" -version = "0.4.40" +version = "0.4.44" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b16afcea1f22891c49a00c751c7b63b2233284064f11a200fc624137c51e2ddb" +checksum = "1d863878d212c87a19c1a610eb53bb01fe12951c0501cf5a0d65f724914a667a" dependencies = [ "filetime", "libc", @@ -24926,21 +25793,21 @@ checksum = "e502f78cdbb8ba4718f566c418c52bc729126ffd16baee5baa718cf25dd5a69a" [[package]] name = "target-triple" -version = "0.1.3" +version = "0.1.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "42a4d50cdb458045afc8131fd91b64904da29548bcb63c7236e0844936c13078" +checksum = "1ac9aa371f599d22256307c24a9d748c041e548cbf599f35d890f9d365361790" [[package]] name = "tempfile" -version = "3.14.0" +version = "3.21.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "28cce251fcbc87fac86a866eeb0d6c2d536fc16d06f184bb61aeae11aa4cee0c" +checksum = "15b61f8f20e3a6f7e0649d825294eaf317edce30f82cf6026e7e4cb9222a7d1e" dependencies = [ - "cfg-if", "fastrand 2.3.0", + "getrandom 0.3.3", "once_cell", - "rustix 0.38.42", - "windows-sys 0.59.0", + "rustix 1.0.8", + "windows-sys 0.60.2", ] [[package]] @@ -24948,28 +25815,28 @@ name = "template-zombienet-tests" version = "0.0.0" dependencies = [ "anyhow", - "env_logger 0.11.3", + "env_logger 0.11.8", "tokio", "zombienet-sdk", ] [[package]] name = "termcolor" -version = "1.2.0" +version = "1.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "be55cf8942feac5c765c2c993422806843c9a9a45d4d5c407ad6dd2ea95eb9b6" +checksum = "06794f8f6c5c898b3275aebefa6b8a1cb24cd2c6c79397ab15774837a0bc5755" dependencies = [ "winapi-util", ] [[package]] name = "terminal_size" -version = "0.3.0" +version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "21bebf2b7c9e0a515f6e0f8c51dc0f8e4696391e6f1ff30379559f8365fb0df7" +checksum = "60b8cb979cb11c32ce1603f8137b22262a9d131aaa5c37b5678025f22b8becd0" dependencies = [ - "rustix 0.38.42", - "windows-sys 0.48.0", + "rustix 1.0.8", + "windows-sys 0.60.2", ] [[package]] @@ -24983,9 +25850,9 @@ dependencies = [ [[package]] name = "termtree" -version = "0.4.1" +version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3369f5ac52d5eb6ab48c6b4ffdc8efbcad6b89c765749064ba298f2c68a16a76" +checksum = "8f50febec83f5ee1df3015341d8bd429f2d1cc62bcba7ea2076759d315084683" [[package]] name = "test-log" @@ -24993,9 +25860,9 @@ version = "0.2.18" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1e33b98a582ea0be1168eba097538ee8dd4bbe0f2b01b22ac92ea30054e5be7b" dependencies = [ - "env_logger 0.11.3", + "env_logger 0.11.8", "test-log-macros", - "tracing-subscriber", + "tracing-subscriber 0.3.19", ] [[package]] @@ -25004,9 +25871,9 @@ version = "0.2.18" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "451b374529930d7601b1eef8d32bc79ae870b6079b069401709c2a8bf9e75f36" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -25121,62 +25988,62 @@ dependencies = [ [[package]] name = "thiserror" -version = "1.0.65" +version = "1.0.69" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5d11abd9594d9b38965ef50805c5e469ca9cc6f197f883f717e0269a3057b3d5" +checksum = "b6aaf5339b578ea85b50e080feb250a3e8ae8cfcdff9a461c9ec2904bc923f52" dependencies = [ - "thiserror-impl 1.0.65", + "thiserror-impl 1.0.69", ] [[package]] name = "thiserror" -version = "2.0.12" +version = "2.0.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "567b8a2dae586314f7be2a752ec7474332959c6460e02bde30d702a66d488708" +checksum = "3467d614147380f2e4e374161426ff399c91084acd2363eaf549172b3d5e60c0" dependencies = [ - "thiserror-impl 2.0.12", + "thiserror-impl 2.0.16", ] [[package]] name = "thiserror-core" -version = "1.0.38" +version = "1.0.50" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d97345f6437bb2004cd58819d8a9ef8e36cdd7661c2abc4bbde0a7c40d9f497" +checksum = "c001ee18b7e5e3f62cbf58c7fe220119e68d902bb7443179c0c8aef30090e999" dependencies = [ "thiserror-core-impl", ] [[package]] name = "thiserror-core-impl" -version = "1.0.38" +version = "1.0.50" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "10ac1c5050e43014d16b2f94d0d2ce79e65ffdd8b38d8048f9c8f6a8a6da62ac" +checksum = "e4c60d69f36615a077cc7663b9cb8e42275722d23e58a7fa3d2c7f2915d09d04" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 1.0.109", + "syn 2.0.106", ] [[package]] name = "thiserror-impl" -version = "1.0.65" +version = "1.0.69" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ae71770322cbd277e69d762a16c444af02aa0575ac0d174f0b9562d3b37f8602" +checksum = "4fee6c4efc90059e10f81e6d42c60a18f76588c3d74cb83a0b242a2b6c7504c1" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "thiserror-impl" -version = "2.0.12" +version = "2.0.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7f7cf42b4507d8ea322120659672cf1b9dbb93f8f2d4ecfd6e51350ff5b17a1d" +checksum = "6c5e1be1c48b9172ee610da68fd9cd2770e7a4056cb3fc98710ee6906f0c7960" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -25187,12 +26054,11 @@ checksum = "3bf63baf9f5039dadc247375c29eb13706706cfde997d0330d05aa63a77d8820" [[package]] name = "thread_local" -version = "1.1.7" +version = "1.1.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3fdd6f064ccff2d6567adcb3873ca630700f00b5ad3f060c25b5dcfd9a4ce152" +checksum = "f60246a4944f24f6e018aa17cdeffb7818b76356965d03b07d6a9886e8962185" dependencies = [ "cfg-if", - "once_cell", ] [[package]] @@ -25237,9 +26103,9 @@ dependencies = [ [[package]] name = "time" -version = "0.3.36" +version = "0.3.41" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5dfd88e563464686c916c7e46e623e520ddc6d79fa6641390f2e3fa86e83e885" +checksum = "8a7619e19bc266e0f9c5e6686659d394bc57973859340060a69221e57dbc0c40" dependencies = [ "deranged", "itoa", @@ -25254,15 +26120,15 @@ dependencies = [ [[package]] name = "time-core" -version = "0.1.2" +version = "0.1.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ef927ca75afb808a4d64dd374f00a2adf8d0fcff8e7b184af886c3c87ec4a3f3" +checksum = "c9e9a38711f559d9e3ce1cdb06dd7c5b8ea546bc90052da6d06bb76da74bb07c" [[package]] name = "time-macros" -version = "0.2.18" +version = "0.2.22" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3f252a68540fde3a3877aeea552b832b40ab9a69e318efd078774a01ddee1ccf" +checksum = "3526739392ec93fd8b359c8e98514cb3e8e021beb4e5f597b00a0221f8ed8a49" dependencies = [ "num-conv", "time-core", @@ -25279,9 +26145,9 @@ dependencies = [ [[package]] name = "tinystr" -version = "0.7.6" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9117f5d4db391c1cf6927e7bea3db74b9a1c1add8f7eda9ffd5364f40f57b82f" +checksum = "5d4f6d1145dcb577acf783d4e601bc1d76a13337bb54e6233add580b07344c8b" dependencies = [ "displaydoc", "zerovec", @@ -25299,9 +26165,9 @@ dependencies = [ [[package]] name = "tinyvec" -version = "1.6.0" +version = "1.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "87cc5ceb3875bb20c2890005a4e226a4651264a5c75edb2421b52861a0a0cb50" +checksum = "bfa5fdc3bce6191a1dbc8c02d5c8bffcf557bafa17c124c5264a458f1b0613fa" dependencies = [ "tinyvec_macros", ] @@ -25314,27 +26180,29 @@ checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" [[package]] name = "tokio" -version = "1.45.0" +version = "1.47.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2513ca694ef9ede0fb23fe71a4ee4107cb102b9dc1930f6d0fd77aae068ae165" +checksum = "89e49afdadebb872d3145a5638b59eb0691ea23e46ca484037cfab3b76b95038" dependencies = [ "backtrace", "bytes", + "io-uring", "libc", "mio", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project-lite", "signal-hook-registry", - "socket2 0.5.9", + "slab", + "socket2 0.6.0", "tokio-macros", - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] name = "tokio-io-timeout" -version = "1.2.0" +version = "1.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "30b74022ada614a1b4834de765f9bb43877f910cc8ce4be40e89042c9223a8bf" +checksum = "0bd86198d9ee903fedd2f9a2e72014287c0d9167e4ae43b5853007205dda1b76" dependencies = [ "pin-project-lite", "tokio", @@ -25346,9 +26214,9 @@ version = "2.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6e06d43f1345a3bcd39f6a56dbb7dcab2ba47e68e8ac134855e7e2bdbaf8cab8" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -25378,26 +26246,25 @@ version = "0.24.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c28327cf380ac148141087fbfb9de9d7bd4e84ab5d2c28fbc911d753de8a7081" dependencies = [ - "rustls 0.21.7", + "rustls 0.21.12", "tokio", ] [[package]] name = "tokio-rustls" -version = "0.26.0" +version = "0.26.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0c7bc40d0e5a97695bb96e27995cd3a08538541b0a846f65bba7a359f36700d4" +checksum = "8e727b36a1a0e8b74c376ac2211e40c2c8af09fb4013c60d910495810f008e9b" dependencies = [ - "rustls 0.23.18", - "rustls-pki-types", + "rustls 0.23.31", "tokio", ] [[package]] name = "tokio-stream" -version = "0.1.16" +version = "0.1.17" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4f4e6ce100d0eb49a2734f8c0812bcd324cf357d21810932c5df6b96ef2b86f1" +checksum = "eca58d7bba4a75707817a2c44174253f9236b2d5fbd055602e9d5c07c139a047" dependencies = [ "futures-core", "pin-project-lite", @@ -25450,19 +26317,19 @@ checksum = "489a59b6730eda1b0171fcfda8b121f4bee2b35cba8645ca35c5f7ba3eb736c1" dependencies = [ "futures-util", "log", - "rustls 0.23.18", - "rustls-native-certs 0.8.0", + "rustls 0.23.31", + "rustls-native-certs 0.8.1", "rustls-pki-types", "tokio", - "tokio-rustls 0.26.0", + "tokio-rustls 0.26.2", "tungstenite 0.27.0", ] [[package]] name = "tokio-util" -version = "0.7.15" +version = "0.7.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "66a539a9ad6d5d281510d5bd368c973d636c02dbf8a67300bfb6b950696ad7df" +checksum = "14307c986784f72ef81c89db7d9e28d6ac26d16213b109ea501696195e6e3ce5" dependencies = [ "bytes", "futures-core", @@ -25475,21 +26342,54 @@ dependencies = [ [[package]] name = "toml" -version = "0.8.19" +version = "0.5.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f4f7f0dd8d50a853a531c426359045b1998f04219d88799810762cd4ad314234" +dependencies = [ + "serde", +] + +[[package]] +name = "toml" +version = "0.8.23" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dc1beb996b9d83529a9e75c17a1686767d148d70663143c7854d8b4a09ced362" +dependencies = [ + "serde", + "serde_spanned 0.6.9", + "toml_datetime 0.6.11", + "toml_edit 0.22.27", +] + +[[package]] +name = "toml" +version = "0.9.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "75129e1dc5000bfbaa9fee9d1b21f974f9fbad9daec557a521ee6e080825f6e8" +dependencies = [ + "indexmap", + "serde", + "serde_spanned 1.0.0", + "toml_datetime 0.7.0", + "toml_parser", + "toml_writer", + "winnow 0.7.13", +] + +[[package]] +name = "toml_datetime" +version = "0.6.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a1ed1f98e3fdc28d6d910e6737ae6ab1a93bf1985935a1193e68f93eeb68d24e" +checksum = "22cddaf88f4fbc13c51aebbf5f8eceb5c7c5a9da2ac40a13519eb5b0a0e8f11c" dependencies = [ "serde", - "serde_spanned", - "toml_datetime", - "toml_edit 0.22.22", ] [[package]] name = "toml_datetime" -version = "0.6.8" +version = "0.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0dd7358ecb8fc2f8d014bf86f6f638ce72ba252a2c3a2572f2a795f1d23efb41" +checksum = "bade1c3e902f58d73d3f294cd7f20391c1cb2fbcb643b73566bc773971df91e3" dependencies = [ "serde", ] @@ -25501,34 +26401,45 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1b5bb770da30e5cbfde35a2d7b9b8a2c4b8ef89548a7a6aeab5c9a576e3e7421" dependencies = [ "indexmap", - "toml_datetime", - "winnow 0.5.15", + "toml_datetime 0.6.11", + "winnow 0.5.40", ] [[package]] name = "toml_edit" -version = "0.21.0" +version = "0.22.27" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d34d383cd00a163b4a5b85053df514d45bc330f6de7737edfe0a93311d1eaa03" +checksum = "41fe8c660ae4257887cf66394862d21dbca4a6ddd26f04a3560410406a2f819a" dependencies = [ "indexmap", - "toml_datetime", - "winnow 0.5.15", + "serde", + "serde_spanned 0.6.9", + "toml_datetime 0.6.11", + "toml_write", + "winnow 0.7.13", ] [[package]] -name = "toml_edit" -version = "0.22.22" +name = "toml_parser" +version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4ae48d6208a266e853d946088ed816055e556cc6028c5e8e2b84d9fa5dd7c7f5" +checksum = "b551886f449aa90d4fe2bdaa9f4a2577ad2dde302c61ecf262d80b116db95c10" dependencies = [ - "indexmap", - "serde", - "serde_spanned", - "toml_datetime", - "winnow 0.6.18", + "winnow 0.7.13", ] +[[package]] +name = "toml_write" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5d99f8c9a7727884afe522e9bd5edbfc91a3312b36a77b5fb8926e4c31a41801" + +[[package]] +name = "toml_writer" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fcc842091f2def52017664b53082ecbbeb5c7731092bad69d2c63050401dfd64" + [[package]] name = "tower" version = "0.4.13" @@ -25546,6 +26457,21 @@ dependencies = [ "tracing", ] +[[package]] +name = "tower" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d039ad9159c98b70ecfd540b2573b97f7f52c3e8d9f8ad57a24b916a536975f9" +dependencies = [ + "futures-core", + "futures-util", + "pin-project-lite", + "sync_wrapper", + "tokio", + "tower-layer", + "tower-service", +] + [[package]] name = "tower-http" version = "0.4.4" @@ -25553,12 +26479,12 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "61c5bb1d698276a2443e5ecfabc1008bf15a36c12e6a7176e7bf089ea9131140" dependencies = [ "base64 0.21.7", - "bitflags 2.6.0", + "bitflags 2.9.3", "bytes", "futures-core", "futures-util", - "http 0.2.9", - "http-body 0.4.5", + "http 0.2.12", + "http-body 0.4.6", "http-range-header", "mime", "pin-project-lite", @@ -25573,33 +26499,51 @@ version = "0.5.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1e9cd434a998747dd2c4276bc96ee2e0c7a2eadf3cae88e52be55a05fa9053f5" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", "bytes", - "http 1.1.0", - "http-body 1.0.0", + "http 1.3.1", + "http-body 1.0.1", "http-body-util", "pin-project-lite", "tower-layer", "tower-service", ] +[[package]] +name = "tower-http" +version = "0.6.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "adc82fd73de2a9722ac5da747f12383d2bfdb93591ee6c58486e0097890f05f2" +dependencies = [ + "bitflags 2.9.3", + "bytes", + "futures-util", + "http 1.3.1", + "http-body 1.0.1", + "iri-string", + "pin-project-lite", + "tower 0.5.2", + "tower-layer", + "tower-service", +] + [[package]] name = "tower-layer" -version = "0.3.2" +version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c20c8dbed6283a09604c3e69b4b7eeb54e298b8a600d4d5ecb5ad39de609f1d0" +checksum = "121c2a6cda46980bb0fcd1647ffaf6cd3fc79a013de288782836f6df9c48780e" [[package]] name = "tower-service" -version = "0.3.2" +version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b6bc1c9ce2b5135ac7f93c72918fc37feb872bdc6a5533a8b85eb4b86bfdae52" +checksum = "8df9b6e13f2d32c91b9bd719c00d1958837bc7dec474d94952798cc8e69eeec3" [[package]] name = "tracing" -version = "0.1.40" +version = "0.1.41" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c3523ab5a71916ccf420eebdf5521fcef02141234bbc0b8a49f2fdc4544364ef" +checksum = "784e0ac535deb450455cbfa28a6f0df145ea1bb7ae51b821cf5e7927fdcfbdd0" dependencies = [ "log", "pin-project-lite", @@ -25609,20 +26553,20 @@ dependencies = [ [[package]] name = "tracing-attributes" -version = "0.1.27" +version = "0.1.30" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "34704c8d6ebcbc939824180af020566b01a7c01f80641264eba0999f6c2b6be7" +checksum = "81383ab64e72a7a8b8e13130c49e3dab29def6d0c7d76a03087b3cf71c5c6903" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "tracing-core" -version = "0.1.32" +version = "0.1.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c06d3da6113f116aaee68e4d601191614c9053067f9ab7f6edbcb161237daa54" +checksum = "b9d12581f227e93f094d3af2ae690a574abb8a2b9b7a96e7cfe9647b2b617678" dependencies = [ "once_cell", "valuable", @@ -25654,10 +26598,10 @@ version = "5.0.0" dependencies = [ "assert_matches", "expander", - "proc-macro-crate 3.1.0", - "proc-macro2 1.0.95", + "proc-macro-crate 3.3.0", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -25673,15 +26617,24 @@ dependencies = [ [[package]] name = "tracing-subscriber" -version = "0.3.18" +version = "0.2.25" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0e0d2eaa99c3c2e41547cfa109e910a68ea03823cccad4a0525dcbc9b01e8c71" +dependencies = [ + "tracing-core", +] + +[[package]] +name = "tracing-subscriber" +version = "0.3.19" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ad0f048c97dbd9faa9b7df56362b8ebcaa52adb06b498c050d2f4e32f90a7a8b" +checksum = "e8189decb5ac0fa7bc8b96b7cb9b2701d60d48805aca84a238004d665fcc4008" dependencies = [ "chrono", "matchers", "nu-ansi-term", "once_cell", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "regex", "sharded-slab", "smallvec", @@ -25741,15 +26694,15 @@ dependencies = [ [[package]] name = "try-lock" -version = "0.2.4" +version = "0.2.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3528ecfd12c466c6f163363caf2d02a71161dd5e1cc6ae7b34207ea2d42d81ed" +checksum = "e421abadd41a4225275504ea4d6566923418b7f05506fbc9c0fe86ba7396114b" [[package]] name = "trybuild" -version = "1.0.103" +version = "1.0.110" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b812699e0c4f813b872b373a4471717d9eb550da14b311058a4d9cf4173cbca6" +checksum = "32e257d7246e7a9fd015fb0b28b330a8d4142151a33f03e6a497754f4b1f6a8e" dependencies = [ "dissimilar", "glob", @@ -25758,7 +26711,7 @@ dependencies = [ "serde_json", "target-triple", "termcolor", - "toml", + "toml 0.9.5", ] [[package]] @@ -25776,12 +26729,12 @@ dependencies = [ "byteorder", "bytes", "data-encoding", - "http 0.2.9", + "http 0.2.12", "httparse", "log", "rand 0.8.5", "sha1", - "thiserror 1.0.65", + "thiserror 1.0.69", "url", "utf-8", ] @@ -25794,12 +26747,12 @@ checksum = "4793cb5e56680ecbb1d843515b23b6de9a75eb04b66643e256a396d43be33c13" dependencies = [ "bytes", "data-encoding", - "http 1.1.0", + "http 1.3.1", "httparse", "log", - "rand 0.9.0", + "rand 0.9.2", "sha1", - "thiserror 2.0.12", + "thiserror 2.0.16", "utf-8", ] @@ -25811,14 +26764,14 @@ checksum = "eadc29d668c91fcc564941132e17b28a7ceb2f3ebf0b9dae3e03fd7a6748eb0d" dependencies = [ "bytes", "data-encoding", - "http 1.1.0", + "http 1.3.1", "httparse", "log", - "rand 0.9.0", - "rustls 0.23.18", + "rand 0.9.2", + "rustls 0.23.31", "rustls-pki-types", "sha1", - "thiserror 2.0.12", + "thiserror 2.0.16", "url", "utf-8", ] @@ -25841,17 +26794,29 @@ dependencies = [ "static_assertions", ] +[[package]] +name = "twox-hash" +version = "2.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8b907da542cbced5261bd3256de1b3a1bf340a3d37f93425a07362a1d687de56" + +[[package]] +name = "typeid" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bc7d623258602320d5c55d1bc22793b57daff0ec7efc270ea7d55ce1d5f5471c" + [[package]] name = "typenum" -version = "1.16.0" +version = "1.18.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "497961ef93d974e23eb6f433eb5fe1b7930b659f06d12dec6fc44a8f554c0bba" +checksum = "1dccffe3ce07af9386bfd29e80c0ab1a8205a2fc34e4bcd40364df902cfa8f3f" [[package]] name = "ucd-trie" -version = "0.1.6" +version = "0.1.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ed646292ffc8188ef8ea4d1e0e0150fb15a5c2e12ad9b8fc191ae7a8a7f3c4b9" +checksum = "2896d95c02a80c6d6a5d6e953d479f5ddf2dfdb6a244441010e373ac0fb88971" [[package]] name = "uint" @@ -25885,15 +26850,15 @@ checksum = "eaea85b334db583fe3274d12b4cd1880032beab409c0d774be044d4480ab9a94" [[package]] name = "unicode-bidi" -version = "0.3.13" +version = "0.3.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "92888ba5573ff080736b3648696b70cafad7d250551175acbaa4e0385b3e1460" +checksum = "5c1cb5db39152898a79168971543b1cb5020dff7fe43c8dc468b0885f5e29df5" [[package]] name = "unicode-ident" -version = "1.0.11" +version = "1.0.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "301abaae475aa91687eb82514b328ab47a211a533026cb25fc3e519b86adfc3c" +checksum = "5a5f39404a5da50712a4c1eecf25e90dd62b613502b7e925fd4e4d19b5c96512" [[package]] name = "unicode-normalization" @@ -25912,21 +26877,15 @@ checksum = "e70f2a8b45122e719eb623c01822704c4e0907e7e426a05927e1a1cfff5b75d0" [[package]] name = "unicode-segmentation" -version = "1.11.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d4c87d22b6e3f4a18d4d40ef354e97c90fcb14dd91d7dc0aa9d8a1172ebf7202" - -[[package]] -name = "unicode-width" -version = "0.1.10" +version = "1.12.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c0edd1e5b14653f783770bce4a4dabb4a5108a5370a5f5d8cfe8710c361f6c8b" +checksum = "f6ccf251212114b54433ec949fd6a7841275f9ada20dddd2f29e9ceea4501493" [[package]] name = "unicode-width" -version = "0.2.0" +version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1fc81956842c57dac11422a97c3b8195a1ff727f06e85c84ed2e8aa277c9a0fd" +checksum = "4a1a07cc7db3810833284e8d372ccdc6da29741639ecc70c9ec107df0fa6154c" [[package]] name = "unicode-xid" @@ -25936,15 +26895,9 @@ checksum = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc" [[package]] name = "unicode-xid" -version = "0.2.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f962df74c8c05a667b5ee8bcf162993134c104e96440b663c8daa176dc772d8c" - -[[package]] -name = "unicode_categories" -version = "0.1.1" +version = "0.2.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "39ec24b3121d976906ece63c9daad25b85969647682eee313cb5779fdd69e14e" +checksum = "ebc1c04c71510c7f702b52b7c350734c9ff1295c464a03335b00bb84fc54f853" [[package]] name = "universal-hash" @@ -25953,7 +26906,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fc1de2c688dc15305988b563c3854064043356019f97a4b46276fe734c4f07ea" dependencies = [ "crypto-common", - "subtle 2.5.0", + "subtle 2.6.1", ] [[package]] @@ -25998,12 +26951,12 @@ checksum = "8ecb6da28b8a351d773b68d5825ac39017e680750f980f3a1a85cd8dd28a47c1" [[package]] name = "url" -version = "2.5.4" +version = "2.5.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "32f8b686cadd1473f4bd0117a5d28d36b1ade384ea9b5069a1c40aefed7fda60" +checksum = "08bc136a29a3d1758e07a9cca267be308aeebf5cfd5a10f3f67ab2097683ef5b" dependencies = [ "form_urlencoded", - "idna 1.0.3", + "idna", "percent-encoding", "serde", ] @@ -26014,12 +26967,6 @@ version = "0.7.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "09cc8ee72d2a9becf2f2febe0205bbed8fc6615b7cb429ad062dc7b7ddd036a9" -[[package]] -name = "utf16_iter" -version = "1.0.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c8232dd3cdaed5356e0f716d285e4b40b932ac434100fe9b7e0e8e935b9e6246" - [[package]] name = "utf8_iter" version = "1.0.4" @@ -26028,30 +26975,32 @@ checksum = "b6c140620e7ffbb22c2dee59cafe6084a59b5ffc27a8859a5f0d494b5d52b6be" [[package]] name = "utf8parse" -version = "0.2.1" +version = "0.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a" +checksum = "06abde3611657adf66d383f00b093d7faecc7fa57071cce2578660c9f1010821" [[package]] name = "uuid" -version = "1.4.1" +version = "1.18.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "79daa5ed5740825c40b389c5e50312b9c86df53fccd33f281df655642b43869d" +checksum = "f33196643e165781c20a5ead5582283a7dacbb87855d867fbc2df3f81eddc1be" dependencies = [ - "getrandom 0.2.10", + "getrandom 0.3.3", + "js-sys", + "wasm-bindgen", ] [[package]] name = "valuable" -version = "0.1.0" +version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "830b7e5d4d90034032940e4ace0d9a9a057e7a45cd94e6c007832e39edb82f6d" +checksum = "ba73ea9cf16a25df0c8caa16c51acb937d5712a8429db78a3ee29d5dcacd3a65" [[package]] name = "value-bag" -version = "1.8.0" +version = "1.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8fec26a25bd6fca441cdd0f769fd7f891bae119f996de31f86a5eddccef54c1d" +checksum = "943ce29a8a743eb10d6082545d861b24f9d1b160b7d741e0f2cdf726bec909c5" dependencies = [ "value-bag-serde1", "value-bag-sval2", @@ -26059,9 +27008,9 @@ dependencies = [ [[package]] name = "value-bag-serde1" -version = "1.8.0" +version = "1.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ead5b693d906686203f19a49e88c477fb8c15798b68cf72f60b4b5521b4ad891" +checksum = "35540706617d373b118d550d41f5dfe0b78a0c195dc13c6815e92e2638432306" dependencies = [ "erased-serde", "serde", @@ -26070,9 +27019,9 @@ dependencies = [ [[package]] name = "value-bag-sval2" -version = "1.8.0" +version = "1.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3b9d0f4a816370c3a0d7d82d603b62198af17675b12fe5e91de6b47ceb505882" +checksum = "6fe7e140a2658cc16f7ee7a86e413e803fc8f9b5127adc8755c19f9fefa63a52" dependencies = [ "sval", "sval_buffer", @@ -26108,9 +27057,9 @@ dependencies = [ [[package]] name = "version_check" -version = "0.9.4" +version = "0.9.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" +checksum = "0b928f33d975fc6ad9f86c8f283853ad26bdd5b10b7f1542aa2fa15e2289105a" [[package]] name = "void" @@ -26135,7 +27084,7 @@ dependencies = [ "rand 0.8.5", "rand_chacha 0.3.1", "rand_core 0.6.4", - "sha2 0.10.8", + "sha2 0.10.9", "sha3", "zeroize", ] @@ -26191,18 +27140,18 @@ dependencies = [ [[package]] name = "wait-timeout" -version = "0.2.0" +version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9f200f5b12eb75f8c1ed65abd4b2db8a6e1b138a20de009dacee265a2498f3f6" +checksum = "09ac3b126d3914f9849036f826e054cbabdc8519970b8998ddaf3b5bd3c65f11" dependencies = [ "libc", ] [[package]] name = "waker-fn" -version = "1.1.0" +version = "1.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9d5b2c62b4012a3e1eca5a7e077d13b3bf498c4073e33ccd58626607748ceeca" +checksum = "317211a0dc0ceedd78fb2ca9a44aed3d7b9b26f81870d485c07122b4350673b7" [[package]] name = "walkdir" @@ -26225,15 +27174,15 @@ dependencies = [ [[package]] name = "wasi" -version = "0.11.0+wasi-snapshot-preview1" +version = "0.11.1+wasi-snapshot-preview1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" +checksum = "ccf3ec651a847eb01de73ccad15eb7d99f80485de043efb2f370cd654f4ea44b" [[package]] name = "wasi" -version = "0.13.3+wasi-0.2.2" +version = "0.14.2+wasi-0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "26816d2e1a4a36a2940b96c5296ce403917633dff8f3440e9b236ed6f6bacad2" +checksum = "9683f9a5a998d873c0d21fcbe3c083009670149a8fab228644b8bd36b2c48cb3" dependencies = [ "wit-bindgen-rt", ] @@ -26244,14 +27193,24 @@ version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b8dad83b4f25e74f184f64c43b150b91efe7647395b42289f38e50566d82855b" +[[package]] +name = "wasix" +version = "0.12.21" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1fbb4ef9bbca0c1170e0b00dd28abc9e3b68669821600cad1caaed606583c6d" +dependencies = [ + "wasi 0.11.1+wasi-snapshot-preview1", +] + [[package]] name = "wasm-bindgen" -version = "0.2.95" +version = "0.2.100" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "128d1e363af62632b8eb57219c8fd7877144af57558fb2ef0368d0087bddeb2e" +checksum = "1edc8929d7499fc4e8f0be2262a241556cfc54a0bea223790e71446f2aab1ef5" dependencies = [ "cfg-if", "once_cell", + "rustversion", "serde", "serde_json", "wasm-bindgen-macro", @@ -26259,36 +27218,36 @@ dependencies = [ [[package]] name = "wasm-bindgen-backend" -version = "0.2.95" +version = "0.2.100" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cb6dd4d3ca0ddffd1dd1c9c04f94b868c37ff5fac97c30b97cff2d74fce3a358" +checksum = "2f0a0651a5c2bc21487bde11ee802ccaf4c51935d0d3d42a6101f98161700bc6" dependencies = [ "bumpalo", "log", - "once_cell", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", "wasm-bindgen-shared", ] [[package]] name = "wasm-bindgen-futures" -version = "0.4.45" +version = "0.4.50" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cc7ec4f8827a71586374db3e87abdb5a2bb3a15afed140221307c3ec06b1f63b" +checksum = "555d470ec0bc3bb57890405e5d4322cc9ea83cebb085523ced7be4144dac1e61" dependencies = [ "cfg-if", "js-sys", + "once_cell", "wasm-bindgen", "web-sys", ] [[package]] name = "wasm-bindgen-macro" -version = "0.2.95" +version = "0.2.100" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e79384be7f8f5a9dd5d7167216f022090cf1f9ec128e6e6a482a2cb5c5422c56" +checksum = "7fe63fc6d09ed3792bd0897b314f53de8e16568c2b3f7982f468c0bf9bd0b407" dependencies = [ "quote 1.0.40", "wasm-bindgen-macro-support", @@ -26296,40 +27255,44 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro-support" -version = "0.2.95" +version = "0.2.100" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "26c6ab57572f7a24a4985830b120de1594465e5d500f24afe89e16b4e833ef68" +checksum = "8ae87ea40c9f689fc23f209965b6fb8a99ad69aeeb0231408be24920604395de" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", "wasm-bindgen-backend", "wasm-bindgen-shared", ] [[package]] name = "wasm-bindgen-shared" -version = "0.2.95" +version = "0.2.100" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "65fc09f10666a9f147042251e0dda9c18f166ff7de300607007e96bdebc1068d" +checksum = "1a05d73b933a847d6cccdda8f838a22ff101ad9bf93e33684f39c1f5f0eece3d" +dependencies = [ + "unicode-ident", +] [[package]] name = "wasm-encoder" -version = "0.31.1" +version = "0.235.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "41763f20eafed1399fff1afb466496d3a959f58241436cfdc17e3f5ca954de16" +checksum = "b3bc393c395cb621367ff02d854179882b9a351b4e0c93d1397e6090b53a5c2a" dependencies = [ - "leb128", + "leb128fmt", + "wasmparser 0.235.0", ] [[package]] name = "wasm-encoder" -version = "0.235.0" +version = "0.237.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b3bc393c395cb621367ff02d854179882b9a351b4e0c93d1397e6090b53a5c2a" +checksum = "efe92d1321afa53ffc88a57c497bb7330c3cf84c98ffdba4a4caf6a0684fad3c" dependencies = [ "leb128fmt", - "wasmparser", + "wasmparser 0.237.0", ] [[package]] @@ -26343,16 +27306,16 @@ dependencies = [ [[package]] name = "wasm-opt" -version = "0.116.0" +version = "0.116.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fc942673e7684671f0c5708fc18993569d184265fd5223bb51fc8e5b9b6cfd52" +checksum = "2fd87a4c135535ffed86123b6fb0f0a5a0bc89e50416c942c5f0662c645f679c" dependencies = [ "anyhow", "libc", "strum 0.24.1", "strum_macros 0.24.3", "tempfile", - "thiserror 1.0.65", + "thiserror 1.0.69", "wasm-opt-cxx-sys", "wasm-opt-sys", ] @@ -26415,17 +27378,33 @@ version = "0.32.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "50386c99b9c32bd2ed71a55b6dd4040af2580530fae8bdb9a6576571a80d0cca" dependencies = [ - "arrayvec 0.7.4", + "arrayvec 0.7.6", "multi-stash", "num-derive", "num-traits", "smallvec", "spin 0.9.8", - "wasmi_collections", + "wasmi_collections 0.32.3", "wasmi_core 0.32.3", "wasmparser-nostd", ] +[[package]] +name = "wasmi" +version = "0.40.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a19af97fcb96045dd1d6b4d23e2b4abdbbe81723dbc5c9f016eb52145b320063" +dependencies = [ + "arrayvec 0.7.6", + "multi-stash", + "smallvec", + "spin 0.9.8", + "wasmi_collections 0.40.0", + "wasmi_core 0.40.0", + "wasmi_ir", + "wasmparser 0.221.3", +] + [[package]] name = "wasmi_arena" version = "0.4.1" @@ -26443,11 +27422,29 @@ dependencies = [ "string-interner", ] +[[package]] +name = "wasmi_collections" +version = "0.40.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e80d6b275b1c922021939d561574bf376613493ae2b61c6963b15db0e8813562" + [[package]] name = "wasmi_core" version = "0.13.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dcf1a7db34bff95b85c261002720c00c3a6168256dcb93041d3fa2054d19856a" +checksum = "dcf1a7db34bff95b85c261002720c00c3a6168256dcb93041d3fa2054d19856a" +dependencies = [ + "downcast-rs", + "libm", + "num-traits", + "paste", +] + +[[package]] +name = "wasmi_core" +version = "0.32.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a23b3a7f6c8c3ceeec6b83531ee61f0013c56e51cbf2b14b0f213548b23a4b41" dependencies = [ "downcast-rs", "libm", @@ -26457,14 +27454,30 @@ dependencies = [ [[package]] name = "wasmi_core" -version = "0.32.3" +version = "0.40.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a23b3a7f6c8c3ceeec6b83531ee61f0013c56e51cbf2b14b0f213548b23a4b41" +checksum = "3a8c51482cc32d31c2c7ff211cd2bedd73c5bd057ba16a2ed0110e7a96097c33" dependencies = [ "downcast-rs", "libm", - "num-traits", - "paste", +] + +[[package]] +name = "wasmi_ir" +version = "0.40.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6e431a14c186db59212a88516788bd68ed51f87aa1e08d1df742522867b5289a" +dependencies = [ + "wasmi_core 0.40.0", +] + +[[package]] +name = "wasmparser" +version = "0.221.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d06bfa36ab3ac2be0dee563380147a5b81ba10dd8885d7fbbc9eb574be67d185" +dependencies = [ + "bitflags 2.9.3", ] [[package]] @@ -26473,13 +27486,24 @@ version = "0.235.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "161296c618fa2d63f6ed5fffd1112937e803cb9ec71b32b01a76321555660917" dependencies = [ - "bitflags 2.6.0", - "hashbrown 0.15.3", + "bitflags 2.9.3", + "hashbrown 0.15.5", "indexmap", - "semver 1.0.18", + "semver 1.0.26", "serde", ] +[[package]] +name = "wasmparser" +version = "0.237.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7d2a40ca0d2bdf4b0bf36c13a737d0b2c58e4c8aaefe1c57f336dd75369ca250" +dependencies = [ + "bitflags 2.9.3", + "indexmap", + "semver 1.0.26", +] + [[package]] name = "wasmparser-nostd" version = "0.100.2" @@ -26497,7 +27521,7 @@ checksum = "75aa8e9076de6b9544e6dab4badada518cca0bf4966d35b131bbd057aed8fa0a" dependencies = [ "anyhow", "termcolor", - "wasmparser", + "wasmparser 0.235.0", ] [[package]] @@ -26506,20 +27530,20 @@ version = "35.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b6fe976922a16af3b0d67172c473d1fd4f1aa5d0af9c8ba6538c741f3af686f4" dependencies = [ - "addr2line 0.24.2", + "addr2line", "anyhow", - "bitflags 2.6.0", + "bitflags 2.9.3", "bumpalo", "cc", "cfg-if", - "gimli 0.31.1", - "hashbrown 0.15.3", + "gimli", + "hashbrown 0.15.5", "indexmap", "libc", "log", "mach2", "memfd", - "object 0.36.7", + "object", "once_cell", "postcard", "pulley-interpreter", @@ -26529,7 +27553,7 @@ dependencies = [ "serde_derive", "smallvec", "target-lexicon", - "wasmparser", + "wasmparser 0.235.0", "wasmtime-environ", "wasmtime-internal-asm-macros", "wasmtime-internal-cache", @@ -26554,10 +27578,10 @@ dependencies = [ "cpp_demangle", "cranelift-bitset", "cranelift-entity", - "gimli 0.31.1", + "gimli", "indexmap", "log", - "object 0.36.7", + "object", "postcard", "rustc-demangle", "serde", @@ -26565,7 +27589,7 @@ dependencies = [ "smallvec", "target-lexicon", "wasm-encoder 0.235.0", - "wasmparser", + "wasmparser 0.235.0", "wasmprinter", ] @@ -26592,8 +27616,8 @@ dependencies = [ "rustix 1.0.8", "serde", "serde_derive", - "sha2 0.10.8", - "toml", + "sha2 0.10.9", + "toml 0.8.23", "windows-sys 0.59.0", "zstd 0.13.3", ] @@ -26611,15 +27635,15 @@ dependencies = [ "cranelift-entity", "cranelift-frontend", "cranelift-native", - "gimli 0.31.1", + "gimli", "itertools 0.14.0", "log", - "object 0.36.7", + "object", "pulley-interpreter", "smallvec", "target-lexicon", - "thiserror 2.0.12", - "wasmparser", + "thiserror 2.0.16", + "wasmparser 0.235.0", "wasmtime-environ", "wasmtime-internal-math", "wasmtime-internal-versioned-export-macros", @@ -26678,7 +27702,7 @@ dependencies = [ "cfg-if", "cranelift-codegen", "log", - "object 0.36.7", + "object", ] [[package]] @@ -26687,9 +27711,9 @@ version = "35.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "342b0466f92b7217a4de9e114175fedee1907028567d2548bcd42f71a8b5b016" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -26700,10 +27724,10 @@ checksum = "2012e7384c25b91aab2f1b6a1e1cbab9d0f199bbea06cc873597a3f047f05730" dependencies = [ "anyhow", "cranelift-codegen", - "gimli 0.31.1", - "object 0.36.7", + "gimli", + "object", "target-lexicon", - "wasmparser", + "wasmparser 0.235.0", "wasmtime-environ", "wasmtime-internal-cranelift", "winch-codegen", @@ -26711,30 +27735,31 @@ dependencies = [ [[package]] name = "wast" -version = "63.0.0" +version = "237.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2560471f60a48b77fccefaf40796fda61c97ce1e790b59dfcec9dc3995c9f63a" +checksum = "fcf66f545acbd55082485cb9a6daab54579cb8628a027162253e8e9f5963c767" dependencies = [ - "leb128", + "bumpalo", + "leb128fmt", "memchr", - "unicode-width 0.1.10", - "wasm-encoder 0.31.1", + "unicode-width", + "wasm-encoder 0.237.0", ] [[package]] name = "wat" -version = "1.0.70" +version = "1.237.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3bdc306c2c4c2f2bf2ba69e083731d0d2a77437fc6a350a19db139636e7e416c" +checksum = "27975186f549e4b8d6878b627be732863883c72f7bf4dcf8f96e5f8242f73da9" dependencies = [ "wast", ] [[package]] name = "web-sys" -version = "0.3.64" +version = "0.3.77" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9b85cbef8c220a6abc02aefd892dfc0fc23afb1c6a426316ec33253a3877249b" +checksum = "33b6dd2ef9186f1f2072e409e99cd22a975331a6b3591b12c764e0e55c60d5d2" dependencies = [ "js-sys", "wasm-bindgen", @@ -26750,17 +27775,35 @@ dependencies = [ "wasm-bindgen", ] +[[package]] +name = "webpki-root-certs" +version = "0.26.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "75c7f0ef91146ebfb530314f5f1d24528d7f0767efbfd31dce919275413e393e" +dependencies = [ + "webpki-root-certs 1.0.2", +] + +[[package]] +name = "webpki-root-certs" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4e4ffd8df1c57e87c325000a3d6ef93db75279dc3a231125aac571650f22b12a" +dependencies = [ + "rustls-pki-types", +] + [[package]] name = "webpki-roots" -version = "0.25.2" +version = "0.25.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "14247bb57be4f377dfb94c72830b8ce8fc6beac03cf4bf7b9732eadd414123fc" +checksum = "5f20c57d8d7db6d3b86154206ae5d8fba62dd39573114de97c2cb0578251f8e1" [[package]] name = "webpki-roots" -version = "0.26.3" +version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bd7c23921eeb1713a4e851530e9b9756e4fb0e89978582942612524cf09f01cd" +checksum = "7e8983c3ab33d6fb807cfcdad2491c4ea8cbc8ed839181c7dfd9c67c83e261b2" dependencies = [ "rustls-pki-types", ] @@ -26924,19 +27967,19 @@ dependencies = [ [[package]] name = "whoami" -version = "1.5.2" +version = "1.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "372d5b87f58ec45c384ba03563b03544dc5fadc3983e434b286913f5b4a9bb6d" +checksum = "5d4a4db5077702ca3015d3d02d74974948aba2ad9e12ab7df718ee64ccd7e97d" dependencies = [ - "redox_syscall 0.5.8", + "libredox", "wasite", ] [[package]] name = "wide" -version = "0.7.11" +version = "0.7.33" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aa469ffa65ef7e0ba0f164183697b89b854253fd31aeb92358b7b6155177d62f" +checksum = "0ce5da8ecb62bcd8ec8b7ea19f69a51275e91299be594ea5cc6ef7819e16cd03" dependencies = [ "bytemuck", "safe_arch", @@ -26944,9 +27987,9 @@ dependencies = [ [[package]] name = "widestring" -version = "1.0.2" +version = "1.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "653f141f39ec16bba3c5abe400a0c60da7468261cc2cbf36805022876bc721a8" +checksum = "dd7cf3379ca1aac9eea11fba24fd7e315d621f8dfe35c8d7d2be8b793726e07d" [[package]] name = "winapi" @@ -26966,11 +28009,11 @@ checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" [[package]] name = "winapi-util" -version = "0.1.5" +version = "0.1.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "70ec6ce85bb158151cae5e5c87f95a8e97d2c0c4b001223f33a334e3ce5de178" +checksum = "0978bf7171b3d90bac376700cb56d606feb40f251a475a5d6634613564460b22" dependencies = [ - "winapi", + "windows-sys 0.60.2", ] [[package]] @@ -26988,12 +28031,12 @@ dependencies = [ "anyhow", "cranelift-assembler-x64", "cranelift-codegen", - "gimli 0.31.1", + "gimli", "regalloc2 0.12.2", "smallvec", "target-lexicon", - "thiserror 2.0.12", - "wasmparser", + "thiserror 2.0.16", + "wasmparser 0.235.0", "wasmtime-environ", "wasmtime-internal-cranelift", "wasmtime-internal-math", @@ -27001,130 +28044,172 @@ dependencies = [ [[package]] name = "windows" -version = "0.48.0" +version = "0.52.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e686886bc078bc1b0b600cac0147aadb815089b6e4da64016cbd754b6342700f" +checksum = "e48a53791691ab099e5e2ad123536d0fff50652600abaf43bbf952894110d0be" dependencies = [ - "windows-targets 0.48.5", + "windows-core 0.52.0", + "windows-targets 0.52.6", ] [[package]] name = "windows" -version = "0.51.1" +version = "0.53.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ca229916c5ee38c2f2bc1e9d8f04df975b4bd93f9955dc69fabb5d91270045c9" +checksum = "efc5cf48f83140dcaab716eeaea345f9e93d0018fb81162753a3f76c3397b538" dependencies = [ - "windows-core 0.51.1", - "windows-targets 0.48.5", + "windows-core 0.53.0", + "windows-targets 0.52.6", ] [[package]] name = "windows" -version = "0.52.0" +version = "0.61.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e48a53791691ab099e5e2ad123536d0fff50652600abaf43bbf952894110d0be" +checksum = "9babd3a767a4c1aef6900409f85f5d53ce2544ccdfaa86dad48c91782c6d6893" dependencies = [ - "windows-core 0.52.0", - "windows-targets 0.52.6", + "windows-collections", + "windows-core 0.61.2", + "windows-future", + "windows-link", + "windows-numerics", ] [[package]] -name = "windows" -version = "0.58.0" +name = "windows-collections" +version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dd04d41d93c4992d421894c18c8b43496aa748dd4c081bac0dc93eb0489272b6" +checksum = "3beeceb5e5cfd9eb1d76b381630e82c4241ccd0d27f1a39ed41b2760b255c5e8" dependencies = [ - "windows-core 0.58.0", - "windows-targets 0.52.6", + "windows-core 0.61.2", ] [[package]] name = "windows-core" -version = "0.51.1" +version = "0.52.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f1f8cf84f35d2db49a46868f947758c7a1138116f7fac3bc844f43ade1292e64" +checksum = "33ab640c8d7e35bf8ba19b884ba838ceb4fba93a4e8c65a9059d08afcfc683d9" dependencies = [ - "windows-targets 0.48.5", + "windows-targets 0.52.6", ] [[package]] name = "windows-core" -version = "0.52.0" +version = "0.53.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "33ab640c8d7e35bf8ba19b884ba838ceb4fba93a4e8c65a9059d08afcfc683d9" +checksum = "9dcc5b895a6377f1ab9fa55acedab1fd5ac0db66ad1e6c7f47e28a22e446a5dd" dependencies = [ + "windows-result 0.1.2", "windows-targets 0.52.6", ] [[package]] name = "windows-core" -version = "0.58.0" +version = "0.61.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6ba6d44ec8c2591c134257ce647b7ea6b20335bf6379a27dac5f1641fcf59f99" +checksum = "c0fdd3ddb90610c7638aa2b3a3ab2904fb9e5cdbecc643ddb3647212781c4ae3" dependencies = [ "windows-implement", "windows-interface", - "windows-result", + "windows-link", + "windows-result 0.3.4", "windows-strings", - "windows-targets 0.52.6", +] + +[[package]] +name = "windows-future" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fc6a41e98427b19fe4b73c550f060b59fa592d7d686537eebf9385621bfbad8e" +dependencies = [ + "windows-core 0.61.2", + "windows-link", + "windows-threading", ] [[package]] name = "windows-implement" -version = "0.58.0" +version = "0.60.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2bbd5b46c938e506ecbce286b6628a02171d56153ba733b6c741fc627ec9579b" +checksum = "a47fddd13af08290e67f4acabf4b459f647552718f683a7b415d290ac744a836" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "windows-interface" -version = "0.58.0" +version = "0.59.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "053c4c462dc91d3b1504c6fe5a726dd15e216ba718e84a0e46a88fbe5ded3515" +checksum = "bd9211b69f8dcdfa817bfd14bf1c97c9188afa36f4750130fcdf3f400eca9fa8" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "windows-link" -version = "0.1.0" +version = "0.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6dccfd733ce2b1753b03b6d3c65edf020262ea35e20ccdf3e288043e6dd620e3" +checksum = "5e6ad25900d524eaabdbbb96d20b4311e1e7ae1699af4fb28c17ae66c80d798a" [[package]] -name = "windows-registry" +name = "windows-numerics" version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e400001bb720a623c1c69032f8e3e4cf09984deec740f007dd2b03ec864804b0" +checksum = "9150af68066c4c5c07ddc0ce30421554771e528bde427614c61038bc2c92c2b1" +dependencies = [ + "windows-core 0.61.2", + "windows-link", +] + +[[package]] +name = "windows-registry" +version = "0.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b8a9ed28765efc97bbc954883f4e6796c33a06546ebafacbabee9696967499e" dependencies = [ - "windows-result", + "windows-link", + "windows-result 0.3.4", "windows-strings", - "windows-targets 0.52.6", ] [[package]] name = "windows-result" -version = "0.2.0" +version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1d1043d8214f791817bab27572aaa8af63732e11bf84aa21a45a78d6c317ae0e" +checksum = "5e383302e8ec8515204254685643de10811af0ed97ea37210dc26fb0032647f8" dependencies = [ "windows-targets 0.52.6", ] +[[package]] +name = "windows-result" +version = "0.3.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "56f42bd332cc6c8eac5af113fc0c1fd6a8fd2aa08a0119358686e5160d0586c6" +dependencies = [ + "windows-link", +] + [[package]] name = "windows-strings" -version = "0.1.0" +version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4cd9b125c486025df0eabcb585e62173c6c9eddcec5d117d3b6e8c30e2ee4d10" +checksum = "56e6c93f3a0c3b36176cb1327a4958a0353d5d166c2a35cb268ace15e91d3b57" dependencies = [ - "windows-result", - "windows-targets 0.52.6", + "windows-link", +] + +[[package]] +name = "windows-sys" +version = "0.45.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "75283be5efb2831d37ea142365f009c02ec203cd29a3ebecbc093d52315b66d0" +dependencies = [ + "windows-targets 0.42.2", ] [[package]] @@ -27154,6 +28239,30 @@ dependencies = [ "windows-targets 0.52.6", ] +[[package]] +name = "windows-sys" +version = "0.60.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f2f500e4d28234f72040990ec9d39e3a6b950f9f22d3dba18416c35882612bcb" +dependencies = [ + "windows-targets 0.53.3", +] + +[[package]] +name = "windows-targets" +version = "0.42.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8e5180c00cd44c9b1c88adb3693291f1cd93605ded80c250a75d472756b4d071" +dependencies = [ + "windows_aarch64_gnullvm 0.42.2", + "windows_aarch64_msvc 0.42.2", + "windows_i686_gnu 0.42.2", + "windows_i686_msvc 0.42.2", + "windows_x86_64_gnu 0.42.2", + "windows_x86_64_gnullvm 0.42.2", + "windows_x86_64_msvc 0.42.2", +] + [[package]] name = "windows-targets" version = "0.48.5" @@ -27178,13 +28287,45 @@ dependencies = [ "windows_aarch64_gnullvm 0.52.6", "windows_aarch64_msvc 0.52.6", "windows_i686_gnu 0.52.6", - "windows_i686_gnullvm", + "windows_i686_gnullvm 0.52.6", "windows_i686_msvc 0.52.6", "windows_x86_64_gnu 0.52.6", "windows_x86_64_gnullvm 0.52.6", "windows_x86_64_msvc 0.52.6", ] +[[package]] +name = "windows-targets" +version = "0.53.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d5fe6031c4041849d7c496a8ded650796e7b6ecc19df1a431c1a363342e5dc91" +dependencies = [ + "windows-link", + "windows_aarch64_gnullvm 0.53.0", + "windows_aarch64_msvc 0.53.0", + "windows_i686_gnu 0.53.0", + "windows_i686_gnullvm 0.53.0", + "windows_i686_msvc 0.53.0", + "windows_x86_64_gnu 0.53.0", + "windows_x86_64_gnullvm 0.53.0", + "windows_x86_64_msvc 0.53.0", +] + +[[package]] +name = "windows-threading" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b66463ad2e0ea3bbf808b7f1d371311c80e115c0b71d60efc142cafbcfb057a6" +dependencies = [ + "windows-link", +] + +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.42.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "597a5118570b68bc08d8d59125332c54f1ba9d9adeedeef5b99b02ba2b0698f8" + [[package]] name = "windows_aarch64_gnullvm" version = "0.48.5" @@ -27197,6 +28338,18 @@ version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "32a4622180e7a0ec044bb555404c800bc9fd9ec262ec147edd5989ccd0c02cd3" +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "86b8d5f90ddd19cb4a147a5fa63ca848db3df085e25fee3cc10b39b6eebae764" + +[[package]] +name = "windows_aarch64_msvc" +version = "0.42.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e08e8864a60f06ef0d0ff4ba04124db8b0fb3be5776a5cd47641e942e58c4d43" + [[package]] name = "windows_aarch64_msvc" version = "0.48.5" @@ -27209,6 +28362,18 @@ version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "09ec2a7bb152e2252b53fa7803150007879548bc709c039df7627cabbd05d469" +[[package]] +name = "windows_aarch64_msvc" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c7651a1f62a11b8cbd5e0d42526e55f2c99886c77e007179efff86c2b137e66c" + +[[package]] +name = "windows_i686_gnu" +version = "0.42.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c61d927d8da41da96a81f029489353e68739737d3beca43145c8afec9a31a84f" + [[package]] name = "windows_i686_gnu" version = "0.48.5" @@ -27221,12 +28386,30 @@ version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8e9b5ad5ab802e97eb8e295ac6720e509ee4c243f69d781394014ebfe8bbfa0b" +[[package]] +name = "windows_i686_gnu" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1dc67659d35f387f5f6c479dc4e28f1d4bb90ddd1a5d3da2e5d97b42d6272c3" + [[package]] name = "windows_i686_gnullvm" version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0eee52d38c090b3caa76c563b86c3a4bd71ef1a819287c19d586d7334ae8ed66" +[[package]] +name = "windows_i686_gnullvm" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9ce6ccbdedbf6d6354471319e781c0dfef054c81fbc7cf83f338a4296c0cae11" + +[[package]] +name = "windows_i686_msvc" +version = "0.42.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "44d840b6ec649f480a41c8d80f9c65108b92d89345dd94027bfe06ac444d1060" + [[package]] name = "windows_i686_msvc" version = "0.48.5" @@ -27239,6 +28422,18 @@ version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "240948bc05c5e7c6dabba28bf89d89ffce3e303022809e73deaefe4f6ec56c66" +[[package]] +name = "windows_i686_msvc" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "581fee95406bb13382d2f65cd4a908ca7b1e4c2f1917f143ba16efe98a589b5d" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.42.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8de912b8b8feb55c064867cf047dda097f92d51efad5b491dfb98f6bbb70cb36" + [[package]] name = "windows_x86_64_gnu" version = "0.48.5" @@ -27251,6 +28446,18 @@ version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "147a5c80aabfbf0c7d901cb5895d1de30ef2907eb21fbbab29ca94c5b08b1a78" +[[package]] +name = "windows_x86_64_gnu" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2e55b5ac9ea33f2fc1716d1742db15574fd6fc8dadc51caab1c16a3d3b4190ba" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.42.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "26d41b46a36d453748aedef1486d5c7a85db22e56aff34643984ea85514e94a3" + [[package]] name = "windows_x86_64_gnullvm" version = "0.48.5" @@ -27263,6 +28470,18 @@ version = "0.52.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "24d5b23dc417412679681396f2b49f3de8c1473deb516bd34410872eff51ed0d" +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.53.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0a6e035dd0599267ce1ee132e51c27dd29437f63325753051e71dd9e42406c57" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.42.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9aec5da331524158c6d1a4ac0ab1541149c0b9505fde06423b02f5ef0106b9f0" + [[package]] name = "windows_x86_64_msvc" version = "0.48.5" @@ -27276,28 +28495,25 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec" [[package]] -name = "winnow" -version = "0.5.15" +name = "windows_x86_64_msvc" +version = "0.53.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7c2e3184b9c4e92ad5167ca73039d0c42476302ab603e2fec4487511f38ccefc" -dependencies = [ - "memchr", -] +checksum = "271414315aff87387382ec3d271b52d7ae78726f5d44ac98b4f4030c91880486" [[package]] name = "winnow" -version = "0.6.18" +version = "0.5.40" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "68a9bda4691f099d435ad181000724da8e5899daa10713c2d432552b9ccd3a6f" +checksum = "f593a95398737aeed53e489c785df13f3618e41dbcd6718c6addbf1395aa6876" dependencies = [ "memchr", ] [[package]] name = "winnow" -version = "0.7.10" +version = "0.7.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c06928c8748d81b05c9be96aad92e1b6ff01833332f281e8cfca3be4b35fc9ec" +checksum = "21a0236b59786fed61e2a80582dd500fe61f18b5dca67a4a067d0bc9039339cf" dependencies = [ "memchr", ] @@ -27314,24 +28530,18 @@ dependencies = [ [[package]] name = "wit-bindgen-rt" -version = "0.33.0" +version = "0.39.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3268f3d866458b787f390cf61f4bbb563b922d091359f9608842999eaee3943c" +checksum = "6f42320e61fe2cfd34354ecb597f86f413484a798ba44a8ca1165c58d42da6c1" dependencies = [ - "bitflags 2.6.0", + "bitflags 2.9.3", ] -[[package]] -name = "write16" -version = "1.0.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d1890f4022759daae28ed4fe62859b1236caebfc61ede2f63ed4e695f3f6d936" - [[package]] name = "writeable" -version = "0.5.5" +version = "0.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1e9df38ee2d2c3c5948ea468a8406ff0db0b29ae1ffde1bcf20ef305bcc95c51" +checksum = "ea2f10b9bb0928dfb1b42b65e1f9e36f7f54dbdf08457afefb38afcdec4fa2bb" [[package]] name = "wyz" @@ -27360,14 +28570,14 @@ version = "0.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fcbc162f30700d6f3f82a24bf7cc62ffe7caea42c0b2cba8bf7f3ae50cf51f69" dependencies = [ - "asn1-rs 0.6.1", + "asn1-rs 0.6.2", "data-encoding", "der-parser 9.0.0", "lazy_static", - "nom", - "oid-registry 0.7.0", + "nom 7.1.3", + "oid-registry 0.7.1", "rusticata-macros", - "thiserror 1.0.65", + "thiserror 1.0.69", "time", ] @@ -27377,24 +28587,25 @@ version = "0.17.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4569f339c0c402346d4a75a9e39cf8dad310e287eef1ff56d4c68e5067f53460" dependencies = [ - "asn1-rs 0.7.0", + "asn1-rs 0.7.1", "data-encoding", "der-parser 10.0.0", "lazy_static", - "nom", + "nom 7.1.3", "oid-registry 0.8.1", "rusticata-macros", - "thiserror 2.0.12", + "thiserror 2.0.16", "time", ] [[package]] name = "xattr" -version = "1.0.1" +version = "1.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f4686009f71ff3e5c4dbcf1a282d0a44db3f021ba69350cd42086b3e5f1c6985" +checksum = "af3a19837351dc82ba89f8a125e22a3c475f05aba604acc023d62b2739ae2909" dependencies = [ "libc", + "rustix 1.0.8", ] [[package]] @@ -27423,7 +28634,7 @@ dependencies = [ name = "xcm-emulator" version = "0.5.0" dependencies = [ - "array-bytes 6.2.2", + "array-bytes 6.2.3", "cumulus-pallet-parachain-system", "cumulus-primitives-core", "cumulus-primitives-parachain-inherent", @@ -27482,10 +28693,10 @@ version = "7.0.0" dependencies = [ "Inflector", "frame-support", - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", "staging-xcm", - "syn 2.0.98", + "syn 2.0.106", "trybuild", ] @@ -27586,9 +28797,9 @@ dependencies = [ [[package]] name = "xml-rs" -version = "0.8.20" +version = "0.8.27" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "791978798f0597cfc70478424c2b4fdc2b7a8024aaff78497ef00f24ef674193" +checksum = "6fd8403733700263c6eb89f192880191f1b83e332f7a20371ddcf421c4a337c7" [[package]] name = "xmltree" @@ -27608,7 +28819,7 @@ dependencies = [ "futures", "log", "nohash-hasher", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project", "rand 0.8.5", "static_assertions", @@ -27623,18 +28834,18 @@ dependencies = [ "futures", "log", "nohash-hasher", - "parking_lot 0.12.3", + "parking_lot 0.12.4", "pin-project", - "rand 0.9.0", + "rand 0.9.2", "static_assertions", "web-time", ] [[package]] name = "yansi" -version = "0.5.1" +version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "09041cd90cf85f7f8b2df60c646f853b7f535ce68f85244eb6731cf89fa498ec" +checksum = "cfe53a6657fd280eaa890a3bc59152892ffa3e30101319d168b781ed6529b049" [[package]] name = "yap" @@ -27714,9 +28925,9 @@ dependencies = [ [[package]] name = "yoke" -version = "0.7.5" +version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "120e6aef9aa629e3d4f52dc8cc43a015c7724194c97dfaf45180d2daf2b77f40" +checksum = "5f41bb01b8226ef4bfd589436a297c53d118f65921786300e427be8d487695cc" dependencies = [ "serde", "stable_deref_trait", @@ -27726,75 +28937,55 @@ dependencies = [ [[package]] name = "yoke-derive" -version = "0.7.5" +version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2380878cad4ac9aac1e2435f3eb4020e8374b5f13c296cb75b4620ff8e229154" +checksum = "38da3c9736e16c5d3c8c597a9aaa5d1fa565d0532ae05e27c24aa62fb32c0ab6" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", - "synstructure 0.13.1", -] - -[[package]] -name = "zerocopy" -version = "0.7.32" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "74d4d3961e53fa4c9a25a8637fc2bfaf2595b3d3ae34875568a5cf64787716be" -dependencies = [ - "zerocopy-derive 0.7.32", + "syn 2.0.106", + "synstructure 0.13.2", ] [[package]] name = "zerocopy" -version = "0.8.20" +version = "0.8.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dde3bb8c68a8f3f1ed4ac9221aad6b10cece3e60a8e2ea54a6a2dec806d0084c" +checksum = "1039dd0d3c310cf05de012d8a39ff557cb0d23087fd44cad61df08fc31907a2f" dependencies = [ - "zerocopy-derive 0.8.20", + "zerocopy-derive", ] [[package]] name = "zerocopy-derive" -version = "0.7.32" +version = "0.8.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9ce1b18ccd8e73a9321186f97e46f9f04b778851177567b1975109d26a08d2a6" +checksum = "9ecf5b4cc5364572d7f4c329661bcc82724222973f2cab6f050a4e5c22f75181" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", -] - -[[package]] -name = "zerocopy-derive" -version = "0.8.20" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eea57037071898bf96a6da35fd626f4f27e9cee3ead2a6c703cf09d472b2e700" -dependencies = [ - "proc-macro2 1.0.95", - "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] name = "zerofrom" -version = "0.1.5" +version = "0.1.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cff3ee08c995dee1859d998dea82f7374f2826091dd9cd47def953cae446cd2e" +checksum = "50cc42e0333e05660c3587f3bf9d0478688e15d870fab3346451ce7f8c9fbea5" dependencies = [ "zerofrom-derive", ] [[package]] name = "zerofrom-derive" -version = "0.1.5" +version = "0.1.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "595eed982f7d355beb85837f651fa22e90b3c044842dc7f2c2842c086f295808" +checksum = "d71e5d6e06ab090c67b5e44993ec16b72dcbaabc526db883a360057678b48502" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", - "synstructure 0.13.1", + "syn 2.0.106", + "synstructure 0.13.2", ] [[package]] @@ -27812,16 +29003,27 @@ version = "1.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ce36e65b0d2999d2aafac989fb249189a141aee1f53c612c1f37d72631959f69" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", +] + +[[package]] +name = "zerotrie" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "36f0bbd478583f79edad978b407914f61b2972f5af6fa089686016be8f9af595" +dependencies = [ + "displaydoc", + "yoke", + "zerofrom", ] [[package]] name = "zerovec" -version = "0.10.4" +version = "0.11.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aa2b893d79df23bfb12d5461018d408ea19dfafe76c2c7ef6d4eba614f8ff079" +checksum = "e7aa2bd55086f1ab526693ecbe444205da57e25f4489879da80635a46d90e73b" dependencies = [ "yoke", "zerofrom", @@ -27830,13 +29032,13 @@ dependencies = [ [[package]] name = "zerovec-derive" -version = "0.10.3" +version = "0.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6eafa6dfb17584ea3e2bd6e76e0cc15ad7af12b09abdd1ca55961bed9b1063c6" +checksum = "5b96237efa0c878c64bd89c436f661be4e46b2f3eff1ebb976f7ef2321d2f58f" dependencies = [ - "proc-macro2 1.0.95", + "proc-macro2 1.0.101", "quote 1.0.40", - "syn 2.0.98", + "syn 2.0.106", ] [[package]] @@ -27847,7 +29049,7 @@ dependencies = [ "parity-scale-codec", "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-tungstenite 0.26.2", "tracing-gum", @@ -27855,20 +29057,20 @@ dependencies = [ [[package]] name = "zombienet-configuration" -version = "0.3.8" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c3a6f9764e5f322f1aa44e1a75258adbabbe1b530974252a66e81331cfe805d5" +checksum = "a5e93ea881757b3d3015d9dd41e04ceafb4d9747c5edd36a3f772c3137cec142" dependencies = [ "anyhow", "lazy_static", - "multiaddr 0.18.1", + "multiaddr 0.18.2", "regex", "reqwest", "serde", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", - "toml", + "toml 0.8.23", "tracing", "url", "zombienet-support", @@ -27876,9 +29078,9 @@ dependencies = [ [[package]] name = "zombienet-orchestrator" -version = "0.3.8" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d7e28aafee53c025762afbc77ebb31b34ef81066bd967ed569508fc42057934" +checksum = "ce17e41af0ad18befadbd7fc2658d2e54e9f644f51b07b1cf68d58d50a3049b9" dependencies = [ "anyhow", "async-trait", @@ -27888,17 +29090,17 @@ dependencies = [ "hex", "libp2p", "libsecp256k1", - "multiaddr 0.18.1", + "multiaddr 0.18.2", "rand 0.8.5", "regex", "reqwest", "serde", "serde_json", - "sha2 0.10.8", - "sp-core 35.0.0", - "subxt 0.38.1", - "subxt-signer 0.38.0", - "thiserror 1.0.65", + "sha2 0.10.9", + "sp-core 36.1.0", + "subxt 0.43.0", + "subxt-signer 0.43.0", + "thiserror 1.0.69", "tokio", "tracing", "uuid", @@ -27910,20 +29112,20 @@ dependencies = [ [[package]] name = "zombienet-prom-metrics-parser" -version = "0.3.8" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9a481e65f290606b358a2c9e79d8f945142a7414f38670113fff3453ac1604bc" +checksum = "fe24a05a4dda190039120ca480b729c5953f1aa52edc2caa1990b06281b71b93" dependencies = [ "pest", "pest_derive", - "thiserror 1.0.65", + "thiserror 1.0.69", ] [[package]] name = "zombienet-provider" -version = "0.3.8" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "51b67d77160754d0681d289a123d11f2a0b23869a222536af046618c94bbb872" +checksum = "38f2f1e242017d86ed78edc0a89478e2e5b95ea22059ed3ca51bf6feb0992b82" dependencies = [ "anyhow", "async-trait", @@ -27938,9 +29140,9 @@ dependencies = [ "serde", "serde_json", "serde_yaml", - "sha2 0.10.8", + "sha2 0.10.9", "tar", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tokio-util", "tracing", @@ -27952,15 +29154,15 @@ dependencies = [ [[package]] name = "zombienet-sdk" -version = "0.3.8" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "91beaacd1c1e824d34b1ff8322834f0762cb5e38e3272611f43d8c1225e6b80c" +checksum = "0ee9678f47cb3e5d52a7c58a11ef4cfdfca33c2388cd755752732aadf563b1ee" dependencies = [ "async-trait", "futures", "lazy_static", - "subxt 0.38.1", - "subxt-signer 0.38.0", + "subxt 0.43.0", + "subxt-signer 0.43.0", "tokio", "zombienet-configuration", "zombienet-orchestrator", @@ -27970,9 +29172,9 @@ dependencies = [ [[package]] name = "zombienet-support" -version = "0.3.8" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c5ff14369c69535857b0a6889f7968032c37d51a43bdd3441a4b0bf060648943" +checksum = "a7e7adcfce4103f9caad531e337001163c5f56c844125fbd580a57dfe3e5463e" dependencies = [ "anyhow", "async-trait", @@ -27983,7 +29185,7 @@ dependencies = [ "regex", "reqwest", "serde_json", - "thiserror 1.0.65", + "thiserror 1.0.69", "tokio", "tracing", "uuid", diff --git a/Cargo.toml b/Cargo.toml index ea58a96bab296..f177f6f5b6383 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -928,7 +928,7 @@ node-rpc = { path = "substrate/bin/node/rpc" } node-testing = { path = "substrate/bin/node/testing" } nohash-hasher = { version = "0.2.0" } novelpoly = { version = "2.0.0", package = "reed-solomon-novelpoly" } -num-bigint = { version = "0.4.3", default-features = false } +num-bigint = { version = "0.4.6", default-features = false } num-format = { version = "0.4.3" } num-integer = { version = "0.1.46", default-features = false } num-rational = { version = "0.4.1" } @@ -1190,6 +1190,7 @@ regex = { version = "1.10.2" } relay-substrate-client = { path = "bridges/relays/client-substrate" } relay-utils = { path = "bridges/relays/utils" } remote-externalities = { path = "substrate/utils/frame/remote-externalities", default-features = false, package = "frame-remote-externalities" } +revm = { version = "27.0.2", default-features = false } ripemd = { version = "0.1.3", default-features = false } rlp = { version = "0.6.1", default-features = false } rococo-emulated-chain = { path = "cumulus/parachains/integration-tests/emulated/chains/relays/rococo" } @@ -1400,9 +1401,9 @@ substrate-test-runtime-client = { path = "substrate/test-utils/runtime/client" } substrate-test-runtime-transaction-pool = { path = "substrate/test-utils/runtime/transaction-pool" } substrate-test-utils = { path = "substrate/test-utils" } substrate-wasm-builder = { path = "substrate/utils/wasm-builder", default-features = false } -subxt = { version = "0.41", default-features = false } -subxt-metadata = { version = "0.41", default-features = false } -subxt-signer = { version = "0.41" } +subxt = { version = "0.43", default-features = false } +subxt-metadata = { version = "0.43", default-features = false } +subxt-signer = { version = "0.43" } syn = { version = "2.0.87" } sysinfo = { version = "0.30" } tar = { version = "0.4" } @@ -1474,9 +1475,9 @@ xcm-runtime-apis = { path = "polkadot/xcm/xcm-runtime-apis", default-features = xcm-simulator = { path = "polkadot/xcm/xcm-simulator", default-features = false } yet-another-parachain-runtime = { path = "cumulus/parachains/runtimes/testing/yet-another-parachain" } zeroize = { version = "1.7.0", default-features = false } -zombienet-configuration = { version = "0.3.8" } -zombienet-orchestrator = { version = "0.3.8" } -zombienet-sdk = { version = "0.3.8" } +zombienet-configuration = { version = "0.3.12" } +zombienet-orchestrator = { version = "0.3.12" } +zombienet-sdk = { version = "0.3.12" } zstd = { version = "0.12.4", default-features = false } [profile.release] diff --git a/bridges/modules/relayers/Cargo.toml b/bridges/modules/relayers/Cargo.toml index 0a9b41a460229..1b27c2879e930 100644 --- a/bridges/modules/relayers/Cargo.toml +++ b/bridges/modules/relayers/Cargo.toml @@ -12,8 +12,8 @@ workspace = true [dependencies] codec = { workspace = true } -log = { workspace = true } scale-info = { features = ["derive"], workspace = true } +tracing = { workspace = true } # Bridge dependencies bp-header-chain = { workspace = true } @@ -55,7 +55,6 @@ std = [ "frame-benchmarking/std", "frame-support/std", "frame-system/std", - "log/std", "pallet-bridge-grandpa/std", "pallet-bridge-messages/std", "pallet-bridge-parachains/std", @@ -66,6 +65,7 @@ std = [ "sp-core/std", "sp-io/std", "sp-runtime/std", + "tracing/std", ] runtime-benchmarks = [ "frame-benchmarking/runtime-benchmarks", diff --git a/bridges/modules/relayers/src/extension/grandpa_adapter.rs b/bridges/modules/relayers/src/extension/grandpa_adapter.rs index 9e98c73f8da04..a8466fe22aca8 100644 --- a/bridges/modules/relayers/src/extension/grandpa_adapter.rs +++ b/bridges/modules/relayers/src/extension/grandpa_adapter.rs @@ -156,12 +156,12 @@ where finality_proof_info.block_number, ) { // we only refund relayer if all calls have updated chain state - log::trace!( + tracing::trace!( target: LOG_TARGET, - "{}.{:?}: relayer {:?} has submitted invalid GRANDPA chain finality proof", - C::IdProvider::STR, - call_info.messages_call_info().lane_id(), - relayer, + id_provider=%C::IdProvider::STR, + lane_id=?call_info.messages_call_info().lane_id(), + ?relayer, + "Relayer has submitted invalid GRANDPA chain finality proof" ); return false } diff --git a/bridges/modules/relayers/src/extension/mod.rs b/bridges/modules/relayers/src/extension/mod.rs index 8d03a0db2e509..c953ab836e9c2 100644 --- a/bridges/modules/relayers/src/extension/mod.rs +++ b/bridges/modules/relayers/src/extension/mod.rs @@ -221,13 +221,13 @@ where // We don't refund anything if the transaction has failed. if let Err(e) = result { - log::trace!( + tracing::trace!( target: LOG_TARGET, - "{}.{:?}: relayer {:?} has submitted invalid messages transaction: {:?}", - Self::IDENTIFIER, - lane_id, - relayer, - e, + error=?e, + id_provider=%Self::IDENTIFIER, + ?lane_id, + ?relayer, + "Relayer has submitted invalid messages transaction", ); return slash_relayer_if_delivery_result } @@ -346,15 +346,14 @@ where priority::compute_priority_boost::(bundled_messages); let valid_transaction = ValidTransactionBuilder::default().priority(priority_boost); - log::trace!( + tracing::trace!( target: LOG_TARGET, - "{}.{:?}: has boosted priority of message delivery transaction \ - of relayer {:?}: {} messages -> {} priority", - Self::IDENTIFIER, - data.call_info.messages_call_info().lane_id(), - data.relayer, - bundled_messages, - priority_boost, + id_provider=%Self::IDENTIFIER, + lane_id=?data.call_info.messages_call_info().lane_id(), + relayer=?data.relayer, + %bundled_messages, + %priority_boost, + "Has boosted priority of message delivery transaction of relayer" ); let validity = valid_transaction.build()?; @@ -370,12 +369,12 @@ where _len: usize, ) -> Result { Ok(val.inspect(|data| { - log::trace!( + tracing::trace!( target: LOG_TARGET, - "{}.{:?}: parsed bridge transaction in prepare: {:?}", - Self::IDENTIFIER, - data.call_info.messages_call_info().lane_id(), - data.call_info, + id_provider=%Self::IDENTIFIER, + lane_id=?data.call_info.messages_call_info().lane_id(), + call_info=?data.call_info, + "Parsed bridge transaction in prepare" ); })) } @@ -399,13 +398,13 @@ where reward, ); - log::trace!( + tracing::trace!( target: LOG_TARGET, - "{}.{:?}: has registered reward: {:?} for {:?}", - Self::IDENTIFIER, - lane_id, - reward, - relayer, + id_provider=%Self::IDENTIFIER, + ?lane_id, + ?relayer, + ?reward, + "Has registered reward" ); }, RelayerAccountAction::Slash(relayer, slash_account) => @@ -437,12 +436,12 @@ where if !MessagesCallHelper::::was_successful( messages_call, ) { - log::trace!( + tracing::trace!( target: LOG_TARGET, - "{}.{:?}: relayer {:?} has submitted invalid messages call", - C::IdProvider::STR, - call_info.messages_call_info().lane_id(), - relayer, + id_provider=%C::IdProvider::STR, + lane_id=?call_info.messages_call_info().lane_id(), + ?relayer, + "Relayer has submitted invalid messages call" ); return false } diff --git a/bridges/modules/relayers/src/extension/parachain_adapter.rs b/bridges/modules/relayers/src/extension/parachain_adapter.rs index 122e7073632fa..7776cc8dbaed4 100644 --- a/bridges/modules/relayers/src/extension/parachain_adapter.rs +++ b/bridges/modules/relayers/src/extension/parachain_adapter.rs @@ -174,12 +174,12 @@ where if !SubmitParachainHeadsHelper::::was_successful(para_proof_info) { // we only refund relayer if all calls have updated chain state - log::trace!( + tracing::trace!( target: LOG_TARGET, - "{}.{:?}: relayer {:?} has submitted invalid parachain finality proof", - C::IdProvider::STR, - call_info.messages_call_info().lane_id(), - relayer, + id_provider=%C::IdProvider::STR, + lane_id=?call_info.messages_call_info().lane_id(), + ?relayer, + "Relayer has submitted invalid parachain finality proof" ); return false } diff --git a/bridges/modules/relayers/src/lib.rs b/bridges/modules/relayers/src/lib.rs index d2fe73d534b89..d771242306b99 100644 --- a/bridges/modules/relayers/src/lib.rs +++ b/bridges/modules/relayers/src/lib.rs @@ -157,12 +157,12 @@ pub mod pallet { } else if let Some(to_reserve) = required_stake.checked_sub(®istration.stake) { T::StakeAndSlash::reserve(&relayer, to_reserve).map_err(|e| { - log::trace!( + tracing::trace!( target: LOG_TARGET, - "Failed to reserve {:?} on relayer {:?} account: {:?}", - to_reserve, - relayer, - e, + error=?e, + ?relayer, + ?to_reserve, + "Failed to reserve on relayer account" ); Error::::FailedToReserve @@ -170,7 +170,7 @@ pub mod pallet { } registration.stake = required_stake; - log::trace!(target: LOG_TARGET, "Successfully registered relayer: {:?}", relayer); + tracing::trace!(target: LOG_TARGET, ?relayer, "Successfully registered relayer"); Self::deposit_event(Event::::RegistrationUpdated { relayer: relayer.clone(), registration, @@ -211,7 +211,7 @@ pub mod pallet { Self::do_unreserve(&relayer, registration.stake)?; } - log::trace!(target: LOG_TARGET, "Successfully deregistered relayer: {:?}", relayer); + tracing::trace!(target: LOG_TARGET, ?relayer, "Successfully deregistered relayer"); Self::deposit_event(Event::::Deregistered { relayer: relayer.clone() }); *maybe_registration = None; @@ -278,14 +278,14 @@ pub mod pallet { beneficiary.clone(), ) .map_err(|e| { - log::error!( + tracing::error!( target: LOG_TARGET, - "Failed to pay ({:?} / {:?}) rewards to {:?}(beneficiary: {:?}), error: {:?}", - reward_kind, - reward_balance, - relayer, - beneficiary, - e, + error=?e, + ?relayer, + ?reward_kind, + ?reward_balance, + ?beneficiary, + "Failed to pay rewards" ); Error::::FailedToPayReward })?; @@ -338,10 +338,10 @@ pub mod pallet { let registration = match RegisteredRelayers::::take(relayer) { Some(registration) => registration, None => { - log::trace!( + tracing::trace!( target: crate::LOG_TARGET, - "Cannot slash unregistered relayer {:?}", - relayer, + ?relayer, + "Cannot slash unregistered relayer" ); return; @@ -355,23 +355,22 @@ pub mod pallet { registration.stake, ) { Ok(failed_to_slash) if failed_to_slash.is_zero() => { - log::trace!( + tracing::trace!( target: crate::LOG_TARGET, - "Relayer account {:?} has been slashed for {:?}. Funds were deposited to {:?}", - relayer, - registration.stake, - slash_destination, + ?relayer, + amount=?registration.stake, + ?slash_destination, + "Relayer account has been slashed. Funds were deposited." ); }, Ok(failed_to_slash) => { - log::trace!( + tracing::trace!( target: crate::LOG_TARGET, - "Relayer account {:?} has been partially slashed for {:?}. Funds were deposited to {:?}. \ - Failed to slash: {:?}", - relayer, - registration.stake, - slash_destination, - failed_to_slash, + ?relayer, + amount=?registration.stake, + ?slash_destination, + ?failed_to_slash, + "Relayer account has been partially slashed. Funds were deposited.", ); }, Err(e) => { @@ -379,15 +378,14 @@ pub mod pallet { // it may fail if there's no beneficiary account. For us, it means that this // account must exist before we'll deploy the bridge - log::debug!( + tracing::debug!( target: crate::LOG_TARGET, - "Failed to slash relayer account {:?}: {:?}. Maybe beneficiary account doesn't exist? \ - Beneficiary: {:?}, amount: {:?}, failed to slash: {:?}", - relayer, - e, - slash_destination, - registration.stake, - registration.stake, + error=?e, + ?relayer, + beneficiary=?slash_destination, + amount=?registration.stake, + failed_to_slash=?registration.stake, + "Failed to slash relayer account. Maybe beneficiary account doesn't exist?" ); }, } @@ -416,12 +414,12 @@ pub mod pallet { old_reward.unwrap_or_else(Zero::zero).saturating_add(reward_balance); *old_reward = Some(new_reward); - log::trace!( + tracing::trace!( target: crate::LOG_TARGET, - "Relayer {:?} can now claim reward for serving payer {:?}: {:?}", - relayer, - reward_kind, - new_reward, + ?relayer, + ?reward_kind, + ?new_reward, + "Relayer can now claim reward for serving payer" ); Self::deposit_event(Event::::RewardRegistered { @@ -455,12 +453,12 @@ pub mod pallet { fn do_unreserve(relayer: &T::AccountId, amount: T::Balance) -> DispatchResult { let failed_to_unreserve = T::StakeAndSlash::unreserve(relayer, amount); if !failed_to_unreserve.is_zero() { - log::trace!( + tracing::trace!( target: LOG_TARGET, - "Failed to unreserve {:?}/{:?} on relayer {:?} account", - failed_to_unreserve, - amount, - relayer, + ?relayer, + ?failed_to_unreserve, + ?amount, + "Failed to unreserve on relayer account", ); fail!(Error::::FailedToUnreserve) diff --git a/bridges/modules/relayers/src/migration.rs b/bridges/modules/relayers/src/migration.rs index 11a809e5d335e..1c2d2355ec707 100644 --- a/bridges/modules/relayers/src/migration.rs +++ b/bridges/modules/relayers/src/migration.rs @@ -191,12 +191,12 @@ pub mod v1 { old_reward.unwrap_or_else(Zero::zero).saturating_add(reward_balance); *old_reward = Some(new_reward); - log::trace!( + tracing::trace!( target: crate::LOG_TARGET, - "Relayer {:?} can now claim reward for serving payer {:?}: {:?}", - relayer, - rewards_account_params, - new_reward, + ?relayer, + ?rewards_account_params, + ?new_reward, + "Relayer can now claim reward" ); }, ); @@ -252,7 +252,7 @@ pub mod v1 { ConstU32<{ u32::MAX }>, > = BoundedBTreeMap::new(); for (key1, key2, reward) in v0::RelayerRewards::::iter() { - log::info!(target: LOG_TARGET, "Reward to migrate: {key1:?}::{key2:?} - {reward:?}"); + tracing::info!(target: LOG_TARGET, ?key1, ?key2, ?reward, "Reward to migrate"); rewards = rewards .try_mutate(|inner| { inner @@ -262,7 +262,7 @@ pub mod v1 { }) .unwrap(); } - log::info!(target: LOG_TARGET, "Found total rewards to migrate: {rewards:?}"); + tracing::info!(target: LOG_TARGET, ?rewards, "Found total rewards to migrate"); Ok(rewards.encode()) } @@ -286,7 +286,7 @@ pub mod v1 { ConstU32<{ u32::MAX }>, > = BoundedBTreeMap::new(); for (key1, key2, reward) in v1::RelayerRewards::::iter() { - log::info!(target: LOG_TARGET, "Migrated rewards: {key1:?}::{key2:?} - {reward:?}"); + tracing::info!(target: LOG_TARGET, ?key1, ?key2, ?reward, "Migrated rewards"); rewards_after = rewards_after .try_mutate(|inner| { inner @@ -296,14 +296,14 @@ pub mod v1 { }) .unwrap(); } - log::info!(target: LOG_TARGET, "Found total migrated rewards: {rewards_after:?}"); + tracing::info!(target: LOG_TARGET, ?rewards_after, "Found total migrated rewards"); frame_support::ensure!( rewards_before == rewards_after, "The rewards were not migrated correctly!." ); - log::info!(target: LOG_TARGET, "migrated all."); + tracing::info!(target: LOG_TARGET, "migrated all."); Ok(()) } } @@ -382,7 +382,7 @@ pub mod v2 { > = BoundedBTreeMap::new(); for (key1, key2, reward) in v1::RelayerRewards::::iter() { let new_key2: T::Reward = key2.into(); - log::info!(target: LOG_TARGET, "Reward to migrate: {key1:?}::{key2:?}->{new_key2:?} - {reward:?}"); + tracing::info!(target: LOG_TARGET, ?key1, ?key2, ?new_key2, ?reward, "Reward to migrate"); rewards = rewards .try_mutate(|inner| { inner @@ -392,7 +392,7 @@ pub mod v2 { }) .unwrap(); } - log::info!(target: LOG_TARGET, "Found total rewards to migrate: {rewards:?}"); + tracing::info!(target: LOG_TARGET, ?rewards, "Found total rewards to migrate"); Ok(rewards.encode()) } @@ -416,7 +416,7 @@ pub mod v2 { ConstU32<{ u32::MAX }>, > = BoundedBTreeMap::new(); for (key1, key2, reward) in v2::RelayerRewards::::iter() { - log::info!(target: LOG_TARGET, "Migrated rewards: {key1:?}::{key2:?} - {reward:?}"); + tracing::info!(target: LOG_TARGET, ?key1, ?key2, ?reward, "Migrated rewards"); rewards_after = rewards_after .try_mutate(|inner| { inner @@ -426,14 +426,14 @@ pub mod v2 { }) .unwrap(); } - log::info!(target: LOG_TARGET, "Found total migrated rewards: {rewards_after:?}"); + tracing::info!(target: LOG_TARGET, ?rewards_after, "Found total migrated rewards"); frame_support::ensure!( rewards_before == rewards_after, "The rewards were not migrated correctly!." ); - log::info!(target: LOG_TARGET, "migrated all."); + tracing::info!(target: LOG_TARGET, "migrated all."); Ok(()) } } diff --git a/bridges/snowbridge/runtime/test-common/Cargo.toml b/bridges/snowbridge/runtime/test-common/Cargo.toml index a4fd7c9562938..68da8579816ed 100644 --- a/bridges/snowbridge/runtime/test-common/Cargo.toml +++ b/bridges/snowbridge/runtime/test-common/Cargo.toml @@ -85,6 +85,7 @@ runtime-benchmarks = [ "pallet-balances/runtime-benchmarks", "pallet-collator-selection/runtime-benchmarks", "pallet-message-queue/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-utility/runtime-benchmarks", "pallet-xcm/runtime-benchmarks", diff --git a/cumulus/pallets/collator-selection/Cargo.toml b/cumulus/pallets/collator-selection/Cargo.toml index eef9e701357c9..dd16585b978e7 100644 --- a/cumulus/pallets/collator-selection/Cargo.toml +++ b/cumulus/pallets/collator-selection/Cargo.toml @@ -46,6 +46,7 @@ runtime-benchmarks = [ "frame-support/runtime-benchmarks", "frame-system/runtime-benchmarks", "pallet-balances/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "sp-runtime/runtime-benchmarks", "sp-staking/runtime-benchmarks", diff --git a/cumulus/pallets/collator-selection/src/benchmarking.rs b/cumulus/pallets/collator-selection/src/benchmarking.rs index 706695106ba69..5d34641aee758 100644 --- a/cumulus/pallets/collator-selection/src/benchmarking.rs +++ b/cumulus/pallets/collator-selection/src/benchmarking.rs @@ -79,6 +79,7 @@ fn register_validators(count: u32) -> Vec(c)).collect::>(); for (who, keys) in validators.clone() { + >::ensure_can_pay_key_deposit(&who).unwrap(); >::set_keys(RawOrigin::Signed(who).into(), keys, Vec::new()).unwrap(); } @@ -158,6 +159,7 @@ mod benchmarks { candidates.push((new_invulnerable.clone(), new_invulnerable_keys)); // set their keys ... for (who, keys) in candidates.clone() { + >::ensure_can_pay_key_deposit(&who).unwrap(); >::set_keys(RawOrigin::Signed(who).into(), keys, Vec::new()) .unwrap(); } @@ -298,6 +300,7 @@ mod benchmarks { let bond: BalanceOf = ::Currency::minimum_balance() * 2u32.into(); ::Currency::make_free_balance_be(&caller, bond); + >::ensure_can_pay_key_deposit(&caller).unwrap(); >::set_keys( RawOrigin::Signed(caller.clone()).into(), keys::(c + 1), @@ -325,6 +328,7 @@ mod benchmarks { let bond: BalanceOf = ::Currency::minimum_balance() * 10u32.into(); ::Currency::make_free_balance_be(&caller, bond); + >::ensure_can_pay_key_deposit(&caller).unwrap(); >::set_keys( RawOrigin::Signed(caller.clone()).into(), keys::(c + 1), @@ -456,5 +460,5 @@ mod benchmarks { } } - impl_benchmark_test_suite!(CollatorSelection, crate::mock::new_test_ext(), crate::mock::Test,); + impl_benchmark_test_suite!(CollatorSelection, crate::mock::new_test_ext(), crate::mock::Test); } diff --git a/cumulus/pallets/session-benchmarking/Cargo.toml b/cumulus/pallets/session-benchmarking/Cargo.toml index 6d77e567c9b6b..307227ccd6464 100644 --- a/cumulus/pallets/session-benchmarking/Cargo.toml +++ b/cumulus/pallets/session-benchmarking/Cargo.toml @@ -29,6 +29,7 @@ runtime-benchmarks = [ "frame-benchmarking/runtime-benchmarks", "frame-support/runtime-benchmarks", "frame-system/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "sp-runtime/runtime-benchmarks", ] std = [ diff --git a/cumulus/pallets/session-benchmarking/src/inner.rs b/cumulus/pallets/session-benchmarking/src/inner.rs index 6c5188921362e..be7d7740be6bd 100644 --- a/cumulus/pallets/session-benchmarking/src/inner.rs +++ b/cumulus/pallets/session-benchmarking/src/inner.rs @@ -35,6 +35,7 @@ mod benchmarks { frame_system::Pallet::::inc_providers(&caller); let keys = T::Keys::decode(&mut sp_runtime::traits::TrailingZeroInput::zeroes()).unwrap(); let proof: Vec = vec![0, 1, 2, 3]; + >::ensure_can_pay_key_deposit(&caller).unwrap(); #[extrinsic_call] _(RawOrigin::Signed(caller), keys, proof); @@ -48,6 +49,7 @@ mod benchmarks { frame_system::Pallet::::inc_providers(&caller); let keys = T::Keys::decode(&mut sp_runtime::traits::TrailingZeroInput::zeroes()).unwrap(); let proof: Vec = vec![0, 1, 2, 3]; + >::ensure_can_pay_key_deposit(&caller).unwrap(); let _t = pallet_session::Pallet::::set_keys( RawOrigin::Signed(caller.clone()).into(), keys, diff --git a/cumulus/pallets/xcmp-queue/src/benchmarking.rs b/cumulus/pallets/xcmp-queue/src/benchmarking.rs index 55916c5513b57..cc6ff9c87b5ea 100644 --- a/cumulus/pallets/xcmp-queue/src/benchmarking.rs +++ b/cumulus/pallets/xcmp-queue/src/benchmarking.rs @@ -59,7 +59,7 @@ mod benchmarks { { assert_ok!(Pallet::::enqueue_xcmp_messages( 0.into(), - &[msg], + &[msg.as_bounded_slice()], &mut WeightMeter::new() )); } @@ -86,7 +86,8 @@ mod benchmarks { }); } - let msgs = vec![Default::default(); n as usize]; + let msg = BoundedVec::new(); + let msgs = vec![msg.as_bounded_slice(); n as usize]; #[cfg(not(test))] let fp_before = T::XcmpQueue::footprint(0.into()); @@ -120,7 +121,7 @@ mod benchmarks { assert_ok!(Pallet::::enqueue_xcmp_messages( 0.into(), - &[BoundedVec::try_from(vec![0; n as usize]).unwrap()], + &[BoundedVec::try_from(vec![0; n as usize]).unwrap().as_bounded_slice()], &mut WeightMeter::new() )); @@ -130,7 +131,7 @@ mod benchmarks { { assert_ok!(Pallet::::enqueue_xcmp_messages( 0.into(), - &[Default::default()], + &[BoundedVec::new().as_bounded_slice()], &mut WeightMeter::new() )); } @@ -169,7 +170,7 @@ mod benchmarks { { assert_ok!(Pallet::::enqueue_xcmp_messages( 0.into(), - &msgs, + &msgs.iter().map(|msg| msg.as_bounded_slice()).collect::>(), &mut WeightMeter::new() )); } @@ -198,7 +199,8 @@ mod benchmarks { get_average_page_pos(MaxXcmpMessageLenOf::::get()) as usize ]) - .unwrap()], + .unwrap() + .as_bounded_slice()], &mut WeightMeter::new() )); @@ -213,7 +215,7 @@ mod benchmarks { { assert_ok!(Pallet::::enqueue_xcmp_messages( 0.into(), - &msgs, + &msgs.iter().map(|msg| msg.as_bounded_slice()).collect::>(), &mut WeightMeter::new() )); } @@ -266,30 +268,14 @@ mod benchmarks { /// Split a singular XCM. #[benchmark] - fn take_first_concatenated_xcm() { - let max_message_size = MaxXcmpMessageLenOf::::get() as usize; - - assert!(MAX_INSTRUCTIONS_TO_DECODE as u32 > MAX_XCM_DECODE_DEPTH, "Preconditon failed"); - let max_instrs = MAX_INSTRUCTIONS_TO_DECODE as u32 - MAX_XCM_DECODE_DEPTH; - let mut xcm = Xcm::(vec![ClearOrigin; max_instrs as usize]); - + fn take_first_concatenated_xcm( + n: Linear<0, { MAX_INSTRUCTIONS_TO_DECODE as u32 - MAX_XCM_DECODE_DEPTH }>, + ) { + let mut xcm = Xcm::(vec![ClearOrigin; n as usize]); for _ in 0..MAX_XCM_DECODE_DEPTH - 1 { xcm = Xcm::(vec![Instruction::SetAppendix(xcm)]); } - let data = VersionedXcm::::from(xcm).encode(); - assert!(data.len() < max_message_size, "Page size is too small"); - // Verify that decoding works with the exact recursion limit: - VersionedXcm::::decode_all_with_depth_limit( - MAX_XCM_DECODE_DEPTH, - &mut &data[..], - ) - .unwrap(); - VersionedXcm::::decode_all_with_depth_limit( - MAX_XCM_DECODE_DEPTH - 1, - &mut &data[..], - ) - .unwrap_err(); #[block] { diff --git a/cumulus/pallets/xcmp-queue/src/lib.rs b/cumulus/pallets/xcmp-queue/src/lib.rs index 5d2ad6c15c895..1f144aa051645 100644 --- a/cumulus/pallets/xcmp-queue/src/lib.rs +++ b/cumulus/pallets/xcmp-queue/src/lib.rs @@ -56,7 +56,7 @@ pub use weights_ext::WeightInfoExt; extern crate alloc; use alloc::{collections::BTreeSet, vec, vec::Vec}; -use bounded_collections::BoundedBTreeSet; +use bounded_collections::{BoundedBTreeSet, BoundedSlice, BoundedVec}; use codec::{Decode, DecodeLimit, Encode, MaxEncodedLen}; use cumulus_primitives_core::{ relay_chain::BlockNumber as RelayBlockNumber, ChannelStatus, GetChannelInfo, MessageSendError, @@ -70,7 +70,6 @@ use frame_support::{ QueuePausedQuery, }, weights::{Weight, WeightMeter}, - BoundedVec, }; use pallet_message_queue::OnQueueChanged; use polkadot_runtime_common::xcm_sender::PriceForMessageDelivery; @@ -641,17 +640,14 @@ impl Pallet { }); } - fn enqueue_xcmp_messages( + fn enqueue_xcmp_messages<'a>( sender: ParaId, - xcms: &[BoundedVec>], + xcms: &[BoundedSlice<'a, u8, MaxXcmpMessageLenOf>], meter: &mut WeightMeter, ) -> Result<(), ()> { let QueueConfigData { drop_threshold, .. } = >::get(); - let batches_footprints = T::XcmpQueue::get_batches_footprints( - sender, - xcms.iter().map(|xcm| xcm.as_bounded_slice()), - drop_threshold, - ); + let batches_footprints = + T::XcmpQueue::get_batches_footprints(sender, xcms.iter().copied(), drop_threshold); let best_batch_footprint = batches_footprints.search_best_by(|batch_info| { let required_weight = T::WeightInfo::enqueue_xcmp_messages( @@ -670,9 +666,7 @@ impl Pallet { best_batch_footprint, )); T::XcmpQueue::enqueue_messages( - xcms.iter() - .take(best_batch_footprint.msgs_count) - .map(|xcm| xcm.as_bounded_slice()), + xcms.iter().take(best_batch_footprint.msgs_count).copied(), sender, ); @@ -695,42 +689,62 @@ impl Pallet { /// /// On error returns a partial batch with all the XCMs processed before the failure. /// This can happen in case of a decoding/re-encoding failure. - pub(crate) fn take_first_concatenated_xcm( - data: &mut &[u8], + pub(crate) fn take_first_concatenated_xcm<'a>( + data: &mut &'a [u8], meter: &mut WeightMeter, - ) -> Result>>, ()> { + ) -> Result>>, ()> { if data.is_empty() { return Ok(None) } - if meter.try_consume(T::WeightInfo::take_first_concatenated_xcm()).is_err() { + // Let's make sure that we can decode at least an empty xcm message. + let base_weight = T::WeightInfo::take_first_concatenated_xcm(0); + if meter.try_consume(base_weight).is_err() { defensive!("Out of weight; could not decode all; dropping"); return Err(()) } - let xcm = VersionedXcm::<()>::decode_with_depth_limit(MAX_XCM_DECODE_DEPTH, data).map_err( + let input_data = &mut &data[..]; + let mut input = codec::CountedInput::new(input_data); + VersionedXcm::<()>::decode_with_depth_limit(MAX_XCM_DECODE_DEPTH, &mut input).map_err( |error| { tracing::debug!(target: LOG_TARGET, ?error, "Failed to decode XCM with depth limit"); () }, )?; - Ok(Some(xcm.encode().try_into().map_err(|error| { - tracing::debug!(target: LOG_TARGET, ?error, "Failed to encode XCM after decoding"); + let (xcm_data, remaining_data) = data.split_at(input.count() as usize); + *data = remaining_data; + + // Consume the extra weight that it took to decode this message. + // This depends on the message len in bytes. + // Saturates if it's over the limit. + let extra_weight = + T::WeightInfo::take_first_concatenated_xcm(xcm_data.len() as u32) - base_weight; + meter.consume(extra_weight); + + let xcm = Some(BoundedSlice::try_from(xcm_data).map_err(|error| { + tracing::error!( + target: LOG_TARGET, + ?error, + "Failed to take XCM after decoding: message is too long" + ); () - })?)) + })?); + + Ok(xcm) } /// Split concatenated encoded `VersionedXcm`s or `MaybeDoubleEncodedVersionedXcm`s into /// batches. /// /// We directly encode them again since that is needed later on. - pub(crate) fn take_first_concatenated_xcms( - data: &mut &[u8], + pub(crate) fn take_first_concatenated_xcms<'a>( + data: &mut &'a [u8], batch_size: usize, meter: &mut WeightMeter, ) -> Result< - Vec>>, - Vec>>, + Vec>>, + Vec>>, > { let mut batch = vec![]; loop { diff --git a/cumulus/pallets/xcmp-queue/src/tests.rs b/cumulus/pallets/xcmp-queue/src/tests.rs index cefbe401df1d7..fbaacc9e682c3 100644 --- a/cumulus/pallets/xcmp-queue/src/tests.rs +++ b/cumulus/pallets/xcmp-queue/src/tests.rs @@ -220,7 +220,11 @@ fn xcm_enqueueing_starts_dropping_on_out_of_weight() { ); let mut weight_meter = WeightMeter::with_limit(required_weight); - let res = XcmpQueue::enqueue_xcmp_messages(1000.into(), &xcms, &mut weight_meter); + let res = XcmpQueue::enqueue_xcmp_messages( + 1000.into(), + &xcms.iter().map(|xcm| xcm.as_bounded_slice()).collect::>(), + &mut weight_meter, + ); if idx < xcms.len() - 1 { assert!(res.is_err()); } else { @@ -709,10 +713,10 @@ fn take_first_concatenated_xcm_works() { .unwrap(); match i % 2 { 0 => { - assert_eq!(xcm, versioned_xcm(older_xcm_version).encode()); + assert_eq!(xcm.to_vec(), versioned_xcm(older_xcm_version).encode()); }, 1 => { - assert_eq!(xcm, versioned_xcm(newer_xcm_version).encode()); + assert_eq!(xcm.to_vec(), versioned_xcm(newer_xcm_version).encode()); }, unexpected => unreachable!("{:?}", unexpected), } @@ -756,11 +760,11 @@ fn take_first_concatenated_xcms_works() { let data = &mut &page[1..]; assert_eq!( XcmpQueue::take_first_concatenated_xcms(data, 5, &mut WeightMeter::new()), - Ok(generate_mock_xcm_batch(0, 5)) + Ok(generate_mock_xcm_batch(0, 5).iter().map(|xcm| xcm.as_bounded_slice()).collect()) ); assert_eq!( XcmpQueue::take_first_concatenated_xcms(data, 5, &mut WeightMeter::new()), - Ok(generate_mock_xcm_batch(5, 4)) + Ok(generate_mock_xcm_batch(5, 4).iter().map(|xcm| xcm.as_bounded_slice()).collect()) ); // Should return partial batch on error @@ -770,7 +774,7 @@ fn take_first_concatenated_xcms_works() { page.extend(generate_mock_xcm(5).encode()); assert_eq!( XcmpQueue::take_first_concatenated_xcms(&mut &page[1..], 10, &mut WeightMeter::new()), - Err(generate_mock_xcm_batch(0, 5)) + Err(generate_mock_xcm_batch(0, 5).iter().map(|xcm| xcm.as_bounded_slice()).collect()) ); } diff --git a/cumulus/pallets/xcmp-queue/src/weights.rs b/cumulus/pallets/xcmp-queue/src/weights.rs index 5ae717a164bbb..dad34691d5907 100644 --- a/cumulus/pallets/xcmp-queue/src/weights.rs +++ b/cumulus/pallets/xcmp-queue/src/weights.rs @@ -16,7 +16,7 @@ //! Autogenerated weights for `cumulus_pallet_xcmp_queue` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-04-25, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` //! HOSTNAME: `Serbans-MacBook-Pro.local`, CPU: `` //! WASM-EXECUTION: `Compiled`, CHAIN: `Some("asset-hub-westend-dev")`, DB CACHE: `1024` @@ -55,7 +55,7 @@ pub trait WeightInfo { fn enqueue_1000_small_xcmp_messages() -> Weight; fn suspend_channel() -> Weight; fn resume_channel() -> Weight; - fn take_first_concatenated_xcm() -> Weight; + fn take_first_concatenated_xcm(n: u32, ) -> Weight; fn on_idle_good_msg() -> Weight; fn on_idle_large_msg() -> Weight; } @@ -67,10 +67,10 @@ impl WeightInfo for SubstrateWeight { /// Proof: `XcmpQueue::QueueConfig` (`max_values`: Some(1), `max_size`: Some(12), added: 507, mode: `MaxEncodedLen`) fn set_config_with_u32() -> Weight { // Proof Size summary in bytes: - // Measured: `109` + // Measured: `175` // Estimated: `1497` - // Minimum execution time: 2_000_000 picoseconds. - Weight::from_parts(3_000_000, 1497) + // Minimum execution time: 3_000_000 picoseconds. + Weight::from_parts(4_000_000, 1497) .saturating_add(T::DbWeight::get().reads(1_u64)) .saturating_add(T::DbWeight::get().writes(1_u64)) } @@ -87,12 +87,12 @@ impl WeightInfo for SubstrateWeight { /// The range of component `n` is `[0, 105467]`. fn enqueue_n_bytes_xcmp_message(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `151` + // Measured: `251` // Estimated: `5487` - // Minimum execution time: 8_000_000 picoseconds. - Weight::from_parts(9_115_841, 5487) + // Minimum execution time: 10_000_000 picoseconds. + Weight::from_parts(12_286_920, 5487) // Standard Error: 1 - .saturating_add(Weight::from_parts(155, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(194, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4_u64)) .saturating_add(T::DbWeight::get().writes(3_u64)) } @@ -109,12 +109,12 @@ impl WeightInfo for SubstrateWeight { /// The range of component `n` is `[0, 1000]`. fn enqueue_n_empty_xcmp_messages(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `151` + // Measured: `251` // Estimated: `5487` - // Minimum execution time: 7_000_000 picoseconds. - Weight::from_parts(8_987_577, 5487) - // Standard Error: 313 - .saturating_add(Weight::from_parts(94_980, 0).saturating_mul(n.into())) + // Minimum execution time: 8_000_000 picoseconds. + Weight::from_parts(13_439_195, 5487) + // Standard Error: 498 + .saturating_add(Weight::from_parts(130_951, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4_u64)) .saturating_add(T::DbWeight::get().writes(3_u64)) } @@ -129,12 +129,12 @@ impl WeightInfo for SubstrateWeight { /// The range of component `n` is `[0, 105457]`. fn enqueue_empty_xcmp_message_at(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `334 + n * (1 ±0)` + // Measured: `434 + n * (1 ±0)` // Estimated: `108986` - // Minimum execution time: 12_000_000 picoseconds. - Weight::from_parts(11_015_940, 108986) - // Standard Error: 32 - .saturating_add(Weight::from_parts(911, 0).saturating_mul(n.into())) + // Minimum execution time: 15_000_000 picoseconds. + Weight::from_parts(15_354_447, 108986) + // Standard Error: 5 + .saturating_add(Weight::from_parts(747, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4_u64)) .saturating_add(T::DbWeight::get().writes(2_u64)) } @@ -151,12 +151,12 @@ impl WeightInfo for SubstrateWeight { /// The range of component `n` is `[0, 100]`. fn enqueue_n_full_pages(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `186` + // Measured: `286` // Estimated: `5487` - // Minimum execution time: 7_000_000 picoseconds. - Weight::from_parts(7_000_000, 5487) - // Standard Error: 20_150 - .saturating_add(Weight::from_parts(20_690_483, 0).saturating_mul(n.into())) + // Minimum execution time: 10_000_000 picoseconds. + Weight::from_parts(10_000_000, 5487) + // Standard Error: 31_014 + .saturating_add(Weight::from_parts(24_068_862, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4_u64)) .saturating_add(T::DbWeight::get().writes(2_u64)) .saturating_add(T::DbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -171,10 +171,10 @@ impl WeightInfo for SubstrateWeight { /// Proof: `XcmpQueue::InboundXcmpSuspended` (`max_values`: Some(1), `max_size`: Some(4002), added: 4497, mode: `MaxEncodedLen`) fn enqueue_1000_small_xcmp_messages() -> Weight { // Proof Size summary in bytes: - // Measured: `53067` + // Measured: `53167` // Estimated: `108986` - // Minimum execution time: 139_000_000 picoseconds. - Weight::from_parts(148_000_000, 108986) + // Minimum execution time: 172_000_000 picoseconds. + Weight::from_parts(181_000_000, 108986) .saturating_add(T::DbWeight::get().reads(4_u64)) .saturating_add(T::DbWeight::get().writes(2_u64)) } @@ -182,9 +182,9 @@ impl WeightInfo for SubstrateWeight { /// Proof: `XcmpQueue::OutboundXcmpStatus` (`max_values`: Some(1), `max_size`: Some(1282), added: 1777, mode: `MaxEncodedLen`) fn suspend_channel() -> Weight { // Proof Size summary in bytes: - // Measured: `109` + // Measured: `175` // Estimated: `2767` - // Minimum execution time: 1_000_000 picoseconds. + // Minimum execution time: 2_000_000 picoseconds. Weight::from_parts(2_000_000, 2767) .saturating_add(T::DbWeight::get().reads(1_u64)) .saturating_add(T::DbWeight::get().writes(1_u64)) @@ -193,19 +193,22 @@ impl WeightInfo for SubstrateWeight { /// Proof: `XcmpQueue::OutboundXcmpStatus` (`max_values`: Some(1), `max_size`: Some(1282), added: 1777, mode: `MaxEncodedLen`) fn resume_channel() -> Weight { // Proof Size summary in bytes: - // Measured: `144` + // Measured: `210` // Estimated: `2767` // Minimum execution time: 2_000_000 picoseconds. Weight::from_parts(3_000_000, 2767) .saturating_add(T::DbWeight::get().reads(1_u64)) .saturating_add(T::DbWeight::get().writes(1_u64)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 6_000_000 picoseconds. - Weight::from_parts(7_000_000, 0) + // Minimum execution time: 1_000_000 picoseconds. + Weight::from_parts(1_825_791, 0) + // Standard Error: 564 + .saturating_add(Weight::from_parts(44_073, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -223,10 +226,10 @@ impl WeightInfo for SubstrateWeight { /// Proof: `MessageQueue::Pages` (`max_values`: None, `max_size`: Some(105521), added: 107996, mode: `MaxEncodedLen`) fn on_idle_good_msg() -> Weight { // Proof Size summary in bytes: - // Measured: `105716` - // Estimated: `109181` - // Minimum execution time: 66_000_000 picoseconds. - Weight::from_parts(71_000_000, 109181) + // Measured: `105816` + // Estimated: `109281` + // Minimum execution time: 63_000_000 picoseconds. + Weight::from_parts(67_000_000, 109281) .saturating_add(T::DbWeight::get().reads(6_u64)) .saturating_add(T::DbWeight::get().writes(5_u64)) } @@ -246,10 +249,10 @@ impl WeightInfo for SubstrateWeight { /// Proof: `MessageQueue::Pages` (`max_values`: None, `max_size`: Some(105521), added: 107996, mode: `MaxEncodedLen`) fn on_idle_large_msg() -> Weight { // Proof Size summary in bytes: - // Measured: `65785` - // Estimated: `69250` - // Minimum execution time: 39_000_000 picoseconds. - Weight::from_parts(45_000_000, 69250) + // Measured: `65885` + // Estimated: `69350` + // Minimum execution time: 45_000_000 picoseconds. + Weight::from_parts(47_000_000, 69350) .saturating_add(T::DbWeight::get().reads(6_u64)) .saturating_add(T::DbWeight::get().writes(5_u64)) } @@ -261,10 +264,10 @@ impl WeightInfo for () { /// Proof: `XcmpQueue::QueueConfig` (`max_values`: Some(1), `max_size`: Some(12), added: 507, mode: `MaxEncodedLen`) fn set_config_with_u32() -> Weight { // Proof Size summary in bytes: - // Measured: `109` + // Measured: `175` // Estimated: `1497` - // Minimum execution time: 2_000_000 picoseconds. - Weight::from_parts(3_000_000, 1497) + // Minimum execution time: 3_000_000 picoseconds. + Weight::from_parts(4_000_000, 1497) .saturating_add(RocksDbWeight::get().reads(1_u64)) .saturating_add(RocksDbWeight::get().writes(1_u64)) } @@ -281,12 +284,12 @@ impl WeightInfo for () { /// The range of component `n` is `[0, 105467]`. fn enqueue_n_bytes_xcmp_message(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `151` + // Measured: `251` // Estimated: `5487` - // Minimum execution time: 8_000_000 picoseconds. - Weight::from_parts(9_115_841, 5487) + // Minimum execution time: 10_000_000 picoseconds. + Weight::from_parts(12_286_920, 5487) // Standard Error: 1 - .saturating_add(Weight::from_parts(155, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(194, 0).saturating_mul(n.into())) .saturating_add(RocksDbWeight::get().reads(4_u64)) .saturating_add(RocksDbWeight::get().writes(3_u64)) } @@ -303,12 +306,12 @@ impl WeightInfo for () { /// The range of component `n` is `[0, 1000]`. fn enqueue_n_empty_xcmp_messages(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `151` + // Measured: `251` // Estimated: `5487` - // Minimum execution time: 7_000_000 picoseconds. - Weight::from_parts(8_987_577, 5487) - // Standard Error: 313 - .saturating_add(Weight::from_parts(94_980, 0).saturating_mul(n.into())) + // Minimum execution time: 8_000_000 picoseconds. + Weight::from_parts(13_439_195, 5487) + // Standard Error: 498 + .saturating_add(Weight::from_parts(130_951, 0).saturating_mul(n.into())) .saturating_add(RocksDbWeight::get().reads(4_u64)) .saturating_add(RocksDbWeight::get().writes(3_u64)) } @@ -323,12 +326,12 @@ impl WeightInfo for () { /// The range of component `n` is `[0, 105457]`. fn enqueue_empty_xcmp_message_at(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `334 + n * (1 ±0)` + // Measured: `434 + n * (1 ±0)` // Estimated: `108986` - // Minimum execution time: 12_000_000 picoseconds. - Weight::from_parts(11_015_940, 108986) - // Standard Error: 32 - .saturating_add(Weight::from_parts(911, 0).saturating_mul(n.into())) + // Minimum execution time: 15_000_000 picoseconds. + Weight::from_parts(15_354_447, 108986) + // Standard Error: 5 + .saturating_add(Weight::from_parts(747, 0).saturating_mul(n.into())) .saturating_add(RocksDbWeight::get().reads(4_u64)) .saturating_add(RocksDbWeight::get().writes(2_u64)) } @@ -345,12 +348,12 @@ impl WeightInfo for () { /// The range of component `n` is `[0, 100]`. fn enqueue_n_full_pages(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `186` + // Measured: `286` // Estimated: `5487` - // Minimum execution time: 7_000_000 picoseconds. - Weight::from_parts(7_000_000, 5487) - // Standard Error: 20_150 - .saturating_add(Weight::from_parts(20_690_483, 0).saturating_mul(n.into())) + // Minimum execution time: 10_000_000 picoseconds. + Weight::from_parts(10_000_000, 5487) + // Standard Error: 31_014 + .saturating_add(Weight::from_parts(24_068_862, 0).saturating_mul(n.into())) .saturating_add(RocksDbWeight::get().reads(4_u64)) .saturating_add(RocksDbWeight::get().writes(2_u64)) .saturating_add(RocksDbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -365,10 +368,10 @@ impl WeightInfo for () { /// Proof: `XcmpQueue::InboundXcmpSuspended` (`max_values`: Some(1), `max_size`: Some(4002), added: 4497, mode: `MaxEncodedLen`) fn enqueue_1000_small_xcmp_messages() -> Weight { // Proof Size summary in bytes: - // Measured: `53067` + // Measured: `53167` // Estimated: `108986` - // Minimum execution time: 139_000_000 picoseconds. - Weight::from_parts(148_000_000, 108986) + // Minimum execution time: 172_000_000 picoseconds. + Weight::from_parts(181_000_000, 108986) .saturating_add(RocksDbWeight::get().reads(4_u64)) .saturating_add(RocksDbWeight::get().writes(2_u64)) } @@ -376,9 +379,9 @@ impl WeightInfo for () { /// Proof: `XcmpQueue::OutboundXcmpStatus` (`max_values`: Some(1), `max_size`: Some(1282), added: 1777, mode: `MaxEncodedLen`) fn suspend_channel() -> Weight { // Proof Size summary in bytes: - // Measured: `109` + // Measured: `175` // Estimated: `2767` - // Minimum execution time: 1_000_000 picoseconds. + // Minimum execution time: 2_000_000 picoseconds. Weight::from_parts(2_000_000, 2767) .saturating_add(RocksDbWeight::get().reads(1_u64)) .saturating_add(RocksDbWeight::get().writes(1_u64)) @@ -387,19 +390,22 @@ impl WeightInfo for () { /// Proof: `XcmpQueue::OutboundXcmpStatus` (`max_values`: Some(1), `max_size`: Some(1282), added: 1777, mode: `MaxEncodedLen`) fn resume_channel() -> Weight { // Proof Size summary in bytes: - // Measured: `144` + // Measured: `210` // Estimated: `2767` // Minimum execution time: 2_000_000 picoseconds. Weight::from_parts(3_000_000, 2767) .saturating_add(RocksDbWeight::get().reads(1_u64)) .saturating_add(RocksDbWeight::get().writes(1_u64)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 6_000_000 picoseconds. - Weight::from_parts(7_000_000, 0) + // Minimum execution time: 1_000_000 picoseconds. + Weight::from_parts(1_825_791, 0) + // Standard Error: 564 + .saturating_add(Weight::from_parts(44_073, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -417,10 +423,10 @@ impl WeightInfo for () { /// Proof: `MessageQueue::Pages` (`max_values`: None, `max_size`: Some(105521), added: 107996, mode: `MaxEncodedLen`) fn on_idle_good_msg() -> Weight { // Proof Size summary in bytes: - // Measured: `105716` - // Estimated: `109181` - // Minimum execution time: 66_000_000 picoseconds. - Weight::from_parts(71_000_000, 109181) + // Measured: `105816` + // Estimated: `109281` + // Minimum execution time: 63_000_000 picoseconds. + Weight::from_parts(67_000_000, 109281) .saturating_add(RocksDbWeight::get().reads(6_u64)) .saturating_add(RocksDbWeight::get().writes(5_u64)) } @@ -440,10 +446,10 @@ impl WeightInfo for () { /// Proof: `MessageQueue::Pages` (`max_values`: None, `max_size`: Some(105521), added: 107996, mode: `MaxEncodedLen`) fn on_idle_large_msg() -> Weight { // Proof Size summary in bytes: - // Measured: `65785` - // Estimated: `69250` - // Minimum execution time: 39_000_000 picoseconds. - Weight::from_parts(45_000_000, 69250) + // Measured: `65885` + // Estimated: `69350` + // Minimum execution time: 45_000_000 picoseconds. + Weight::from_parts(47_000_000, 69350) .saturating_add(RocksDbWeight::get().reads(6_u64)) .saturating_add(RocksDbWeight::get().writes(5_u64)) } diff --git a/cumulus/parachains/integration-tests/emulated/common/src/xcm_helpers.rs b/cumulus/parachains/integration-tests/emulated/common/src/xcm_helpers.rs index a990e70434b1e..7a355337f11d1 100644 --- a/cumulus/parachains/integration-tests/emulated/common/src/xcm_helpers.rs +++ b/cumulus/parachains/integration-tests/emulated/common/src/xcm_helpers.rs @@ -92,19 +92,34 @@ pub fn get_amount_from_versioned_assets(assets: VersionedAssets) -> u128 { amount } +fn to_mq_processed_id(event: C::RuntimeEvent) -> Option +where + ::Runtime: pallet_message_queue::Config, + C::RuntimeEvent: TryInto::Runtime>>, +{ + if let Ok(pallet_message_queue::Event::Processed { id, .. }) = event.try_into() { + Some(id) + } else { + None + } +} + +/// Helper method to find all `Event::Processed` IDs from the chain's events. +pub fn find_all_mq_processed_ids() -> Vec +where + ::Runtime: pallet_message_queue::Config, + C::RuntimeEvent: TryInto::Runtime>>, +{ + C::events().into_iter().filter_map(to_mq_processed_id::).collect() +} + /// Helper method to find the ID of the first `Event::Processed` event in the chain's events. pub fn find_mq_processed_id() -> Option where ::Runtime: pallet_message_queue::Config, C::RuntimeEvent: TryInto::Runtime>>, { - C::events().into_iter().find_map(|event| { - if let Ok(pallet_message_queue::Event::Processed { id, .. }) = event.try_into() { - Some(id) - } else { - None - } - }) + C::events().into_iter().find_map(to_mq_processed_id::) } /// Helper method to find the message ID of the first `Event::Sent` event in the chain's events. diff --git a/cumulus/parachains/integration-tests/emulated/tests/bridges/bridge-hub-westend/src/tests/asset_transfers.rs b/cumulus/parachains/integration-tests/emulated/tests/bridges/bridge-hub-westend/src/tests/asset_transfers.rs index 6bd130110eb7d..fa641e13c09fa 100644 --- a/cumulus/parachains/integration-tests/emulated/tests/bridges/bridge-hub-westend/src/tests/asset_transfers.rs +++ b/cumulus/parachains/integration-tests/emulated/tests/bridges/bridge-hub-westend/src/tests/asset_transfers.rs @@ -16,7 +16,7 @@ use crate::tests::{snowbridge_common::snowbridge_sovereign, *}; use emulated_integration_tests_common::{ macros::Dmp, - xcm_helpers::{find_mq_processed_id, find_xcm_sent_message_id}, + xcm_helpers::{find_all_mq_processed_ids, find_mq_processed_id, find_xcm_sent_message_id}, xcm_simulator::helpers::TopicIdTracker, }; use xcm::latest::AssetTransferFilter; @@ -1145,7 +1145,7 @@ fn send_back_rocs_from_penpal_westend_through_asset_hub_westend_to_asset_hub_roc ); let msg_sent_id = - find_xcm_sent_message_id::().expect("Missing Sent Event"); + find_xcm_sent_message_id::().expect("Missing Sent Event on PenpalB"); topic_id_tracker.insert("PenpalB", msg_sent_id.into()); result @@ -1171,9 +1171,9 @@ fn send_back_rocs_from_penpal_westend_through_asset_hub_westend_to_asset_hub_roc ) => {}, ] ); - let mq_prc_id = - find_mq_processed_id::().expect("Missing Processed Event"); - topic_id_tracker.insert("AssetHubWestend", mq_prc_id); + let mq_prc_ids = find_all_mq_processed_ids::(); + assert!(!mq_prc_ids.is_empty(), "Missing Processed Event on AssetHubWestend"); + topic_id_tracker.insert_all("AssetHubWestend", &mq_prc_ids); }); }); } @@ -1200,10 +1200,11 @@ fn send_back_rocs_from_penpal_westend_through_asset_hub_westend_to_asset_hub_roc ) => {}, ] ); - let mq_prc_id = find_mq_processed_id::().expect("Missing Processed Event"); - topic_id_tracker.insert("AssetHubRococo", mq_prc_id); + let mq_prc_ids = find_all_mq_processed_ids::(); + assert!(!mq_prc_ids.is_empty(), "Missing Processed Event on AssetHubRococo"); + topic_id_tracker.insert_all("AssetHubRococo", &mq_prc_ids); }); - topic_id_tracker.assert_unique(); + topic_id_tracker.assert_only_id_seen_on_all_chains("PenpalB"); let sender_rocs_after = PenpalB::execute_with(|| { type ForeignAssets = ::ForeignAssets; @@ -1482,8 +1483,9 @@ fn send_pens_and_wnds_from_penpal_westend_via_ahw_to_ahr() { let wnd = Location::new(2, [GlobalConsensus(ByGenesis(WESTEND_GENESIS_HASH))]); AssetHubRococo::execute_with(|| { type RuntimeEvent = ::RuntimeEvent; - let mq_prc_id = find_mq_processed_id::().expect("Missing Processed Event"); - topic_id_tracker.insert_and_assert_unique("AssetHubRococo", mq_prc_id); + let mq_prc_ids = find_all_mq_processed_ids::(); + assert!(!mq_prc_ids.is_empty(), "Missing Processed Event on AssetHubRococo"); + topic_id_tracker.insert_all("AssetHubRococo", &mq_prc_ids); assert_expected_events!( AssetHubRococo, vec![ @@ -1500,8 +1502,8 @@ fn send_pens_and_wnds_from_penpal_westend_via_ahw_to_ahr() { ); }); - // assert unique topic across all chains - topic_id_tracker.assert_unique(); + // assert that the only topic ID on 'PenpalB' exists on all chains + topic_id_tracker.assert_only_id_seen_on_all_chains("PenpalB"); // account balances after let sender_wnds_after = PenpalB::execute_with(|| { diff --git a/cumulus/parachains/runtimes/assets/asset-hub-rococo/Cargo.toml b/cumulus/parachains/runtimes/assets/asset-hub-rococo/Cargo.toml index 48e8b651ebc46..7c444359209de 100644 --- a/cumulus/parachains/runtimes/assets/asset-hub-rococo/Cargo.toml +++ b/cumulus/parachains/runtimes/assets/asset-hub-rococo/Cargo.toml @@ -133,6 +133,7 @@ runtime-benchmarks = [ "pallet-nft-fractionalization/runtime-benchmarks", "pallet-nfts/runtime-benchmarks", "pallet-proxy/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-transaction-payment/runtime-benchmarks", "pallet-uniques/runtime-benchmarks", diff --git a/cumulus/parachains/runtimes/assets/asset-hub-rococo/src/lib.rs b/cumulus/parachains/runtimes/assets/asset-hub-rococo/src/lib.rs index c26c17fbb7adf..abb842085d437 100644 --- a/cumulus/parachains/runtimes/assets/asset-hub-rococo/src/lib.rs +++ b/cumulus/parachains/runtimes/assets/asset-hub-rococo/src/lib.rs @@ -129,7 +129,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("statemine"), impl_name: alloc::borrow::Cow::Borrowed("statemine"), authoring_version: 1, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 16, diff --git a/cumulus/parachains/runtimes/assets/asset-hub-rococo/src/weights/cumulus_pallet_xcmp_queue.rs b/cumulus/parachains/runtimes/assets/asset-hub-rococo/src/weights/cumulus_pallet_xcmp_queue.rs index ddc76fe451ad6..a5fe66fae5b0a 100644 --- a/cumulus/parachains/runtimes/assets/asset-hub-rococo/src/weights/cumulus_pallet_xcmp_queue.rs +++ b/cumulus/parachains/runtimes/assets/asset-hub-rococo/src/weights/cumulus_pallet_xcmp_queue.rs @@ -16,9 +16,9 @@ //! Autogenerated weights for `cumulus_pallet_xcmp_queue` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-05-05, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `16d5a52ef0dc`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `b8d1375f7728`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -56,8 +56,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `109` // Estimated: `1497` - // Minimum execution time: 4_908_000 picoseconds. - Weight::from_parts(5_133_000, 0) + // Minimum execution time: 4_959_000 picoseconds. + Weight::from_parts(5_329_000, 0) .saturating_add(Weight::from_parts(0, 1497)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -77,11 +77,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `151` // Estimated: `5487` - // Minimum execution time: 13_653_000 picoseconds. - Weight::from_parts(9_457_298, 0) + // Minimum execution time: 14_349_000 picoseconds. + Weight::from_parts(9_748_630, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 6 - .saturating_add(Weight::from_parts(1_016, 0).saturating_mul(n.into())) + // Standard Error: 7 + .saturating_add(Weight::from_parts(1_042, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -100,11 +100,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `151` // Estimated: `5487` - // Minimum execution time: 11_593_000 picoseconds. - Weight::from_parts(15_263_900, 0) + // Minimum execution time: 12_178_000 picoseconds. + Weight::from_parts(17_653_288, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 239 - .saturating_add(Weight::from_parts(136_065, 0).saturating_mul(n.into())) + // Standard Error: 291 + .saturating_add(Weight::from_parts(142_184, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -121,11 +121,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `334 + n * (1 ±0)` // Estimated: `108986` - // Minimum execution time: 20_217_000 picoseconds. - Weight::from_parts(20_647_000, 0) + // Minimum execution time: 21_593_000 picoseconds. + Weight::from_parts(12_434_518, 0) .saturating_add(Weight::from_parts(0, 108986)) - // Standard Error: 12 - .saturating_add(Weight::from_parts(2_576, 0).saturating_mul(n.into())) + // Standard Error: 13 + .saturating_add(Weight::from_parts(2_294, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) } @@ -144,11 +144,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `186` // Estimated: `5487` - // Minimum execution time: 13_262_000 picoseconds. - Weight::from_parts(13_670_000, 0) + // Minimum execution time: 13_602_000 picoseconds. + Weight::from_parts(13_864_000, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 81_154 - .saturating_add(Weight::from_parts(105_979_285, 0).saturating_mul(n.into())) + // Standard Error: 96_416 + .saturating_add(Weight::from_parts(98_057_393, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) .saturating_add(T::DbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -165,8 +165,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `53067` // Estimated: `108986` - // Minimum execution time: 289_304_000 picoseconds. - Weight::from_parts(299_215_000, 0) + // Minimum execution time: 275_630_000 picoseconds. + Weight::from_parts(282_810_000, 0) .saturating_add(Weight::from_parts(0, 108986)) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) @@ -177,8 +177,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `109` // Estimated: `2767` - // Minimum execution time: 3_121_000 picoseconds. - Weight::from_parts(3_254_000, 0) + // Minimum execution time: 3_200_000 picoseconds. + Weight::from_parts(3_393_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -189,19 +189,22 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `144` // Estimated: `2767` - // Minimum execution time: 4_409_000 picoseconds. - Weight::from_parts(4_555_000, 0) + // Minimum execution time: 4_456_000 picoseconds. + Weight::from_parts(4_669_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 5_368_000 picoseconds. - Weight::from_parts(5_614_000, 0) + // Minimum execution time: 2_048_000 picoseconds. + Weight::from_parts(2_441_692, 0) .saturating_add(Weight::from_parts(0, 0)) + // Standard Error: 143 + .saturating_add(Weight::from_parts(17_966, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -221,8 +224,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `105716` // Estimated: `109181` - // Minimum execution time: 231_957_000 picoseconds. - Weight::from_parts(242_676_000, 0) + // Minimum execution time: 187_620_000 picoseconds. + Weight::from_parts(209_054_000, 0) .saturating_add(Weight::from_parts(0, 109181)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) @@ -245,8 +248,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `65785` // Estimated: `69250` - // Minimum execution time: 134_722_000 picoseconds. - Weight::from_parts(138_495_000, 0) + // Minimum execution time: 126_787_000 picoseconds. + Weight::from_parts(133_110_000, 0) .saturating_add(Weight::from_parts(0, 69250)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) diff --git a/cumulus/parachains/runtimes/assets/asset-hub-westend/Cargo.toml b/cumulus/parachains/runtimes/assets/asset-hub-westend/Cargo.toml index 26bf9731690bb..7944e1ff40414 100644 --- a/cumulus/parachains/runtimes/assets/asset-hub-westend/Cargo.toml +++ b/cumulus/parachains/runtimes/assets/asset-hub-westend/Cargo.toml @@ -183,6 +183,7 @@ runtime-benchmarks = [ "pallet-referenda/runtime-benchmarks", "pallet-revive/runtime-benchmarks", "pallet-scheduler/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking-async-rc-client/runtime-benchmarks", "pallet-staking-async/runtime-benchmarks", "pallet-staking/runtime-benchmarks", diff --git a/cumulus/parachains/runtimes/assets/asset-hub-westend/src/lib.rs b/cumulus/parachains/runtimes/assets/asset-hub-westend/src/lib.rs index 46094e233b1c7..f0ef5432aeda7 100644 --- a/cumulus/parachains/runtimes/assets/asset-hub-westend/src/lib.rs +++ b/cumulus/parachains/runtimes/assets/asset-hub-westend/src/lib.rs @@ -145,7 +145,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("westmint"), impl_name: alloc::borrow::Cow::Borrowed("westmint"), authoring_version: 1, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 16, diff --git a/cumulus/parachains/runtimes/assets/asset-hub-westend/src/weights/cumulus_pallet_xcmp_queue.rs b/cumulus/parachains/runtimes/assets/asset-hub-westend/src/weights/cumulus_pallet_xcmp_queue.rs index a3e0129468d65..0d303d5c77eb0 100644 --- a/cumulus/parachains/runtimes/assets/asset-hub-westend/src/weights/cumulus_pallet_xcmp_queue.rs +++ b/cumulus/parachains/runtimes/assets/asset-hub-westend/src/weights/cumulus_pallet_xcmp_queue.rs @@ -16,9 +16,9 @@ //! Autogenerated weights for `cumulus_pallet_xcmp_queue` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-05-05, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `16d5a52ef0dc`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `b8d1375f7728`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -54,10 +54,10 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// Proof: `XcmpQueue::QueueConfig` (`max_values`: Some(1), `max_size`: Some(12), added: 507, mode: `MaxEncodedLen`) fn set_config_with_u32() -> Weight { // Proof Size summary in bytes: - // Measured: `109` + // Measured: `175` // Estimated: `1497` - // Minimum execution time: 4_883_000 picoseconds. - Weight::from_parts(5_223_000, 0) + // Minimum execution time: 5_238_000 picoseconds. + Weight::from_parts(5_695_000, 0) .saturating_add(Weight::from_parts(0, 1497)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -75,13 +75,13 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// The range of component `n` is `[0, 105467]`. fn enqueue_n_bytes_xcmp_message(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `151` + // Measured: `251` // Estimated: `5487` - // Minimum execution time: 13_840_000 picoseconds. - Weight::from_parts(8_982_973, 0) + // Minimum execution time: 15_235_000 picoseconds. + Weight::from_parts(11_414_155, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 6 - .saturating_add(Weight::from_parts(995, 0).saturating_mul(n.into())) + // Standard Error: 7 + .saturating_add(Weight::from_parts(1_044, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -98,13 +98,13 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// The range of component `n` is `[0, 1000]`. fn enqueue_n_empty_xcmp_messages(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `151` + // Measured: `251` // Estimated: `5487` - // Minimum execution time: 12_129_000 picoseconds. - Weight::from_parts(15_937_292, 0) + // Minimum execution time: 12_885_000 picoseconds. + Weight::from_parts(17_648_279, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 225 - .saturating_add(Weight::from_parts(115_324, 0).saturating_mul(n.into())) + // Standard Error: 260 + .saturating_add(Weight::from_parts(146_465, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -119,13 +119,13 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// The range of component `n` is `[0, 105457]`. fn enqueue_empty_xcmp_message_at(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `334 + n * (1 ±0)` + // Measured: `434 + n * (1 ±0)` // Estimated: `108986` - // Minimum execution time: 20_484_000 picoseconds. - Weight::from_parts(20_648_000, 0) + // Minimum execution time: 24_912_000 picoseconds. + Weight::from_parts(16_404_977, 0) .saturating_add(Weight::from_parts(0, 108986)) - // Standard Error: 11 - .saturating_add(Weight::from_parts(2_365, 0).saturating_mul(n.into())) + // Standard Error: 14 + .saturating_add(Weight::from_parts(2_304, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) } @@ -142,13 +142,13 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// The range of component `n` is `[0, 100]`. fn enqueue_n_full_pages(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `186` + // Measured: `286` // Estimated: `5487` - // Minimum execution time: 12_963_000 picoseconds. - Weight::from_parts(13_277_000, 0) + // Minimum execution time: 14_636_000 picoseconds. + Weight::from_parts(15_119_000, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 63_306 - .saturating_add(Weight::from_parts(104_765_134, 0).saturating_mul(n.into())) + // Standard Error: 78_913 + .saturating_add(Weight::from_parts(98_091_696, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) .saturating_add(T::DbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -163,10 +163,10 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// Proof: `XcmpQueue::InboundXcmpSuspended` (`max_values`: Some(1), `max_size`: Some(4002), added: 4497, mode: `MaxEncodedLen`) fn enqueue_1000_small_xcmp_messages() -> Weight { // Proof Size summary in bytes: - // Measured: `53067` + // Measured: `53167` // Estimated: `108986` - // Minimum execution time: 255_661_000 picoseconds. - Weight::from_parts(264_825_000, 0) + // Minimum execution time: 281_890_000 picoseconds. + Weight::from_parts(301_578_000, 0) .saturating_add(Weight::from_parts(0, 108986)) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) @@ -175,10 +175,10 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// Proof: `XcmpQueue::OutboundXcmpStatus` (`max_values`: Some(1), `max_size`: Some(1282), added: 1777, mode: `MaxEncodedLen`) fn suspend_channel() -> Weight { // Proof Size summary in bytes: - // Measured: `109` + // Measured: `175` // Estimated: `2767` - // Minimum execution time: 3_092_000 picoseconds. - Weight::from_parts(3_339_000, 0) + // Minimum execution time: 3_559_000 picoseconds. + Weight::from_parts(3_941_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -187,21 +187,24 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// Proof: `XcmpQueue::OutboundXcmpStatus` (`max_values`: Some(1), `max_size`: Some(1282), added: 1777, mode: `MaxEncodedLen`) fn resume_channel() -> Weight { // Proof Size summary in bytes: - // Measured: `144` + // Measured: `210` // Estimated: `2767` - // Minimum execution time: 4_352_000 picoseconds. - Weight::from_parts(4_577_000, 0) + // Minimum execution time: 4_747_000 picoseconds. + Weight::from_parts(5_000_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 5_050_000 picoseconds. - Weight::from_parts(5_270_000, 0) + // Minimum execution time: 1_983_000 picoseconds. + Weight::from_parts(2_340_802, 0) .saturating_add(Weight::from_parts(0, 0)) + // Standard Error: 95 + .saturating_add(Weight::from_parts(17_197, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -219,11 +222,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// Proof: `MessageQueue::Pages` (`max_values`: None, `max_size`: Some(105521), added: 107996, mode: `MaxEncodedLen`) fn on_idle_good_msg() -> Weight { // Proof Size summary in bytes: - // Measured: `105716` - // Estimated: `109181` - // Minimum execution time: 210_820_000 picoseconds. - Weight::from_parts(221_925_000, 0) - .saturating_add(Weight::from_parts(0, 109181)) + // Measured: `105816` + // Estimated: `109281` + // Minimum execution time: 191_606_000 picoseconds. + Weight::from_parts(204_871_000, 0) + .saturating_add(Weight::from_parts(0, 109281)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) } @@ -243,11 +246,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// Proof: `MessageQueue::Pages` (`max_values`: None, `max_size`: Some(105521), added: 107996, mode: `MaxEncodedLen`) fn on_idle_large_msg() -> Weight { // Proof Size summary in bytes: - // Measured: `65785` - // Estimated: `69250` - // Minimum execution time: 127_555_000 picoseconds. - Weight::from_parts(130_147_000, 0) - .saturating_add(Weight::from_parts(0, 69250)) + // Measured: `65885` + // Estimated: `69350` + // Minimum execution time: 127_183_000 picoseconds. + Weight::from_parts(133_929_000, 0) + .saturating_add(Weight::from_parts(0, 69350)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) } diff --git a/cumulus/parachains/runtimes/assets/asset-hub-westend/tests/tests.rs b/cumulus/parachains/runtimes/assets/asset-hub-westend/tests/tests.rs index 8f48a3171916e..3d65d3b168293 100644 --- a/cumulus/parachains/runtimes/assets/asset-hub-westend/tests/tests.rs +++ b/cumulus/parachains/runtimes/assets/asset-hub-westend/tests/tests.rs @@ -85,6 +85,16 @@ const ALICE: [u8; 32] = [1u8; 32]; const BOB: [u8; 32] = [2u8; 32]; const SOME_ASSET_ADMIN: [u8; 32] = [5u8; 32]; +const ERC20_PVM: &[u8] = + include_bytes!("../../../../../../substrate/frame/revive/fixtures/erc20/erc20.polkavm"); + +const FAKE_ERC20_PVM: &[u8] = + include_bytes!("../../../../../../substrate/frame/revive/fixtures/erc20/fake_erc20.polkavm"); + +const EXPENSIVE_ERC20_PVM: &[u8] = include_bytes!( + "../../../../../../substrate/frame/revive/fixtures/erc20/expensive_erc20.polkavm" +); + parameter_types! { pub Governance: GovernanceOrigin = GovernanceOrigin::Origin(RuntimeOrigin::root()); } @@ -1670,10 +1680,7 @@ fn withdraw_and_deposit_erc20s() { assert_ok!(Revive::map_account(RuntimeOrigin::signed(sender.clone()))); assert_ok!(Revive::map_account(RuntimeOrigin::signed(beneficiary.clone()))); - let code = include_bytes!( - "../../../../../../substrate/frame/revive/fixtures/contracts/erc20.polkavm" - ) - .to_vec(); + let code = ERC20_PVM.to_vec(); let initial_amount_u256 = U256::from(1_000_000_000_000u128); let constructor_data = sol_data::Uint::<256>::abi_encode(&initial_amount_u256); @@ -1832,10 +1839,7 @@ fn smart_contract_does_not_return_bool_fails() { assert_ok!(Revive::map_account(RuntimeOrigin::signed(beneficiary.clone()))); // This contract implements the ERC20 interface for `transfer` except it returns a uint256. - let code = include_bytes!( - "../../../../../../substrate/frame/revive/fixtures/contracts/fake_erc20.polkavm" - ) - .to_vec(); + let code = FAKE_ERC20_PVM.to_vec(); let initial_amount_u256 = U256::from(1_000_000_000_000u128); let constructor_data = sol_data::Uint::<256>::abi_encode(&initial_amount_u256); @@ -1888,10 +1892,7 @@ fn expensive_erc20_runs_out_of_gas() { assert_ok!(Revive::map_account(RuntimeOrigin::signed(beneficiary.clone()))); // This contract does a lot more storage writes in `transfer`. - let code = include_bytes!( - "../../../../../../substrate/frame/revive/fixtures/contracts/expensive_erc20.polkavm" - ) - .to_vec(); + let code = EXPENSIVE_ERC20_PVM.to_vec(); let initial_amount_u256 = U256::from(1_000_000_000_000u128); let constructor_data = sol_data::Uint::<256>::abi_encode(&initial_amount_u256); diff --git a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/Cargo.toml b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/Cargo.toml index c6bd870e78863..8f36b2e4875a7 100644 --- a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/Cargo.toml +++ b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/Cargo.toml @@ -243,6 +243,7 @@ runtime-benchmarks = [ "pallet-collator-selection/runtime-benchmarks", "pallet-message-queue/runtime-benchmarks", "pallet-multisig/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-transaction-payment/runtime-benchmarks", "pallet-utility/runtime-benchmarks", diff --git a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/src/lib.rs b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/src/lib.rs index 2d951af2d2cde..d91dd0adcdfb6 100644 --- a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/src/lib.rs +++ b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/src/lib.rs @@ -253,7 +253,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("bridge-hub-rococo"), impl_name: alloc::borrow::Cow::Borrowed("bridge-hub-rococo"), authoring_version: 1, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 6, diff --git a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/src/weights/cumulus_pallet_xcmp_queue.rs b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/src/weights/cumulus_pallet_xcmp_queue.rs index 40f13c7090b47..e96a8ab5a5b6b 100644 --- a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/src/weights/cumulus_pallet_xcmp_queue.rs +++ b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/src/weights/cumulus_pallet_xcmp_queue.rs @@ -16,9 +16,9 @@ //! Autogenerated weights for `cumulus_pallet_xcmp_queue` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-05-05, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `16d5a52ef0dc`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `b8d1375f7728`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -56,8 +56,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `4` // Estimated: `1497` - // Minimum execution time: 4_326_000 picoseconds. - Weight::from_parts(4_616_000, 0) + // Minimum execution time: 4_460_000 picoseconds. + Weight::from_parts(4_675_000, 0) .saturating_add(Weight::from_parts(0, 1497)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -77,11 +77,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `80` // Estimated: `5487` - // Minimum execution time: 13_374_000 picoseconds. - Weight::from_parts(9_220_505, 0) + // Minimum execution time: 14_234_000 picoseconds. + Weight::from_parts(9_599_674, 0) .saturating_add(Weight::from_parts(0, 5487)) // Standard Error: 6 - .saturating_add(Weight::from_parts(989, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(1_047, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -100,11 +100,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `80` // Estimated: `5487` - // Minimum execution time: 11_436_000 picoseconds. - Weight::from_parts(15_588_934, 0) + // Minimum execution time: 12_070_000 picoseconds. + Weight::from_parts(16_440_071, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 215 - .saturating_add(Weight::from_parts(121_183, 0).saturating_mul(n.into())) + // Standard Error: 266 + .saturating_add(Weight::from_parts(146_239, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -121,11 +121,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `263 + n * (1 ±0)` // Estimated: `109014` - // Minimum execution time: 21_929_000 picoseconds. - Weight::from_parts(1_150_129, 0) + // Minimum execution time: 23_688_000 picoseconds. + Weight::from_parts(14_746_605, 0) .saturating_add(Weight::from_parts(0, 109014)) - // Standard Error: 16 - .saturating_add(Weight::from_parts(2_654, 0).saturating_mul(n.into())) + // Standard Error: 12 + .saturating_add(Weight::from_parts(2_328, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) } @@ -144,11 +144,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `115` // Estimated: `5487` - // Minimum execution time: 12_994_000 picoseconds. - Weight::from_parts(13_450_000, 0) + // Minimum execution time: 13_401_000 picoseconds. + Weight::from_parts(13_651_000, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 59_142 - .saturating_add(Weight::from_parts(101_994_623, 0).saturating_mul(n.into())) + // Standard Error: 70_006 + .saturating_add(Weight::from_parts(97_625_139, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) .saturating_add(T::DbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -165,8 +165,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `52996` // Estimated: `109014` - // Minimum execution time: 266_450_000 picoseconds. - Weight::from_parts(274_887_000, 0) + // Minimum execution time: 288_846_000 picoseconds. + Weight::from_parts(297_120_000, 0) .saturating_add(Weight::from_parts(0, 109014)) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) @@ -177,8 +177,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `4` // Estimated: `2767` - // Minimum execution time: 2_388_000 picoseconds. - Weight::from_parts(2_520_000, 0) + // Minimum execution time: 2_567_000 picoseconds. + Weight::from_parts(2_706_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -189,19 +189,22 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `39` // Estimated: `2767` - // Minimum execution time: 3_782_000 picoseconds. - Weight::from_parts(3_940_000, 0) + // Minimum execution time: 3_781_000 picoseconds. + Weight::from_parts(3_998_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 5_418_000 picoseconds. - Weight::from_parts(5_613_000, 0) + // Minimum execution time: 2_079_000 picoseconds. + Weight::from_parts(2_410_204, 0) .saturating_add(Weight::from_parts(0, 0)) + // Standard Error: 97 + .saturating_add(Weight::from_parts(17_210, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -221,8 +224,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `105645` // Estimated: `109110` - // Minimum execution time: 210_814_000 picoseconds. - Weight::from_parts(217_016_000, 0) + // Minimum execution time: 192_718_000 picoseconds. + Weight::from_parts(203_462_000, 0) .saturating_add(Weight::from_parts(0, 109110)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) @@ -245,8 +248,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `65714` // Estimated: `69179` - // Minimum execution time: 126_881_000 picoseconds. - Weight::from_parts(131_302_000, 0) + // Minimum execution time: 125_934_000 picoseconds. + Weight::from_parts(129_980_000, 0) .saturating_add(Weight::from_parts(0, 69179)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) diff --git a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/Cargo.toml b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/Cargo.toml index 49c6861c99bec..bfc46ffe66cbb 100644 --- a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/Cargo.toml +++ b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/Cargo.toml @@ -252,6 +252,7 @@ runtime-benchmarks = [ "pallet-collator-selection/runtime-benchmarks", "pallet-message-queue/runtime-benchmarks", "pallet-multisig/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-transaction-payment/runtime-benchmarks", "pallet-utility/runtime-benchmarks", diff --git a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/src/lib.rs b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/src/lib.rs index 99742ceed289f..eaa58ac1b62ed 100644 --- a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/src/lib.rs +++ b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/src/lib.rs @@ -243,7 +243,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("bridge-hub-westend"), impl_name: alloc::borrow::Cow::Borrowed("bridge-hub-westend"), authoring_version: 1, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 6, diff --git a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/src/weights/cumulus_pallet_xcmp_queue.rs b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/src/weights/cumulus_pallet_xcmp_queue.rs index f8a44aa4779c9..87969cb8abfe3 100644 --- a/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/src/weights/cumulus_pallet_xcmp_queue.rs +++ b/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-westend/src/weights/cumulus_pallet_xcmp_queue.rs @@ -16,9 +16,9 @@ //! Autogenerated weights for `cumulus_pallet_xcmp_queue` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-05-05, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `16d5a52ef0dc`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `b8d1375f7728`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -56,8 +56,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `142` // Estimated: `1497` - // Minimum execution time: 5_195_000 picoseconds. - Weight::from_parts(5_568_000, 0) + // Minimum execution time: 5_022_000 picoseconds. + Weight::from_parts(5_424_000, 0) .saturating_add(Weight::from_parts(0, 1497)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -77,11 +77,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `148` // Estimated: `5487` - // Minimum execution time: 13_430_000 picoseconds. - Weight::from_parts(9_574_197, 0) + // Minimum execution time: 14_324_000 picoseconds. + Weight::from_parts(9_117_035, 0) .saturating_add(Weight::from_parts(0, 5487)) // Standard Error: 6 - .saturating_add(Weight::from_parts(973, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(1_053, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -100,11 +100,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `148` // Estimated: `5487` - // Minimum execution time: 11_564_000 picoseconds. - Weight::from_parts(15_506_334, 0) + // Minimum execution time: 11_747_000 picoseconds. + Weight::from_parts(16_504_385, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 205 - .saturating_add(Weight::from_parts(114_494, 0).saturating_mul(n.into())) + // Standard Error: 230 + .saturating_add(Weight::from_parts(147_286, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -121,11 +121,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `330 + n * (1 ±0)` // Estimated: `109014` - // Minimum execution time: 19_772_000 picoseconds. - Weight::from_parts(20_089_000, 0) + // Minimum execution time: 21_596_000 picoseconds. + Weight::from_parts(11_861_199, 0) .saturating_add(Weight::from_parts(0, 109014)) - // Standard Error: 11 - .saturating_add(Weight::from_parts(2_427, 0).saturating_mul(n.into())) + // Standard Error: 13 + .saturating_add(Weight::from_parts(2_291, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) } @@ -144,11 +144,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `183` // Estimated: `5487` - // Minimum execution time: 12_651_000 picoseconds. - Weight::from_parts(13_268_000, 0) + // Minimum execution time: 13_488_000 picoseconds. + Weight::from_parts(13_700_000, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 55_621 - .saturating_add(Weight::from_parts(102_763_421, 0).saturating_mul(n.into())) + // Standard Error: 89_638 + .saturating_add(Weight::from_parts(98_160_015, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) .saturating_add(T::DbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -165,8 +165,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `53063` // Estimated: `109014` - // Minimum execution time: 252_294_000 picoseconds. - Weight::from_parts(260_540_000, 0) + // Minimum execution time: 283_182_000 picoseconds. + Weight::from_parts(292_377_000, 0) .saturating_add(Weight::from_parts(0, 109014)) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) @@ -177,8 +177,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `142` // Estimated: `2767` - // Minimum execution time: 3_337_000 picoseconds. - Weight::from_parts(3_498_000, 0) + // Minimum execution time: 3_375_000 picoseconds. + Weight::from_parts(3_603_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -189,19 +189,22 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `177` // Estimated: `2767` - // Minimum execution time: 4_674_000 picoseconds. - Weight::from_parts(4_822_000, 0) + // Minimum execution time: 4_447_000 picoseconds. + Weight::from_parts(4_769_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 5_045_000 picoseconds. - Weight::from_parts(5_399_000, 0) + // Minimum execution time: 2_172_000 picoseconds. + Weight::from_parts(2_524_868, 0) .saturating_add(Weight::from_parts(0, 0)) + // Standard Error: 195 + .saturating_add(Weight::from_parts(17_700, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -221,8 +224,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `105713` // Estimated: `109178` - // Minimum execution time: 211_435_000 picoseconds. - Weight::from_parts(222_691_000, 0) + // Minimum execution time: 187_431_000 picoseconds. + Weight::from_parts(199_807_000, 0) .saturating_add(Weight::from_parts(0, 109178)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) @@ -245,8 +248,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `65782` // Estimated: `69247` - // Minimum execution time: 126_438_000 picoseconds. - Weight::from_parts(129_423_000, 0) + // Minimum execution time: 122_370_000 picoseconds. + Weight::from_parts(130_426_000, 0) .saturating_add(Weight::from_parts(0, 69247)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) diff --git a/cumulus/parachains/runtimes/collectives/collectives-westend/Cargo.toml b/cumulus/parachains/runtimes/collectives/collectives-westend/Cargo.toml index 1f2606e953f86..6afa0188191ba 100644 --- a/cumulus/parachains/runtimes/collectives/collectives-westend/Cargo.toml +++ b/cumulus/parachains/runtimes/collectives/collectives-westend/Cargo.toml @@ -127,6 +127,7 @@ runtime-benchmarks = [ "pallet-referenda/runtime-benchmarks", "pallet-salary/runtime-benchmarks", "pallet-scheduler/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-state-trie-migration/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-transaction-payment/runtime-benchmarks", diff --git a/cumulus/parachains/runtimes/collectives/collectives-westend/src/lib.rs b/cumulus/parachains/runtimes/collectives/collectives-westend/src/lib.rs index 97198c0a226eb..cd89e9151c635 100644 --- a/cumulus/parachains/runtimes/collectives/collectives-westend/src/lib.rs +++ b/cumulus/parachains/runtimes/collectives/collectives-westend/src/lib.rs @@ -129,7 +129,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("collectives-westend"), impl_name: alloc::borrow::Cow::Borrowed("collectives-westend"), authoring_version: 1, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 6, diff --git a/cumulus/parachains/runtimes/collectives/collectives-westend/src/weights/cumulus_pallet_xcmp_queue.rs b/cumulus/parachains/runtimes/collectives/collectives-westend/src/weights/cumulus_pallet_xcmp_queue.rs index bed529edcea33..332320b527657 100644 --- a/cumulus/parachains/runtimes/collectives/collectives-westend/src/weights/cumulus_pallet_xcmp_queue.rs +++ b/cumulus/parachains/runtimes/collectives/collectives-westend/src/weights/cumulus_pallet_xcmp_queue.rs @@ -16,9 +16,9 @@ //! Autogenerated weights for `cumulus_pallet_xcmp_queue` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-05-05, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `16d5a52ef0dc`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `b8d1375f7728`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -56,8 +56,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `142` // Estimated: `1497` - // Minimum execution time: 4_975_000 picoseconds. - Weight::from_parts(5_353_000, 0) + // Minimum execution time: 5_163_000 picoseconds. + Weight::from_parts(5_403_000, 0) .saturating_add(Weight::from_parts(0, 1497)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -75,13 +75,13 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// The range of component `n` is `[0, 105467]`. fn enqueue_n_bytes_xcmp_message(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `148` + // Measured: `184` // Estimated: `5487` - // Minimum execution time: 13_084_000 picoseconds. - Weight::from_parts(8_989_453, 0) + // Minimum execution time: 14_411_000 picoseconds. + Weight::from_parts(9_821_468, 0) .saturating_add(Weight::from_parts(0, 5487)) // Standard Error: 6 - .saturating_add(Weight::from_parts(1_026, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(965, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -98,13 +98,13 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// The range of component `n` is `[0, 1000]`. fn enqueue_n_empty_xcmp_messages(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `148` + // Measured: `184` // Estimated: `5487` - // Minimum execution time: 10_913_000 picoseconds. - Weight::from_parts(14_988_541, 0) + // Minimum execution time: 12_086_000 picoseconds. + Weight::from_parts(17_308_897, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 235 - .saturating_add(Weight::from_parts(130_851, 0).saturating_mul(n.into())) + // Standard Error: 271 + .saturating_add(Weight::from_parts(144_787, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -119,13 +119,13 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// The range of component `n` is `[0, 105457]`. fn enqueue_empty_xcmp_message_at(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `330 + n * (1 ±0)` + // Measured: `367 + n * (1 ±0)` // Estimated: `108986` - // Minimum execution time: 19_799_000 picoseconds. - Weight::from_parts(20_095_000, 0) + // Minimum execution time: 21_448_000 picoseconds. + Weight::from_parts(12_714_843, 0) .saturating_add(Weight::from_parts(0, 108986)) - // Standard Error: 12 - .saturating_add(Weight::from_parts(2_584, 0).saturating_mul(n.into())) + // Standard Error: 11 + .saturating_add(Weight::from_parts(2_056, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) } @@ -142,13 +142,13 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// The range of component `n` is `[0, 100]`. fn enqueue_n_full_pages(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `183` + // Measured: `219` // Estimated: `5487` - // Minimum execution time: 12_421_000 picoseconds. - Weight::from_parts(12_780_000, 0) + // Minimum execution time: 13_650_000 picoseconds. + Weight::from_parts(13_915_000, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 84_412 - .saturating_add(Weight::from_parts(106_740_006, 0).saturating_mul(n.into())) + // Standard Error: 68_118 + .saturating_add(Weight::from_parts(90_488_147, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) .saturating_add(T::DbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -163,10 +163,10 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// Proof: `XcmpQueue::InboundXcmpSuspended` (`max_values`: Some(1), `max_size`: Some(4002), added: 4497, mode: `MaxEncodedLen`) fn enqueue_1000_small_xcmp_messages() -> Weight { // Proof Size summary in bytes: - // Measured: `53063` + // Measured: `53100` // Estimated: `108986` - // Minimum execution time: 279_435_000 picoseconds. - Weight::from_parts(285_825_000, 0) + // Minimum execution time: 268_288_000 picoseconds. + Weight::from_parts(273_155_000, 0) .saturating_add(Weight::from_parts(0, 108986)) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) @@ -177,8 +177,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `142` // Estimated: `2767` - // Minimum execution time: 3_187_000 picoseconds. - Weight::from_parts(3_390_000, 0) + // Minimum execution time: 3_196_000 picoseconds. + Weight::from_parts(3_456_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -189,19 +189,22 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `177` // Estimated: `2767` - // Minimum execution time: 4_450_000 picoseconds. - Weight::from_parts(4_688_000, 0) + // Minimum execution time: 4_468_000 picoseconds. + Weight::from_parts(4_880_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 5_199_000 picoseconds. - Weight::from_parts(5_368_000, 0) + // Minimum execution time: 2_003_000 picoseconds. + Weight::from_parts(2_438_969, 0) .saturating_add(Weight::from_parts(0, 0)) + // Standard Error: 175 + .saturating_add(Weight::from_parts(17_883, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -219,11 +222,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// Proof: `MessageQueue::Pages` (`max_values`: None, `max_size`: Some(105521), added: 107996, mode: `MaxEncodedLen`) fn on_idle_good_msg() -> Weight { // Proof Size summary in bytes: - // Measured: `105713` - // Estimated: `109178` - // Minimum execution time: 229_715_000 picoseconds. - Weight::from_parts(232_586_000, 0) - .saturating_add(Weight::from_parts(0, 109178)) + // Measured: `105749` + // Estimated: `109214` + // Minimum execution time: 177_632_000 picoseconds. + Weight::from_parts(186_057_000, 0) + .saturating_add(Weight::from_parts(0, 109214)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) } @@ -243,11 +246,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn /// Proof: `MessageQueue::Pages` (`max_values`: None, `max_size`: Some(105521), added: 107996, mode: `MaxEncodedLen`) fn on_idle_large_msg() -> Weight { // Proof Size summary in bytes: - // Measured: `65782` - // Estimated: `69247` - // Minimum execution time: 133_351_000 picoseconds. - Weight::from_parts(135_787_000, 0) - .saturating_add(Weight::from_parts(0, 69247)) + // Measured: `65818` + // Estimated: `69283` + // Minimum execution time: 116_557_000 picoseconds. + Weight::from_parts(120_206_000, 0) + .saturating_add(Weight::from_parts(0, 69283)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) } diff --git a/cumulus/parachains/runtimes/coretime/coretime-rococo/Cargo.toml b/cumulus/parachains/runtimes/coretime/coretime-rococo/Cargo.toml index 6d9de54ca9685..6320dd8ef4400 100644 --- a/cumulus/parachains/runtimes/coretime/coretime-rococo/Cargo.toml +++ b/cumulus/parachains/runtimes/coretime/coretime-rococo/Cargo.toml @@ -170,6 +170,7 @@ runtime-benchmarks = [ "pallet-message-queue/runtime-benchmarks", "pallet-multisig/runtime-benchmarks", "pallet-proxy/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-sudo/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-transaction-payment/runtime-benchmarks", diff --git a/cumulus/parachains/runtimes/coretime/coretime-rococo/src/lib.rs b/cumulus/parachains/runtimes/coretime/coretime-rococo/src/lib.rs index 69ce1e0d5aeda..dfefc339e6a76 100644 --- a/cumulus/parachains/runtimes/coretime/coretime-rococo/src/lib.rs +++ b/cumulus/parachains/runtimes/coretime/coretime-rococo/src/lib.rs @@ -159,7 +159,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("coretime-rococo"), impl_name: alloc::borrow::Cow::Borrowed("coretime-rococo"), authoring_version: 1, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 2, diff --git a/cumulus/parachains/runtimes/coretime/coretime-rococo/src/weights/cumulus_pallet_xcmp_queue.rs b/cumulus/parachains/runtimes/coretime/coretime-rococo/src/weights/cumulus_pallet_xcmp_queue.rs index 5051a8c8e96b2..bccbf7df370eb 100644 --- a/cumulus/parachains/runtimes/coretime/coretime-rococo/src/weights/cumulus_pallet_xcmp_queue.rs +++ b/cumulus/parachains/runtimes/coretime/coretime-rococo/src/weights/cumulus_pallet_xcmp_queue.rs @@ -16,9 +16,9 @@ //! Autogenerated weights for `cumulus_pallet_xcmp_queue` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-05-05, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `16d5a52ef0dc`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `b8d1375f7728`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -56,8 +56,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `76` // Estimated: `1497` - // Minimum execution time: 4_788_000 picoseconds. - Weight::from_parts(5_033_000, 0) + // Minimum execution time: 5_033_000 picoseconds. + Weight::from_parts(5_335_000, 0) .saturating_add(Weight::from_parts(0, 1497)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -77,11 +77,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `82` // Estimated: `5487` - // Minimum execution time: 12_649_000 picoseconds. - Weight::from_parts(8_733_180, 0) + // Minimum execution time: 13_695_000 picoseconds. + Weight::from_parts(9_707_464, 0) .saturating_add(Weight::from_parts(0, 5487)) // Standard Error: 6 - .saturating_add(Weight::from_parts(982, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(946, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -100,11 +100,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `82` // Estimated: `5487` - // Minimum execution time: 10_604_000 picoseconds. - Weight::from_parts(14_570_286, 0) + // Minimum execution time: 11_606_000 picoseconds. + Weight::from_parts(15_497_649, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 193 - .saturating_add(Weight::from_parts(117_011, 0).saturating_mul(n.into())) + // Standard Error: 383 + .saturating_add(Weight::from_parts(144_897, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -121,11 +121,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `264 + n * (1 ±0)` // Estimated: `108986` - // Minimum execution time: 19_467_000 picoseconds. - Weight::from_parts(19_689_000, 0) + // Minimum execution time: 20_569_000 picoseconds. + Weight::from_parts(12_353_232, 0) .saturating_add(Weight::from_parts(0, 108986)) // Standard Error: 11 - .saturating_add(Weight::from_parts(2_365, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(2_033, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) } @@ -144,11 +144,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `117` // Estimated: `5487` - // Minimum execution time: 12_234_000 picoseconds. - Weight::from_parts(12_623_000, 0) + // Minimum execution time: 13_109_000 picoseconds. + Weight::from_parts(13_377_000, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 62_233 - .saturating_add(Weight::from_parts(102_929_572, 0).saturating_mul(n.into())) + // Standard Error: 87_993 + .saturating_add(Weight::from_parts(91_358_719, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) .saturating_add(T::DbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -165,8 +165,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `52997` // Estimated: `108986` - // Minimum execution time: 254_750_000 picoseconds. - Weight::from_parts(262_602_000, 0) + // Minimum execution time: 264_958_000 picoseconds. + Weight::from_parts(270_387_000, 0) .saturating_add(Weight::from_parts(0, 108986)) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) @@ -177,8 +177,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `76` // Estimated: `2767` - // Minimum execution time: 2_920_000 picoseconds. - Weight::from_parts(3_228_000, 0) + // Minimum execution time: 3_267_000 picoseconds. + Weight::from_parts(3_446_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -189,19 +189,22 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `111` // Estimated: `2767` - // Minimum execution time: 4_301_000 picoseconds. - Weight::from_parts(4_501_000, 0) + // Minimum execution time: 4_396_000 picoseconds. + Weight::from_parts(4_516_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 5_274_000 picoseconds. - Weight::from_parts(5_575_000, 0) + // Minimum execution time: 2_001_000 picoseconds. + Weight::from_parts(2_478_301, 0) .saturating_add(Weight::from_parts(0, 0)) + // Standard Error: 143 + .saturating_add(Weight::from_parts(17_452, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -221,8 +224,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `105647` // Estimated: `109112` - // Minimum execution time: 212_251_000 picoseconds. - Weight::from_parts(220_677_000, 0) + // Minimum execution time: 174_001_000 picoseconds. + Weight::from_parts(178_058_000, 0) .saturating_add(Weight::from_parts(0, 109112)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) @@ -245,8 +248,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `65716` // Estimated: `69181` - // Minimum execution time: 125_236_000 picoseconds. - Weight::from_parts(127_502_000, 0) + // Minimum execution time: 116_008_000 picoseconds. + Weight::from_parts(118_667_000, 0) .saturating_add(Weight::from_parts(0, 69181)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) diff --git a/cumulus/parachains/runtimes/coretime/coretime-westend/Cargo.toml b/cumulus/parachains/runtimes/coretime/coretime-westend/Cargo.toml index 4e366d0eacd0f..a40bebb5747c0 100644 --- a/cumulus/parachains/runtimes/coretime/coretime-westend/Cargo.toml +++ b/cumulus/parachains/runtimes/coretime/coretime-westend/Cargo.toml @@ -170,6 +170,7 @@ runtime-benchmarks = [ "pallet-message-queue/runtime-benchmarks", "pallet-multisig/runtime-benchmarks", "pallet-proxy/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-sudo/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-transaction-payment/runtime-benchmarks", diff --git a/cumulus/parachains/runtimes/coretime/coretime-westend/src/lib.rs b/cumulus/parachains/runtimes/coretime/coretime-westend/src/lib.rs index 15adbad1cd740..0a60b6660e46b 100644 --- a/cumulus/parachains/runtimes/coretime/coretime-westend/src/lib.rs +++ b/cumulus/parachains/runtimes/coretime/coretime-westend/src/lib.rs @@ -159,7 +159,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("coretime-westend"), impl_name: alloc::borrow::Cow::Borrowed("coretime-westend"), authoring_version: 1, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 2, diff --git a/cumulus/parachains/runtimes/coretime/coretime-westend/src/weights/cumulus_pallet_xcmp_queue.rs b/cumulus/parachains/runtimes/coretime/coretime-westend/src/weights/cumulus_pallet_xcmp_queue.rs index 7aa9c8a0896c2..dbb67783fdebf 100644 --- a/cumulus/parachains/runtimes/coretime/coretime-westend/src/weights/cumulus_pallet_xcmp_queue.rs +++ b/cumulus/parachains/runtimes/coretime/coretime-westend/src/weights/cumulus_pallet_xcmp_queue.rs @@ -16,9 +16,9 @@ //! Autogenerated weights for `cumulus_pallet_xcmp_queue` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-05-05, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `16d5a52ef0dc`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `b8d1375f7728`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -56,8 +56,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `76` // Estimated: `1497` - // Minimum execution time: 4_864_000 picoseconds. - Weight::from_parts(5_179_000, 0) + // Minimum execution time: 4_928_000 picoseconds. + Weight::from_parts(5_358_000, 0) .saturating_add(Weight::from_parts(0, 1497)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -77,11 +77,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `82` // Estimated: `5487` - // Minimum execution time: 12_962_000 picoseconds. - Weight::from_parts(8_522_179, 0) + // Minimum execution time: 14_370_000 picoseconds. + Weight::from_parts(9_971_021, 0) .saturating_add(Weight::from_parts(0, 5487)) // Standard Error: 6 - .saturating_add(Weight::from_parts(1_028, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(941, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -100,11 +100,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `82` // Estimated: `5487` - // Minimum execution time: 10_903_000 picoseconds. - Weight::from_parts(14_761_815, 0) + // Minimum execution time: 11_949_000 picoseconds. + Weight::from_parts(16_605_001, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 200 - .saturating_add(Weight::from_parts(117_611, 0).saturating_mul(n.into())) + // Standard Error: 316 + .saturating_add(Weight::from_parts(146_307, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -121,11 +121,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `264 + n * (1 ±0)` // Estimated: `108986` - // Minimum execution time: 19_215_000 picoseconds. - Weight::from_parts(19_684_000, 0) + // Minimum execution time: 21_297_000 picoseconds. + Weight::from_parts(13_185_882, 0) .saturating_add(Weight::from_parts(0, 108986)) // Standard Error: 12 - .saturating_add(Weight::from_parts(2_568, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(2_037, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) } @@ -144,11 +144,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `117` // Estimated: `5487` - // Minimum execution time: 12_217_000 picoseconds. - Weight::from_parts(12_477_000, 0) + // Minimum execution time: 13_210_000 picoseconds. + Weight::from_parts(13_504_000, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 55_582 - .saturating_add(Weight::from_parts(106_437_894, 0).saturating_mul(n.into())) + // Standard Error: 64_713 + .saturating_add(Weight::from_parts(90_594_857, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) .saturating_add(T::DbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -165,8 +165,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `52997` // Estimated: `108986` - // Minimum execution time: 264_971_000 picoseconds. - Weight::from_parts(275_172_000, 0) + // Minimum execution time: 269_027_000 picoseconds. + Weight::from_parts(285_137_000, 0) .saturating_add(Weight::from_parts(0, 108986)) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) @@ -177,8 +177,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `76` // Estimated: `2767` - // Minimum execution time: 2_996_000 picoseconds. - Weight::from_parts(3_216_000, 0) + // Minimum execution time: 3_058_000 picoseconds. + Weight::from_parts(3_349_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -189,19 +189,22 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `111` // Estimated: `2767` - // Minimum execution time: 4_320_000 picoseconds. - Weight::from_parts(4_499_000, 0) + // Minimum execution time: 4_268_000 picoseconds. + Weight::from_parts(4_503_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 5_044_000 picoseconds. - Weight::from_parts(5_145_000, 0) + // Minimum execution time: 2_005_000 picoseconds. + Weight::from_parts(2_414_620, 0) .saturating_add(Weight::from_parts(0, 0)) + // Standard Error: 257 + .saturating_add(Weight::from_parts(19_194, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -221,8 +224,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `105647` // Estimated: `109112` - // Minimum execution time: 223_930_000 picoseconds. - Weight::from_parts(234_241_000, 0) + // Minimum execution time: 177_174_000 picoseconds. + Weight::from_parts(181_060_000, 0) .saturating_add(Weight::from_parts(0, 109112)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) @@ -245,8 +248,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `65716` // Estimated: `69181` - // Minimum execution time: 132_117_000 picoseconds. - Weight::from_parts(134_663_000, 0) + // Minimum execution time: 116_529_000 picoseconds. + Weight::from_parts(118_305_000, 0) .saturating_add(Weight::from_parts(0, 69181)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) diff --git a/cumulus/parachains/runtimes/glutton/glutton-westend/src/lib.rs b/cumulus/parachains/runtimes/glutton/glutton-westend/src/lib.rs index 3bfd427febb57..617d8f1174a7a 100644 --- a/cumulus/parachains/runtimes/glutton/glutton-westend/src/lib.rs +++ b/cumulus/parachains/runtimes/glutton/glutton-westend/src/lib.rs @@ -103,7 +103,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("glutton-westend"), impl_name: alloc::borrow::Cow::Borrowed("glutton-westend"), authoring_version: 1, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 1, diff --git a/cumulus/parachains/runtimes/people/people-rococo/Cargo.toml b/cumulus/parachains/runtimes/people/people-rococo/Cargo.toml index d451018532c89..ade7dee71673c 100644 --- a/cumulus/parachains/runtimes/people/people-rococo/Cargo.toml +++ b/cumulus/parachains/runtimes/people/people-rococo/Cargo.toml @@ -170,6 +170,7 @@ runtime-benchmarks = [ "pallet-migrations/runtime-benchmarks", "pallet-multisig/runtime-benchmarks", "pallet-proxy/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-transaction-payment/runtime-benchmarks", "pallet-utility/runtime-benchmarks", diff --git a/cumulus/parachains/runtimes/people/people-rococo/src/lib.rs b/cumulus/parachains/runtimes/people/people-rococo/src/lib.rs index 259706b52cf2f..9e20bf64f91cf 100644 --- a/cumulus/parachains/runtimes/people/people-rococo/src/lib.rs +++ b/cumulus/parachains/runtimes/people/people-rococo/src/lib.rs @@ -146,7 +146,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("people-rococo"), impl_name: alloc::borrow::Cow::Borrowed("people-rococo"), authoring_version: 1, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 1, diff --git a/cumulus/parachains/runtimes/people/people-rococo/src/weights/cumulus_pallet_xcmp_queue.rs b/cumulus/parachains/runtimes/people/people-rococo/src/weights/cumulus_pallet_xcmp_queue.rs index 32ae0f05dadba..ceab118a036d6 100644 --- a/cumulus/parachains/runtimes/people/people-rococo/src/weights/cumulus_pallet_xcmp_queue.rs +++ b/cumulus/parachains/runtimes/people/people-rococo/src/weights/cumulus_pallet_xcmp_queue.rs @@ -16,9 +16,9 @@ //! Autogenerated weights for `cumulus_pallet_xcmp_queue` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-05-05, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `16d5a52ef0dc`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `b8d1375f7728`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -56,8 +56,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `76` // Estimated: `1497` - // Minimum execution time: 4_894_000 picoseconds. - Weight::from_parts(5_140_000, 0) + // Minimum execution time: 5_057_000 picoseconds. + Weight::from_parts(5_254_000, 0) .saturating_add(Weight::from_parts(0, 1497)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -77,11 +77,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `82` // Estimated: `5487` - // Minimum execution time: 13_062_000 picoseconds. - Weight::from_parts(8_854_073, 0) + // Minimum execution time: 13_643_000 picoseconds. + Weight::from_parts(9_652_139, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 6 - .saturating_add(Weight::from_parts(985, 0).saturating_mul(n.into())) + // Standard Error: 7 + .saturating_add(Weight::from_parts(1_039, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -100,11 +100,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `82` // Estimated: `5487` - // Minimum execution time: 10_915_000 picoseconds. - Weight::from_parts(14_766_724, 0) + // Minimum execution time: 11_614_000 picoseconds. + Weight::from_parts(15_847_295, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 228 - .saturating_add(Weight::from_parts(117_905, 0).saturating_mul(n.into())) + // Standard Error: 243 + .saturating_add(Weight::from_parts(145_536, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -121,11 +121,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `264 + n * (1 ±0)` // Estimated: `108986` - // Minimum execution time: 19_506_000 picoseconds. - Weight::from_parts(19_645_000, 0) + // Minimum execution time: 20_891_000 picoseconds. + Weight::from_parts(12_137_030, 0) .saturating_add(Weight::from_parts(0, 108986)) // Standard Error: 12 - .saturating_add(Weight::from_parts(2_407, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(2_290, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) } @@ -144,11 +144,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `117` // Estimated: `5487` - // Minimum execution time: 12_218_000 picoseconds. - Weight::from_parts(12_586_000, 0) + // Minimum execution time: 13_104_000 picoseconds. + Weight::from_parts(13_302_000, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 105_927 - .saturating_add(Weight::from_parts(101_388_985, 0).saturating_mul(n.into())) + // Standard Error: 76_089 + .saturating_add(Weight::from_parts(98_243_339, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) .saturating_add(T::DbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -165,8 +165,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `52997` // Estimated: `108986` - // Minimum execution time: 253_077_000 picoseconds. - Weight::from_parts(257_994_000, 0) + // Minimum execution time: 280_014_000 picoseconds. + Weight::from_parts(291_117_000, 0) .saturating_add(Weight::from_parts(0, 108986)) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) @@ -177,8 +177,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `76` // Estimated: `2767` - // Minimum execution time: 3_102_000 picoseconds. - Weight::from_parts(3_289_000, 0) + // Minimum execution time: 3_280_000 picoseconds. + Weight::from_parts(3_455_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -189,19 +189,22 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `111` // Estimated: `2767` - // Minimum execution time: 4_386_000 picoseconds. - Weight::from_parts(4_658_000, 0) + // Minimum execution time: 4_477_000 picoseconds. + Weight::from_parts(4_728_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 5_154_000 picoseconds. - Weight::from_parts(5_368_000, 0) + // Minimum execution time: 2_028_000 picoseconds. + Weight::from_parts(2_386_598, 0) .saturating_add(Weight::from_parts(0, 0)) + // Standard Error: 125 + .saturating_add(Weight::from_parts(18_383, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -221,8 +224,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `105647` // Estimated: `109112` - // Minimum execution time: 209_858_000 picoseconds. - Weight::from_parts(220_504_000, 0) + // Minimum execution time: 183_291_000 picoseconds. + Weight::from_parts(195_539_000, 0) .saturating_add(Weight::from_parts(0, 109112)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) @@ -245,8 +248,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `65716` // Estimated: `69181` - // Minimum execution time: 127_163_000 picoseconds. - Weight::from_parts(132_512_000, 0) + // Minimum execution time: 121_905_000 picoseconds. + Weight::from_parts(129_494_000, 0) .saturating_add(Weight::from_parts(0, 69181)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) diff --git a/cumulus/parachains/runtimes/people/people-westend/Cargo.toml b/cumulus/parachains/runtimes/people/people-westend/Cargo.toml index 9e0dd19a9aa3a..5dc76682c9092 100644 --- a/cumulus/parachains/runtimes/people/people-westend/Cargo.toml +++ b/cumulus/parachains/runtimes/people/people-westend/Cargo.toml @@ -172,6 +172,7 @@ runtime-benchmarks = [ "pallet-migrations/runtime-benchmarks", "pallet-multisig/runtime-benchmarks", "pallet-proxy/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-transaction-payment/runtime-benchmarks", "pallet-utility/runtime-benchmarks", diff --git a/cumulus/parachains/runtimes/people/people-westend/src/lib.rs b/cumulus/parachains/runtimes/people/people-westend/src/lib.rs index b0430eff34259..cbdca464f860b 100644 --- a/cumulus/parachains/runtimes/people/people-westend/src/lib.rs +++ b/cumulus/parachains/runtimes/people/people-westend/src/lib.rs @@ -149,7 +149,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("people-westend"), impl_name: alloc::borrow::Cow::Borrowed("people-westend"), authoring_version: 1, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 2, diff --git a/cumulus/parachains/runtimes/people/people-westend/src/weights/cumulus_pallet_xcmp_queue.rs b/cumulus/parachains/runtimes/people/people-westend/src/weights/cumulus_pallet_xcmp_queue.rs index 7159ed0809bd9..1aeff1e6f5ed1 100644 --- a/cumulus/parachains/runtimes/people/people-westend/src/weights/cumulus_pallet_xcmp_queue.rs +++ b/cumulus/parachains/runtimes/people/people-westend/src/weights/cumulus_pallet_xcmp_queue.rs @@ -16,9 +16,9 @@ //! Autogenerated weights for `cumulus_pallet_xcmp_queue` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-05-05, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `16d5a52ef0dc`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `b8d1375f7728`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -56,8 +56,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `76` // Estimated: `1497` - // Minimum execution time: 4_910_000 picoseconds. - Weight::from_parts(5_170_000, 0) + // Minimum execution time: 5_237_000 picoseconds. + Weight::from_parts(5_369_000, 0) .saturating_add(Weight::from_parts(0, 1497)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -77,11 +77,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `82` // Estimated: `5487` - // Minimum execution time: 12_705_000 picoseconds. - Weight::from_parts(8_172_546, 0) + // Minimum execution time: 13_997_000 picoseconds. + Weight::from_parts(10_370_954, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 6 - .saturating_add(Weight::from_parts(1_028, 0).saturating_mul(n.into())) + // Standard Error: 7 + .saturating_add(Weight::from_parts(1_001, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -100,11 +100,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `82` // Estimated: `5487` - // Minimum execution time: 10_949_000 picoseconds. - Weight::from_parts(14_462_029, 0) + // Minimum execution time: 11_600_000 picoseconds. + Weight::from_parts(16_515_274, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 201 - .saturating_add(Weight::from_parts(119_824, 0).saturating_mul(n.into())) + // Standard Error: 246 + .saturating_add(Weight::from_parts(145_121, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(3)) } @@ -121,11 +121,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `264 + n * (1 ±0)` // Estimated: `108986` - // Minimum execution time: 19_543_000 picoseconds. - Weight::from_parts(19_802_000, 0) + // Minimum execution time: 20_767_000 picoseconds. + Weight::from_parts(11_519_699, 0) .saturating_add(Weight::from_parts(0, 108986)) // Standard Error: 12 - .saturating_add(Weight::from_parts(2_565, 0).saturating_mul(n.into())) + .saturating_add(Weight::from_parts(2_307, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) } @@ -144,11 +144,11 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `117` // Estimated: `5487` - // Minimum execution time: 12_500_000 picoseconds. - Weight::from_parts(12_672_000, 0) + // Minimum execution time: 13_110_000 picoseconds. + Weight::from_parts(13_275_000, 0) .saturating_add(Weight::from_parts(0, 5487)) - // Standard Error: 221_916 - .saturating_add(Weight::from_parts(106_306_015, 0).saturating_mul(n.into())) + // Standard Error: 65_885 + .saturating_add(Weight::from_parts(97_483_896, 0).saturating_mul(n.into())) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) .saturating_add(T::DbWeight::get().writes((1_u64).saturating_mul(n.into()))) @@ -165,8 +165,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `52997` // Estimated: `108986` - // Minimum execution time: 266_767_000 picoseconds. - Weight::from_parts(275_163_000, 0) + // Minimum execution time: 278_359_000 picoseconds. + Weight::from_parts(286_253_000, 0) .saturating_add(Weight::from_parts(0, 108986)) .saturating_add(T::DbWeight::get().reads(4)) .saturating_add(T::DbWeight::get().writes(2)) @@ -177,8 +177,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `76` // Estimated: `2767` - // Minimum execution time: 2_950_000 picoseconds. - Weight::from_parts(3_180_000, 0) + // Minimum execution time: 3_289_000 picoseconds. + Weight::from_parts(3_396_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) @@ -189,19 +189,22 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `111` // Estimated: `2767` - // Minimum execution time: 4_530_000 picoseconds. - Weight::from_parts(4_798_000, 0) + // Minimum execution time: 4_435_000 picoseconds. + Weight::from_parts(4_724_000, 0) .saturating_add(Weight::from_parts(0, 2767)) .saturating_add(T::DbWeight::get().reads(1)) .saturating_add(T::DbWeight::get().writes(1)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 5_231_000 picoseconds. - Weight::from_parts(5_399_000, 0) + // Minimum execution time: 2_039_000 picoseconds. + Weight::from_parts(2_426_754, 0) .saturating_add(Weight::from_parts(0, 0)) + // Standard Error: 153 + .saturating_add(Weight::from_parts(17_160, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) @@ -221,8 +224,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `105647` // Estimated: `109112` - // Minimum execution time: 227_766_000 picoseconds. - Weight::from_parts(236_600_000, 0) + // Minimum execution time: 187_032_000 picoseconds. + Weight::from_parts(203_070_000, 0) .saturating_add(Weight::from_parts(0, 109112)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) @@ -245,8 +248,8 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn // Proof Size summary in bytes: // Measured: `65716` // Estimated: `69181` - // Minimum execution time: 132_541_000 picoseconds. - Weight::from_parts(135_781_000, 0) + // Minimum execution time: 121_653_000 picoseconds. + Weight::from_parts(131_943_000, 0) .saturating_add(Weight::from_parts(0, 69181)) .saturating_add(T::DbWeight::get().reads(6)) .saturating_add(T::DbWeight::get().writes(5)) diff --git a/cumulus/parachains/runtimes/testing/penpal/Cargo.toml b/cumulus/parachains/runtimes/testing/penpal/Cargo.toml index 44b27445414cb..7d76b9c5a81e0 100644 --- a/cumulus/parachains/runtimes/testing/penpal/Cargo.toml +++ b/cumulus/parachains/runtimes/testing/penpal/Cargo.toml @@ -177,6 +177,7 @@ runtime-benchmarks = [ "pallet-collator-selection/runtime-benchmarks", "pallet-message-queue/runtime-benchmarks", "pallet-revive/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-sudo/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-transaction-payment/runtime-benchmarks", diff --git a/cumulus/polkadot-omni-node/README.md b/cumulus/polkadot-omni-node/README.md index 0d3fdaaf4c2fe..9031ec375dee3 100644 --- a/cumulus/polkadot-omni-node/README.md +++ b/cumulus/polkadot-omni-node/README.md @@ -46,11 +46,11 @@ local variants are available only for a build of `polkadot-omni-node` with `westend-native` and `rococo-native` features respectively. - -Additionaly, although deprecated, the `--para-id` flag can still be used to set the JSON key named -`para_id`. The removal of the flag will happen starting with `stable2512`. The alternative of not using -it is to implement the `cumulus_primitives_core::GetParachainInfo` runtime API for the runtime, and -upgrade it on-chain as well, to be compatible with nodes released starting with `stable2512`. +Additionaly, the `--para-id` flag can be used to set the JSON key named `para_id`. This flag is used +by nodes to determine the parachain id, and it is especially useful when the parachain id can not be +fetched from the runtime, when the state points to a runtime that does not implement the +`cumulus_primitives_core::GetParachainInfo` runtime API. It is recommended for runtimes to implement +the runtime API and be upgraded on chain. Example command bellow: diff --git a/cumulus/polkadot-omni-node/lib/src/cli.rs b/cumulus/polkadot-omni-node/lib/src/cli.rs index 5f9f949ce7268..af9f6c00dd7d8 100644 --- a/cumulus/polkadot-omni-node/lib/src/cli.rs +++ b/cumulus/polkadot-omni-node/lib/src/cli.rs @@ -316,7 +316,7 @@ impl RelayChainCli { let base = FromArgMatches::from_arg_matches(&matches).unwrap_or_else(|e| e.exit()); let extension = Extensions::try_get(&*para_config.chain_spec); - let chain_id = extension.map(|e| e.relay_chain.clone()); + let chain_id = extension.map(|e| e.relay_chain()); let base_path = para_config.base_path.path().join("polkadot"); Self { base, chain_id, base_path: Some(base_path), _phantom: Default::default() } diff --git a/cumulus/polkadot-omni-node/lib/src/common/chain_spec.rs b/cumulus/polkadot-omni-node/lib/src/common/chain_spec.rs index 7107045c0f407..2a55d75785238 100644 --- a/cumulus/polkadot-omni-node/lib/src/common/chain_spec.rs +++ b/cumulus/polkadot-omni-node/lib/src/common/chain_spec.rs @@ -32,59 +32,52 @@ pub struct DiskChainSpecLoader; impl LoadSpec for DiskChainSpecLoader { fn load_spec(&self, path: &str) -> Result, String> { - Ok(Box::new(DeprecatedGenericChainSpec::from_json_file(path.into())?)) - } -} - -/// Generic extensions for Parachain ChainSpecs. -#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, ChainSpecExtension)] -pub struct Extensions { - /// The relay chain of the Parachain. - #[serde(alias = "relayChain", alias = "RelayChain")] - pub relay_chain: String, -} - -impl Extensions { - /// Try to get the extension from the given `ChainSpec`. - pub fn try_get(chain_spec: &dyn sc_service::ChainSpec) -> Option<&Self> { - sc_chain_spec::get_extension(chain_spec.extensions()) + Ok(Box::new(GenericChainSpec::from_json_file(path.into())?)) } } /// Generic extensions for Parachain ChainSpecs used for extracting the extensions from chain specs. -/// This is also used only while `para_id` is around the corner. -// TODO: https://github.com/paritytech/polkadot-sdk/issues/8747 -// TODO: https://github.com/paritytech/polkadot-sdk/issues/8740 #[derive(Debug, Clone, PartialEq, Serialize, Deserialize, ChainSpecExtension)] -pub struct DeprecatedExtensions { +pub struct Extensions { /// The relay chain of the Parachain. It is kept here only for compatibility reasons until /// people migrate to using the new `Extensions` struct and associated logic in the node /// corresponding to pulling the parachain id from the runtime. #[serde(alias = "relayChain", alias = "RelayChain")] - pub relay_chain: String, + relay_chain: String, /// The id of the Parachain. #[serde(alias = "paraId", alias = "ParaId")] - #[deprecated( - note = "The para_id information is not required anymore and will be removed starting with `stable2512`. Runtimes must implement a new API called `cumulus_primitives_core::GetParachainInfo` to still be compatible with node versions starting with `stable2512`." - )] - pub para_id: Option, + para_id: Option, } -impl DeprecatedExtensions { +impl Extensions { /// Try to get the extension from the given `ChainSpec`. pub fn try_get(chain_spec: &dyn sc_service::ChainSpec) -> Option<&Self> { sc_chain_spec::get_extension(chain_spec.extensions()) } + + /// Create the extensions only with the relay_chain. + pub fn new_with_relay_chain(relay_chain: String) -> Self { + Extensions { relay_chain, para_id: None } + } + + /// Initialize extensions based on given parameters. + pub fn new(relay_chain: String, para_id: u32) -> Self { + Extensions { relay_chain, para_id: Some(para_id) } + } + + /// Para id field getter + pub fn para_id(&self) -> Option { + self.para_id + } + + /// Relay chain field getter + pub fn relay_chain(&self) -> String { + self.relay_chain.clone() + } } /// Generic chain spec for all polkadot-parachain runtimes pub type GenericChainSpec = sc_service::GenericChainSpec; -/// Generic chain spec which keeps chain spec loading compatible for those who provide -/// `para_id` extension instead of implementing the runtime API -/// `cumulus_primitives_core::GetParachainInfo`. -// TODO: https://github.com/paritytech/polkadot-sdk/issues/8747 -// TODO: https://github.com/paritytech/polkadot-sdk/issues/8740 -pub type DeprecatedGenericChainSpec = sc_service::GenericChainSpec; #[cfg(test)] mod tests { @@ -97,21 +90,13 @@ mod tests { let pascal_case = r#"{"RelayChain":"relay","ParaId":1}"#; let para_id_missing = r#"{"RelayChain":"westend"}"#; - let camel_case_extension: DeprecatedExtensions = serde_json::from_str(camel_case).unwrap(); - let snake_case_extension: DeprecatedExtensions = serde_json::from_str(snake_case).unwrap(); - let pascal_case_extension: DeprecatedExtensions = - serde_json::from_str(pascal_case).unwrap(); + let camel_case_extension: Extensions = serde_json::from_str(camel_case).unwrap(); + let snake_case_extension: Extensions = serde_json::from_str(snake_case).unwrap(); + let pascal_case_extension: Extensions = serde_json::from_str(pascal_case).unwrap(); let missing_paraid_extension: Extensions = serde_json::from_str(para_id_missing).unwrap(); - let missing_paraid_deprecated: DeprecatedExtensions = - serde_json::from_str(para_id_missing).unwrap(); assert_eq!(camel_case_extension, snake_case_extension); assert_eq!(snake_case_extension, pascal_case_extension); assert_eq!(missing_paraid_extension.relay_chain, "westend".to_string()); - - // TODO: remove it once `para_id` is removed: https://github.com/paritytech/polkadot-sdk/issues/8740 - assert_eq!(missing_paraid_deprecated.relay_chain, "westend".to_string()); - #[allow(deprecated)] - let test = missing_paraid_deprecated.para_id.is_none(); - assert!(test); + assert!(missing_paraid_extension.para_id.is_none()); } } diff --git a/cumulus/polkadot-omni-node/lib/src/common/spec.rs b/cumulus/polkadot-omni-node/lib/src/common/spec.rs index 5331c7b461031..f0d4cc0e0a88d 100644 --- a/cumulus/polkadot-omni-node/lib/src/common/spec.rs +++ b/cumulus/polkadot-omni-node/lib/src/common/spec.rs @@ -15,7 +15,7 @@ // limitations under the License. use crate::{ - chain_spec::DeprecatedExtensions, + chain_spec::Extensions, common::{ command::NodeCommandRunner, rpc::BuildRpcExtensions, @@ -51,7 +51,7 @@ use sc_telemetry::{TelemetryHandle, TelemetryWorker}; use sc_tracing::tracing::Instrument; use sc_transaction_pool::TransactionPoolHandle; use sc_transaction_pool_api::OffchainTransactionPoolFactory; -use sp_api::ProvideRuntimeApi; +use sp_api::{ApiExt, ProvideRuntimeApi}; use sp_keystore::KeystorePtr; use sp_runtime::traits::AccountIdConversion; use std::{future::Future, pin::Pin, sync::Arc, time::Duration}; @@ -157,19 +157,27 @@ pub(crate) trait BaseNodeSpec { parachain_config: &Configuration, ) -> Option { let best_hash = client.chain_info().best_hash; - let para_id = if let Ok(para_id) = client.runtime_api().parachain_id(best_hash) { - para_id + let para_id = if client + .runtime_api() + .has_api::>(best_hash) + .ok() + .filter(|has_api| *has_api) + .is_some() + { + client + .runtime_api() + .parachain_id(best_hash) + .inspect_err(|err| { + log::error!( + "`cumulus_primitives_core::GetParachainInfo` runtime API call errored with {}", + err + ); + }) + .ok()? } else { - // TODO: remove this once `para_id` extension is removed: https://github.com/paritytech/polkadot-sdk/issues/8740 - #[allow(deprecated)] - let id = ParaId::from( - DeprecatedExtensions::try_get(&*parachain_config.chain_spec) - .and_then(|ext| ext.para_id)?, - ); - // TODO: https://github.com/paritytech/polkadot-sdk/issues/8747 - // TODO: https://github.com/paritytech/polkadot-sdk/issues/8740 - log::info!("Deprecation notice: the parachain id was provided via the chain spec. This way of providing the parachain id to the node is not recommended. The alternative is to implement the `cumulus_primitives_core::GetParachainInfo` runtime API in the runtime, and upgrade it on-chain. Starting with `stable2512` providing the parachain id via the chain spec will not be supported anymore."); - id + ParaId::from( + Extensions::try_get(&*parachain_config.chain_spec).and_then(|ext| ext.para_id())?, + ) }; let parachain_account = diff --git a/cumulus/polkadot-omni-node/lib/src/nodes/mod.rs b/cumulus/polkadot-omni-node/lib/src/nodes/mod.rs index b310e30c92c58..0b27038ee318d 100644 --- a/cumulus/polkadot-omni-node/lib/src/nodes/mod.rs +++ b/cumulus/polkadot-omni-node/lib/src/nodes/mod.rs @@ -24,7 +24,7 @@ use sc_service::{Configuration, TaskManager}; /// The current node version for cumulus official binaries, which takes the basic /// SemVer form `..`. It should correspond to the latest /// `polkadot` version of a stable release. -pub const NODE_VERSION: &'static str = "1.19.0"; +pub const NODE_VERSION: &'static str = "1.19.1"; /// Trait that extends the `DynNodeSpec` trait with manual seal related logic. /// diff --git a/cumulus/polkadot-parachain/src/chain_spec/asset_hubs.rs b/cumulus/polkadot-parachain/src/chain_spec/asset_hubs.rs index ead445979bf1a..adae8dc30962f 100644 --- a/cumulus/polkadot-parachain/src/chain_spec/asset_hubs.rs +++ b/cumulus/polkadot-parachain/src/chain_spec/asset_hubs.rs @@ -25,7 +25,7 @@ pub fn asset_hub_westend_development_config() -> GenericChainSpec { GenericChainSpec::builder( asset_hub_westend_runtime::WASM_BINARY .expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: "westend".into() }, + Extensions::new_with_relay_chain("westend".into()), ) .with_name("Westend Asset Hub Development") .with_id("asset-hub-westend-dev") @@ -43,7 +43,7 @@ pub fn asset_hub_westend_local_config() -> GenericChainSpec { GenericChainSpec::builder( asset_hub_westend_runtime::WASM_BINARY .expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: "westend-local".into() }, + Extensions::new_with_relay_chain("westend-local".into()), ) .with_name("Westend Asset Hub Local") .with_id("asset-hub-westend-local") @@ -61,7 +61,7 @@ pub fn asset_hub_westend_config() -> GenericChainSpec { GenericChainSpec::builder( asset_hub_westend_runtime::WASM_BINARY .expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: "westend".into() }, + Extensions::new_with_relay_chain("westend".into()), ) .with_name("Westend Asset Hub") .with_id("asset-hub-westend") @@ -80,7 +80,6 @@ pub fn asset_hub_rococo_development_config() -> GenericChainSpec { properties, "Rococo Asset Hub Development", "asset-hub-rococo-dev", - 1000, ) } @@ -88,21 +87,15 @@ fn asset_hub_rococo_like_development_config( properties: sc_chain_spec::Properties, name: &str, chain_id: &str, - para_id: u32, ) -> GenericChainSpec { GenericChainSpec::builder( asset_hub_rococo_runtime::WASM_BINARY.expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: "rococo-dev".into() }, + Extensions::new_with_relay_chain("rococo-dev".into()), ) .with_name(name) .with_id(chain_id) .with_chain_type(ChainType::Local) .with_genesis_config_preset_name(sp_genesis_builder::DEV_RUNTIME_PRESET) - .with_genesis_config_patch(serde_json::json!({ - "parachainInfo": { - "parachainId": para_id, - }, - })) .with_properties(properties) .build() } @@ -116,7 +109,6 @@ pub fn asset_hub_rococo_local_config() -> GenericChainSpec { properties, "Rococo Asset Hub Local", "asset-hub-rococo-local", - 1000, ) } @@ -124,21 +116,15 @@ fn asset_hub_rococo_like_local_config( properties: sc_chain_spec::Properties, name: &str, chain_id: &str, - para_id: u32, ) -> GenericChainSpec { GenericChainSpec::builder( asset_hub_rococo_runtime::WASM_BINARY.expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: "rococo-local".into() }, + Extensions::new_with_relay_chain("rococo-local".into()), ) .with_name(name) .with_id(chain_id) .with_chain_type(ChainType::Local) .with_genesis_config_preset_name(sp_genesis_builder::LOCAL_TESTNET_RUNTIME_PRESET) - .with_genesis_config_patch(serde_json::json!({ - "parachainInfo": { - "parachainId": para_id, - }, - })) .with_properties(properties) .build() } @@ -149,7 +135,7 @@ pub fn asset_hub_rococo_genesis_config() -> GenericChainSpec { properties.insert("tokenDecimals".into(), 12.into()); GenericChainSpec::builder( asset_hub_rococo_runtime::WASM_BINARY.expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: "rococo".into() }, + Extensions::new_with_relay_chain("rococo".into()), ) .with_name("Rococo Asset Hub") .with_id("asset-hub-rococo") diff --git a/cumulus/polkadot-parachain/src/chain_spec/bridge_hubs.rs b/cumulus/polkadot-parachain/src/chain_spec/bridge_hubs.rs index 2adeaf2c99215..4927dcba7be05 100644 --- a/cumulus/polkadot-parachain/src/chain_spec/bridge_hubs.rs +++ b/cumulus/polkadot-parachain/src/chain_spec/bridge_hubs.rs @@ -14,7 +14,6 @@ // See the License for the specific language governing permissions and // limitations under the License. -use cumulus_primitives_core::ParaId; use polkadot_omni_node_lib::chain_spec::GenericChainSpec; use sc_chain_spec::{ChainSpec, ChainType}; use std::str::FromStr; @@ -77,14 +76,12 @@ impl BridgeHubRuntimeType { westend::BRIDGE_HUB_WESTEND_LOCAL, "Westend BridgeHub Local", "westend-local", - ParaId::new(1002), ChainType::Local, ))), BridgeHubRuntimeType::WestendDevelopment => Ok(Box::new(westend::local_config( westend::BRIDGE_HUB_WESTEND_DEVELOPMENT, "Westend BridgeHub Development", "westend-dev", - ParaId::new(1002), ChainType::Development, ))), BridgeHubRuntimeType::Rococo => Ok(Box::new(GenericChainSpec::from_json_bytes( @@ -94,7 +91,6 @@ impl BridgeHubRuntimeType { rococo::BRIDGE_HUB_ROCOCO_LOCAL, "Rococo BridgeHub Local", "rococo-local", - ParaId::new(1013), |_| (), ChainType::Local, ))), @@ -102,7 +98,6 @@ impl BridgeHubRuntimeType { rococo::BRIDGE_HUB_ROCOCO_DEVELOPMENT, "Rococo BridgeHub Development", "rococo-dev", - ParaId::new(1013), |_| (), ChainType::Development, ))), @@ -126,7 +121,7 @@ fn ensure_id(id: &str) -> Result<&str, String> { /// Sub-module for Rococo setup pub mod rococo { - use super::{ChainType, ParaId}; + use super::ChainType; use polkadot_omni_node_lib::chain_spec::{Extensions, GenericChainSpec}; pub(crate) const BRIDGE_HUB_ROCOCO: &str = "bridge-hub-rococo"; @@ -137,7 +132,6 @@ pub mod rococo { id: &str, chain_name: &str, relay_chain: &str, - para_id: ParaId, modify_props: ModifyProperties, chain_type: ChainType, ) -> GenericChainSpec { @@ -151,7 +145,7 @@ pub mod rococo { GenericChainSpec::builder( bridge_hub_rococo_runtime::WASM_BINARY .expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: relay_chain.to_string() }, + Extensions::new_with_relay_chain(relay_chain.to_string()), ) .with_name(chain_name) .with_id(super::ensure_id(id).expect("invalid id")) @@ -161,11 +155,6 @@ pub mod rococo { ChainType::Local => sp_genesis_builder::LOCAL_TESTNET_RUNTIME_PRESET, _ => panic!("chain_type: {chain_type:?} not supported here!"), }) - .with_genesis_config_patch(serde_json::json!({ - "parachainInfo": { - "parachainId": para_id, - }, - })) .with_properties(properties) .build() } @@ -179,7 +168,7 @@ pub mod kusama { /// Sub-module for Westend setup. pub mod westend { - use super::{ChainType, ParaId}; + use super::ChainType; use polkadot_omni_node_lib::chain_spec::{Extensions, GenericChainSpec}; pub(crate) const BRIDGE_HUB_WESTEND: &str = "bridge-hub-westend"; @@ -190,7 +179,6 @@ pub mod westend { id: &str, chain_name: &str, relay_chain: &str, - para_id: ParaId, chain_type: ChainType, ) -> GenericChainSpec { let mut properties = sc_chain_spec::Properties::new(); @@ -200,7 +188,7 @@ pub mod westend { GenericChainSpec::builder( bridge_hub_westend_runtime::WASM_BINARY .expect("WASM binary was not build, please build it!"), - Extensions { relay_chain: relay_chain.to_string() }, + Extensions::new_with_relay_chain(relay_chain.to_string()), ) .with_name(chain_name) .with_id(super::ensure_id(id).expect("invalid id")) @@ -210,11 +198,6 @@ pub mod westend { ChainType::Local => sp_genesis_builder::LOCAL_TESTNET_RUNTIME_PRESET, _ => panic!("chain_type: {chain_type:?} not supported here!"), }) - .with_genesis_config_patch(serde_json::json!({ - "parachainInfo": { - "parachainId": para_id, - }, - })) .with_properties(properties) .build() } diff --git a/cumulus/polkadot-parachain/src/chain_spec/collectives.rs b/cumulus/polkadot-parachain/src/chain_spec/collectives.rs index 5d2d57224f7b1..1e9a4489c99b0 100644 --- a/cumulus/polkadot-parachain/src/chain_spec/collectives.rs +++ b/cumulus/polkadot-parachain/src/chain_spec/collectives.rs @@ -27,7 +27,7 @@ pub fn collectives_westend_development_config() -> GenericChainSpec { GenericChainSpec::builder( collectives_westend_runtime::WASM_BINARY .expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: "westend-dev".into() }, + Extensions::new_with_relay_chain("westend-dev".into()), ) .with_name("Westend Collectives Development") .with_id("collectives_westend_dev") @@ -48,7 +48,7 @@ pub fn collectives_westend_local_config() -> GenericChainSpec { GenericChainSpec::builder( collectives_westend_runtime::WASM_BINARY .expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: "westend-local".into() }, + Extensions::new_with_relay_chain("westend-local".into()), ) .with_name("Westend Collectives Local") .with_id("collectives_westend_local") diff --git a/cumulus/polkadot-parachain/src/chain_spec/coretime.rs b/cumulus/polkadot-parachain/src/chain_spec/coretime.rs index 47cc66bdd4eca..e5cc4891d1f02 100644 --- a/cumulus/polkadot-parachain/src/chain_spec/coretime.rs +++ b/cumulus/polkadot-parachain/src/chain_spec/coretime.rs @@ -168,17 +168,20 @@ pub mod rococo { .expect("WASM binary was not built, please build it!") }; - GenericChainSpec::builder(wasm_binary, Extensions { relay_chain: relay_chain.to_string() }) - .with_name(&chain_name) - .with_id(runtime_type.into()) - .with_chain_type(chain_type.clone()) - .with_genesis_config_preset_name(match chain_type { - ChainType::Development => sp_genesis_builder::DEV_RUNTIME_PRESET, - ChainType::Local => sp_genesis_builder::LOCAL_TESTNET_RUNTIME_PRESET, - _ => panic!("chain_type: {chain_type:?} not supported here!"), - }) - .with_properties(properties) - .build() + GenericChainSpec::builder( + wasm_binary, + Extensions::new_with_relay_chain(relay_chain.to_string()), + ) + .with_name(&chain_name) + .with_id(runtime_type.into()) + .with_chain_type(chain_type.clone()) + .with_genesis_config_preset_name(match chain_type { + ChainType::Development => sp_genesis_builder::DEV_RUNTIME_PRESET, + ChainType::Local => sp_genesis_builder::LOCAL_TESTNET_RUNTIME_PRESET, + _ => panic!("chain_type: {chain_type:?} not supported here!"), + }) + .with_properties(properties) + .build() } } @@ -205,7 +208,7 @@ pub mod westend { GenericChainSpec::builder( coretime_westend_runtime::WASM_BINARY .expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: relay_chain.to_string() }, + Extensions::new_with_relay_chain(relay_chain.to_string()), ) .with_name(&chain_name) .with_id(runtime_type.into()) diff --git a/cumulus/polkadot-parachain/src/chain_spec/glutton.rs b/cumulus/polkadot-parachain/src/chain_spec/glutton.rs index 346075207836c..71f12ca3af969 100644 --- a/cumulus/polkadot-parachain/src/chain_spec/glutton.rs +++ b/cumulus/polkadot-parachain/src/chain_spec/glutton.rs @@ -29,7 +29,7 @@ pub fn glutton_westend_config( GenericChainSpec::builder( glutton_westend_runtime::WASM_BINARY.expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: relay_chain.into() }, + Extensions::new_with_relay_chain(relay_chain.into()), ) .with_name(&chain_type_name(para_id, &chain_type)) .with_id(&chain_id(para_id, &chain_type)) @@ -39,11 +39,6 @@ pub fn glutton_westend_config( ChainType::Local => sp_genesis_builder::LOCAL_TESTNET_RUNTIME_PRESET, _ => panic!("chain_type: {chain_type:?} not supported here!"), }) - .with_genesis_config_patch(serde_json::json!({ - "parachainInfo": { - "parachainId": para_id, - }, - })) .build() } diff --git a/cumulus/polkadot-parachain/src/chain_spec/penpal.rs b/cumulus/polkadot-parachain/src/chain_spec/penpal.rs index c82f5c57f4b15..2d9cda5b68f42 100644 --- a/cumulus/polkadot-parachain/src/chain_spec/penpal.rs +++ b/cumulus/polkadot-parachain/src/chain_spec/penpal.rs @@ -27,9 +27,7 @@ pub fn get_penpal_chain_spec(id: ParaId, relay_chain: &str) -> GenericChainSpec GenericChainSpec::builder( penpal_runtime::WASM_BINARY.expect("WASM binary was not built, please build it!"), - Extensions { - relay_chain: relay_chain.into(), // You MUST set this to the correct network! - }, + Extensions::new_with_relay_chain(relay_chain.into()), ) .with_name("Penpal Parachain") .with_id(&format!("penpal-{}", relay_chain.replace("-local", ""))) diff --git a/cumulus/polkadot-parachain/src/chain_spec/people.rs b/cumulus/polkadot-parachain/src/chain_spec/people.rs index fcd25d8127dbd..6735a15973df9 100644 --- a/cumulus/polkadot-parachain/src/chain_spec/people.rs +++ b/cumulus/polkadot-parachain/src/chain_spec/people.rs @@ -14,7 +14,6 @@ // See the License for the specific language governing permissions and // limitations under the License. -use cumulus_primitives_core::ParaId; use polkadot_omni_node_lib::chain_spec::GenericChainSpec; use sc_chain_spec::{ChainSpec, ChainType}; use std::str::FromStr; @@ -72,14 +71,12 @@ impl PeopleRuntimeType { rococo::PEOPLE_ROCOCO_LOCAL, "Rococo People Local", "rococo-local", - ParaId::new(1004), ChainType::Local, ))), PeopleRuntimeType::RococoDevelopment => Ok(Box::new(rococo::local_config( rococo::PEOPLE_ROCOCO_DEVELOPMENT, "Rococo People Development", "rococo-development", - ParaId::new(1004), ChainType::Development, ))), PeopleRuntimeType::Westend => Ok(Box::new(GenericChainSpec::from_json_bytes( @@ -89,14 +86,12 @@ impl PeopleRuntimeType { westend::PEOPLE_WESTEND_LOCAL, "Westend People Local", "westend-local", - ParaId::new(1004), ChainType::Local, ))), PeopleRuntimeType::WestendDevelopment => Ok(Box::new(westend::local_config( westend::PEOPLE_WESTEND_DEVELOPMENT, "Westend People Development", "westend-development", - ParaId::new(1004), ChainType::Development, ))), other => Err(std::format!( @@ -122,7 +117,6 @@ fn ensure_id(id: &str) -> Result<&str, String> { /// Sub-module for Rococo setup. pub mod rococo { - use super::ParaId; use polkadot_omni_node_lib::chain_spec::{Extensions, GenericChainSpec}; use sc_chain_spec::ChainType; @@ -131,10 +125,9 @@ pub mod rococo { pub(crate) const PEOPLE_ROCOCO_DEVELOPMENT: &str = "people-rococo-dev"; pub fn local_config( - id: &str, + spec_id: &str, chain_name: &str, relay_chain: &str, - para_id: ParaId, chain_type: ChainType, ) -> GenericChainSpec { let mut properties = sc_chain_spec::Properties::new(); @@ -145,21 +138,16 @@ pub mod rococo { GenericChainSpec::builder( people_rococo_runtime::WASM_BINARY .expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: relay_chain.to_string() }, + Extensions::new_with_relay_chain(relay_chain.to_string()), ) .with_name(chain_name) - .with_id(super::ensure_id(id).expect("invalid id")) + .with_id(super::ensure_id(spec_id).expect("invalid id")) .with_chain_type(chain_type.clone()) .with_genesis_config_preset_name(match chain_type { ChainType::Development => sp_genesis_builder::DEV_RUNTIME_PRESET, ChainType::Local => sp_genesis_builder::LOCAL_TESTNET_RUNTIME_PRESET, _ => panic!("chain_type: {chain_type:?} not supported here!"), }) - .with_genesis_config_patch(serde_json::json!({ - "parachainInfo": { - "parachainId": para_id, - }, - })) .with_properties(properties) .build() } @@ -167,7 +155,6 @@ pub mod rococo { /// Sub-module for Westend setup. pub mod westend { - use super::ParaId; use polkadot_omni_node_lib::chain_spec::{Extensions, GenericChainSpec}; use sc_chain_spec::ChainType; @@ -176,10 +163,9 @@ pub mod westend { pub(crate) const PEOPLE_WESTEND_DEVELOPMENT: &str = "people-westend-dev"; pub fn local_config( - id: &str, + spec_id: &str, chain_name: &str, relay_chain: &str, - para_id: ParaId, chain_type: ChainType, ) -> GenericChainSpec { let mut properties = sc_chain_spec::Properties::new(); @@ -190,21 +176,16 @@ pub mod westend { GenericChainSpec::builder( people_westend_runtime::WASM_BINARY .expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: relay_chain.to_string() }, + Extensions::new_with_relay_chain(relay_chain.to_string()), ) .with_name(chain_name) - .with_id(super::ensure_id(id).expect("invalid id")) + .with_id(super::ensure_id(spec_id).expect("invalid id")) .with_chain_type(chain_type.clone()) .with_genesis_config_preset_name(match chain_type { ChainType::Development => sp_genesis_builder::DEV_RUNTIME_PRESET, ChainType::Local => sp_genesis_builder::LOCAL_TESTNET_RUNTIME_PRESET, _ => panic!("chain_type: {chain_type:?} not supported here!"), }) - .with_genesis_config_patch(serde_json::json!({ - "parachainInfo": { - "parachainId": para_id, - }, - })) .with_properties(properties) .build() } diff --git a/cumulus/polkadot-parachain/src/chain_spec/rococo_parachain.rs b/cumulus/polkadot-parachain/src/chain_spec/rococo_parachain.rs index 8d2dca95f111c..dc6a3b6666277 100644 --- a/cumulus/polkadot-parachain/src/chain_spec/rococo_parachain.rs +++ b/cumulus/polkadot-parachain/src/chain_spec/rococo_parachain.rs @@ -27,7 +27,7 @@ use sp_core::crypto::UncheckedInto; pub fn rococo_parachain_local_config() -> GenericChainSpec { GenericChainSpec::builder( rococo_parachain_runtime::WASM_BINARY.expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: "rococo-local".into() }, + Extensions::new_with_relay_chain("rococo-local".into()), ) .with_name("Rococo Parachain Local") .with_id("local_testnet") @@ -39,7 +39,7 @@ pub fn rococo_parachain_local_config() -> GenericChainSpec { pub fn staging_rococo_parachain_local_config() -> GenericChainSpec { GenericChainSpec::builder( rococo_parachain_runtime::WASM_BINARY.expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: "rococo-local".into() }, + Extensions::new_with_relay_chain("rococo-local".into()), ) .with_name("Staging Rococo Parachain Local") .with_id("staging_testnet") diff --git a/cumulus/polkadot-parachain/src/chain_spec/yet_another_parachain.rs b/cumulus/polkadot-parachain/src/chain_spec/yet_another_parachain.rs index fb1a6adfcdf2f..3905f8d62b7a0 100644 --- a/cumulus/polkadot-parachain/src/chain_spec/yet_another_parachain.rs +++ b/cumulus/polkadot-parachain/src/chain_spec/yet_another_parachain.rs @@ -86,7 +86,7 @@ pub fn yet_another_parachain_config( GenericChainSpec::builder( yet_another_parachain_runtime::WASM_BINARY .expect("WASM binary was not built, please build it!"), - Extensions { relay_chain: relay.into() }, + Extensions::new_with_relay_chain(relay.into()), ) .with_name("Yet Another Parachain") .with_id("yet_another_parachain") diff --git a/polkadot/node/primitives/src/lib.rs b/polkadot/node/primitives/src/lib.rs index 3a187ce5e03b2..10791dc283daf 100644 --- a/polkadot/node/primitives/src/lib.rs +++ b/polkadot/node/primitives/src/lib.rs @@ -62,7 +62,7 @@ pub use disputes::{ /// relatively rare. /// /// The associated worker binaries should use the same version as the node that spawns them. -pub const NODE_VERSION: &'static str = "1.19.0"; +pub const NODE_VERSION: &'static str = "1.19.1"; // For a 16-ary Merkle Prefix Trie, we can expect at most 16 32-byte hashes per node // plus some overhead: diff --git a/polkadot/runtime/common/Cargo.toml b/polkadot/runtime/common/Cargo.toml index c4c43f2102639..31a7269148012 100644 --- a/polkadot/runtime/common/Cargo.toml +++ b/polkadot/runtime/common/Cargo.toml @@ -131,6 +131,7 @@ runtime-benchmarks = [ "pallet-election-provider-multi-phase/runtime-benchmarks", "pallet-fast-unstake/runtime-benchmarks", "pallet-identity/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "pallet-transaction-payment/runtime-benchmarks", diff --git a/polkadot/runtime/parachains/Cargo.toml b/polkadot/runtime/parachains/Cargo.toml index 5cf22bbd38c38..cddfb75d3e9f9 100644 --- a/polkadot/runtime/parachains/Cargo.toml +++ b/polkadot/runtime/parachains/Cargo.toml @@ -131,6 +131,7 @@ runtime-benchmarks = [ "pallet-broker/runtime-benchmarks", "pallet-message-queue/runtime-benchmarks", "pallet-mmr/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "polkadot-parachain-primitives/runtime-benchmarks", diff --git a/polkadot/runtime/parachains/src/disputes/slashing/benchmarking.rs b/polkadot/runtime/parachains/src/disputes/slashing/benchmarking.rs index f99aa2d1b1936..4aa076faac431 100644 --- a/polkadot/runtime/parachains/src/disputes/slashing/benchmarking.rs +++ b/polkadot/runtime/parachains/src/disputes/slashing/benchmarking.rs @@ -76,6 +76,7 @@ where let proof: Vec = vec![]; whitelist_account!(controller); + pallet_session::Pallet::::ensure_can_pay_key_deposit(&controller).unwrap(); pallet_session::Pallet::::set_keys(RawOrigin::Signed(controller).into(), keys, proof) .expect("session::set_keys should work"); } diff --git a/polkadot/runtime/rococo/Cargo.toml b/polkadot/runtime/rococo/Cargo.toml index 96c613014e94a..be65accb31cee 100644 --- a/polkadot/runtime/rococo/Cargo.toml +++ b/polkadot/runtime/rococo/Cargo.toml @@ -244,6 +244,7 @@ runtime-benchmarks = [ "pallet-recovery/runtime-benchmarks", "pallet-referenda/runtime-benchmarks", "pallet-scheduler/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-society/runtime-benchmarks", "pallet-staking/runtime-benchmarks", "pallet-state-trie-migration/runtime-benchmarks", diff --git a/polkadot/runtime/rococo/src/lib.rs b/polkadot/runtime/rococo/src/lib.rs index 7a7c046555d65..78e943f0c179a 100644 --- a/polkadot/runtime/rococo/src/lib.rs +++ b/polkadot/runtime/rococo/src/lib.rs @@ -184,7 +184,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("rococo"), impl_name: alloc::borrow::Cow::Borrowed("parity-rococo-v2.0"), authoring_version: 0, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 26, diff --git a/polkadot/runtime/test-runtime/Cargo.toml b/polkadot/runtime/test-runtime/Cargo.toml index b9119d5f9c57d..4c4a79500f250 100644 --- a/polkadot/runtime/test-runtime/Cargo.toml +++ b/polkadot/runtime/test-runtime/Cargo.toml @@ -132,6 +132,7 @@ runtime-benchmarks = [ "pallet-grandpa/runtime-benchmarks", "pallet-indices/runtime-benchmarks", "pallet-offences/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking/runtime-benchmarks", "pallet-sudo/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", diff --git a/polkadot/runtime/westend/Cargo.toml b/polkadot/runtime/westend/Cargo.toml index 30174bf794908..b44bdf62c3bb1 100644 --- a/polkadot/runtime/westend/Cargo.toml +++ b/polkadot/runtime/westend/Cargo.toml @@ -267,6 +267,7 @@ runtime-benchmarks = [ "pallet-referenda/runtime-benchmarks", "pallet-scheduler/runtime-benchmarks", "pallet-session-benchmarking/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking-async-ah-client/runtime-benchmarks", "pallet-staking-async-rc-client/runtime-benchmarks", "pallet-staking/runtime-benchmarks", diff --git a/polkadot/runtime/westend/src/lib.rs b/polkadot/runtime/westend/src/lib.rs index c3107ab3db8a3..2724d102da2e2 100644 --- a/polkadot/runtime/westend/src/lib.rs +++ b/polkadot/runtime/westend/src/lib.rs @@ -174,7 +174,7 @@ pub const VERSION: RuntimeVersion = RuntimeVersion { spec_name: alloc::borrow::Cow::Borrowed("westend"), impl_name: alloc::borrow::Cow::Borrowed("parity-westend"), authoring_version: 2, - spec_version: 1_019_002, + spec_version: 1_019_003, impl_version: 0, apis: RUNTIME_API_VERSIONS, transaction_version: 27, @@ -509,6 +509,7 @@ impl pallet_authorship::Config for Runtime { parameter_types! { pub const Period: BlockNumber = 10 * MINUTES; pub const Offset: BlockNumber = 0; + pub const KeyDeposit: Balance = deposit(1, 5 * 32 + 33); } impl_opaque_keys! { @@ -534,7 +535,7 @@ impl pallet_session::Config for Runtime { type DisablingStrategy = pallet_session::disabling::UpToLimitWithReEnablingDisablingStrategy; type WeightInfo = weights::pallet_session::WeightInfo; type Currency = Balances; - type KeyDeposit = (); + type KeyDeposit = KeyDeposit; } impl pallet_session::historical::Config for Runtime { diff --git a/polkadot/runtime/westend/src/weights/pallet_session.rs b/polkadot/runtime/westend/src/weights/pallet_session.rs index 813c6e3a66711..9f93de3cb9e66 100644 --- a/polkadot/runtime/westend/src/weights/pallet_session.rs +++ b/polkadot/runtime/westend/src/weights/pallet_session.rs @@ -17,9 +17,9 @@ //! Autogenerated weights for `pallet_session` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-02-22, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-19, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `3a2e9ae8a8f5`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `276823fd1fd5`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -51,36 +51,36 @@ use core::marker::PhantomData; /// Weight functions for `pallet_session`. pub struct WeightInfo(PhantomData); impl pallet_session::WeightInfo for WeightInfo { - /// Storage: `Staking::Ledger` (r:1 w:0) - /// Proof: `Staking::Ledger` (`max_values`: None, `max_size`: Some(1091), added: 3566, mode: `MaxEncodedLen`) /// Storage: `Session::NextKeys` (r:1 w:1) /// Proof: `Session::NextKeys` (`max_values`: None, `max_size`: None, mode: `Measured`) /// Storage: `Session::KeyOwner` (r:6 w:6) /// Proof: `Session::KeyOwner` (`max_values`: None, `max_size`: None, mode: `Measured`) + /// Storage: `Balances::Holds` (r:1 w:1) + /// Proof: `Balances::Holds` (`max_values`: None, `max_size`: Some(139), added: 2614, mode: `MaxEncodedLen`) fn set_keys() -> Weight { // Proof Size summary in bytes: - // Measured: `1899` - // Estimated: `17739` - // Minimum execution time: 71_274_000 picoseconds. - Weight::from_parts(73_693_000, 0) - .saturating_add(Weight::from_parts(0, 17739)) + // Measured: `1154` + // Estimated: `16994` + // Minimum execution time: 98_517_000 picoseconds. + Weight::from_parts(101_461_000, 0) + .saturating_add(Weight::from_parts(0, 16994)) .saturating_add(T::DbWeight::get().reads(8)) - .saturating_add(T::DbWeight::get().writes(7)) + .saturating_add(T::DbWeight::get().writes(8)) } - /// Storage: `Staking::Ledger` (r:1 w:0) - /// Proof: `Staking::Ledger` (`max_values`: None, `max_size`: Some(1091), added: 3566, mode: `MaxEncodedLen`) /// Storage: `Session::NextKeys` (r:1 w:1) /// Proof: `Session::NextKeys` (`max_values`: None, `max_size`: None, mode: `Measured`) + /// Storage: `Balances::Holds` (r:1 w:1) + /// Proof: `Balances::Holds` (`max_values`: None, `max_size`: Some(139), added: 2614, mode: `MaxEncodedLen`) /// Storage: `Session::KeyOwner` (r:0 w:6) /// Proof: `Session::KeyOwner` (`max_values`: None, `max_size`: None, mode: `Measured`) fn purge_keys() -> Weight { // Proof Size summary in bytes: - // Measured: `1814` - // Estimated: `5279` - // Minimum execution time: 52_441_000 picoseconds. - Weight::from_parts(55_437_000, 0) - .saturating_add(Weight::from_parts(0, 5279)) + // Measured: `1141` + // Estimated: `4606` + // Minimum execution time: 71_897_000 picoseconds. + Weight::from_parts(74_310_000, 0) + .saturating_add(Weight::from_parts(0, 4606)) .saturating_add(T::DbWeight::get().reads(2)) - .saturating_add(T::DbWeight::get().writes(7)) + .saturating_add(T::DbWeight::get().writes(8)) } } diff --git a/polkadot/runtime/westend/src/weights/polkadot_runtime_parachains_disputes_slashing.rs b/polkadot/runtime/westend/src/weights/polkadot_runtime_parachains_disputes_slashing.rs index d75724d1ae0f5..866a160598acf 100644 --- a/polkadot/runtime/westend/src/weights/polkadot_runtime_parachains_disputes_slashing.rs +++ b/polkadot/runtime/westend/src/weights/polkadot_runtime_parachains_disputes_slashing.rs @@ -17,9 +17,9 @@ //! Autogenerated weights for `polkadot_runtime_parachains::disputes::slashing` //! //! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 32.0.0 -//! DATE: 2025-02-21, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` +//! DATE: 2025-08-19, STEPS: `50`, REPEAT: `20`, LOW RANGE: `[]`, HIGH RANGE: `[]` //! WORST CASE MAP SIZE: `1000000` -//! HOSTNAME: `3a2e9ae8a8f5`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` +//! HOSTNAME: `276823fd1fd5`, CPU: `Intel(R) Xeon(R) CPU @ 2.60GHz` //! WASM-EXECUTION: `Compiled`, CHAIN: `None`, DB CACHE: 1024 // Executed Command: @@ -61,12 +61,16 @@ impl polkadot_runtime_parachains::disputes::slashing::W /// Proof: `Offences::ConcurrentReportsIndex` (`max_values`: None, `max_size`: None, mode: `Measured`) /// Storage: `Offences::Reports` (r:1 w:1) /// Proof: `Offences::Reports` (`max_values`: None, `max_size`: None, mode: `Measured`) + /// Storage: `StakingAhClient::Mode` (r:1 w:0) + /// Proof: `StakingAhClient::Mode` (`max_values`: Some(1), `max_size`: Some(1), added: 496, mode: `MaxEncodedLen`) + /// Storage: `Staking::SlashRewardFraction` (r:1 w:0) + /// Proof: `Staking::SlashRewardFraction` (`max_values`: Some(1), `max_size`: Some(4), added: 499, mode: `MaxEncodedLen`) /// Storage: `Staking::ActiveEra` (r:1 w:0) /// Proof: `Staking::ActiveEra` (`max_values`: Some(1), `max_size`: Some(13), added: 508, mode: `MaxEncodedLen`) /// Storage: `Staking::ErasStartSessionIndex` (r:1 w:0) /// Proof: `Staking::ErasStartSessionIndex` (`max_values`: None, `max_size`: Some(16), added: 2491, mode: `MaxEncodedLen`) /// Storage: `Staking::Invulnerables` (r:1 w:0) - /// Proof: `Staking::Invulnerables` (`max_values`: Some(1), `max_size`: Some(641), added: 1136, mode: `MaxEncodedLen`) + /// Proof: `Staking::Invulnerables` (`max_values`: Some(1), `max_size`: None, mode: `Measured`) /// Storage: `Staking::ErasStakersOverview` (r:1 w:0) /// Proof: `Staking::ErasStakersOverview` (`max_values`: None, `max_size`: Some(92), added: 2567, mode: `MaxEncodedLen`) /// Storage: `Session::DisabledValidators` (r:1 w:1) @@ -75,22 +79,24 @@ impl polkadot_runtime_parachains::disputes::slashing::W /// Proof: `Session::Validators` (`max_values`: Some(1), `max_size`: None, mode: `Measured`) /// Storage: `Staking::ValidatorSlashInEra` (r:1 w:1) /// Proof: `Staking::ValidatorSlashInEra` (`max_values`: None, `max_size`: Some(72), added: 2547, mode: `MaxEncodedLen`) - /// Storage: `Staking::OffenceQueue` (r:1 w:1) - /// Proof: `Staking::OffenceQueue` (`max_values`: None, `max_size`: Some(101), added: 2576, mode: `MaxEncodedLen`) - /// Storage: `Staking::OffenceQueueEras` (r:1 w:1) - /// Proof: `Staking::OffenceQueueEras` (`max_values`: Some(1), `max_size`: Some(9), added: 504, mode: `MaxEncodedLen`) + /// Storage: `Staking::SlashingSpans` (r:1 w:1) + /// Proof: `Staking::SlashingSpans` (`max_values`: None, `max_size`: None, mode: `Measured`) + /// Storage: `Staking::SpanSlash` (r:1 w:1) + /// Proof: `Staking::SpanSlash` (`max_values`: None, `max_size`: Some(76), added: 2551, mode: `MaxEncodedLen`) + /// Storage: `Staking::UnappliedSlashes` (r:1 w:1) + /// Proof: `Staking::UnappliedSlashes` (`max_values`: None, `max_size`: None, mode: `Measured`) /// The range of component `n` is `[4, 300]`. fn report_dispute_lost_unsigned(n: u32, ) -> Weight { // Proof Size summary in bytes: - // Measured: `2024 + n * (33 ±0)` - // Estimated: `5386 + n * (34 ±0)` - // Minimum execution time: 88_786_000 picoseconds. - Weight::from_parts(127_346_367, 0) - .saturating_add(Weight::from_parts(0, 5386)) - // Standard Error: 3_530 - .saturating_add(Weight::from_parts(144_389, 0).saturating_mul(n.into())) - .saturating_add(T::DbWeight::get().reads(14)) - .saturating_add(T::DbWeight::get().writes(7)) + // Measured: `2145 + n * (33 ±0)` + // Estimated: `5588 + n * (34 ±0)` + // Minimum execution time: 106_507_000 picoseconds. + Weight::from_parts(151_695_565, 0) + .saturating_add(Weight::from_parts(0, 5588)) + // Standard Error: 4_446 + .saturating_add(Weight::from_parts(202_889, 0).saturating_mul(n.into())) + .saturating_add(T::DbWeight::get().reads(17)) + .saturating_add(T::DbWeight::get().writes(8)) .saturating_add(Weight::from_parts(0, 34).saturating_mul(n.into())) } } diff --git a/polkadot/xcm/xcm-simulator/src/lib.rs b/polkadot/xcm/xcm-simulator/src/lib.rs index d494c64daacec..160240a6e12d9 100644 --- a/polkadot/xcm/xcm-simulator/src/lib.rs +++ b/polkadot/xcm/xcm-simulator/src/lib.rs @@ -467,10 +467,51 @@ pub mod helpers { } } - /// A test utility for tracking XCM topic IDs - #[derive(Clone)] + /// A test utility for tracking XCM topic IDs. + /// + /// # Examples + /// + /// ``` + /// use sp_runtime::testing::H256; + /// use xcm_simulator::helpers::TopicIdTracker; + /// + /// // Dummy topic IDs + /// let topic_id = H256::repeat_byte(0x42); + /// + /// // Create a new tracker + /// let mut tracker = TopicIdTracker::new(); + /// + /// // Insert the same topic ID for three chains + /// tracker.insert("ChainA", topic_id); + /// tracker.insert_all("ChainB", &[topic_id]); + /// tracker.insert_and_assert_unique("ChainC", topic_id); + /// + /// // Assert the topic ID exists everywhere + /// tracker.assert_contains("ChainA", &topic_id); + /// tracker.assert_id_seen_on_all_chains(&topic_id); + /// tracker.assert_only_id_seen_on_all_chains("ChainB"); + /// tracker.assert_unique(); + /// + /// // You can also test that inserting inconsistent topic IDs fails: + /// let another_id = H256::repeat_byte(0x43); + /// let result = std::panic::catch_unwind(|| { + /// let mut tracker = TopicIdTracker::new(); + /// tracker.insert("ChainA", topic_id); + /// tracker.insert_and_assert_unique("ChainB", another_id); + /// }); + /// assert!(result.is_err()); + /// + /// let result = std::panic::catch_unwind(|| { + /// let mut tracker = TopicIdTracker::new(); + /// tracker.insert("ChainA", topic_id); + /// tracker.insert("ChainB", another_id); + /// tracker.assert_unique(); + /// }); + /// assert!(result.is_err()); + /// ``` + #[derive(Clone, Debug)] pub struct TopicIdTracker { - ids: HashMap, + ids: HashMap>, } impl TopicIdTracker { /// Initialises a new, empty topic ID tracker. @@ -478,9 +519,53 @@ pub mod helpers { TopicIdTracker { ids: HashMap::new() } } + /// Asserts that the given topic ID has been recorded for the specified chain. + pub fn assert_contains(&self, chain: &str, id: &H256) { + let ids = self + .ids + .get(chain) + .expect(&format!("No topic IDs recorded for chain '{}'", chain)); + + assert!( + ids.contains(id), + "Expected topic ID {:?} not found for chain '{}'. Found topic IDs: {:?}", + id, + chain, + ids + ); + } + + /// Asserts that the given topic ID has been recorded on all chains. + pub fn assert_id_seen_on_all_chains(&self, id: &H256) { + self.ids.keys().for_each(|chain| { + self.assert_contains(chain, id); + }); + } + + /// Asserts that exactly one topic ID is recorded on the given chain, and that the same ID + /// is present on all other chains. + pub fn assert_only_id_seen_on_all_chains(&self, chain: &str) { + let ids = self + .ids + .get(chain) + .expect(&format!("No topic IDs recorded for chain '{}'", chain)); + + assert_eq!( + ids.len(), + 1, + "Expected exactly one topic ID for chain '{}', but found {}: {:?}", + chain, + ids.len(), + ids + ); + + let id = *ids.iter().next().unwrap(); + self.assert_id_seen_on_all_chains(&id); + } + /// Asserts that exactly one unique topic ID is present across all captured entries. pub fn assert_unique(&self) { - let unique_ids: HashSet<_> = self.ids.values().collect(); + let unique_ids: HashSet<_> = self.ids.values().flatten().collect(); assert_eq!( unique_ids.len(), 1, @@ -492,14 +577,28 @@ pub mod helpers { /// Inserts a topic ID with the given chain name in the captor. pub fn insert(&mut self, chain: &str, id: H256) { - self.ids.insert(chain.to_string(), id); + self.ids.entry(chain.to_string()).or_default().insert(id); + } + + /// Inserts all topic IDs associated with the given chain name. + pub fn insert_all(&mut self, chain: &str, ids: &[H256]) { + ids.iter().for_each(|&id| self.insert(chain, id)); } /// Inserts a topic ID for a given chain and then asserts global uniqueness. pub fn insert_and_assert_unique(&mut self, chain: &str, id: H256) { - if let Some(existing_id) = self.ids.get(chain) { + if let Some(existing_ids) = self.ids.get(chain) { assert_eq!( - id, *existing_id, + existing_ids.len(), + 1, + "Expected exactly one topic ID for chain '{}', but found: {:?}", + chain, + existing_ids + ); + let existing_id = + *existing_ids.iter().next().expect(&format!("Topic ID for chain '{}'", chain)); + assert_eq!( + id, existing_id, "Topic ID mismatch for chain '{}': expected {:?}, got {:?}", id, existing_id, chain ); @@ -509,4 +608,33 @@ pub mod helpers { self.assert_unique(); } } + + #[cfg(test)] + mod tests { + use super::*; + use sp_runtime::testing::H256; + + #[test] + #[should_panic(expected = "Expected exactly one topic ID")] + fn test_assert_unique_fails_with_multiple_ids() { + let mut tracker = TopicIdTracker::new(); + let id1 = H256::repeat_byte(0x42); + let id2 = H256::repeat_byte(0x43); + + tracker.insert("ChainA", id1); + tracker.insert("ChainB", id2); + tracker.assert_unique(); + } + + #[test] + #[should_panic(expected = "Topic ID mismatch")] + fn test_insert_and_assert_unique_mismatch() { + let mut tracker = TopicIdTracker::new(); + let id1 = H256::repeat_byte(0x42); + let id2 = H256::repeat_byte(0x43); + + tracker.insert_and_assert_unique("ChainA", id1); + tracker.insert_and_assert_unique("ChainA", id2); + } + } } diff --git a/prdoc/pr_9177.prdoc b/prdoc/pr_9177.prdoc new file mode 100644 index 0000000000000..9f4e954fe6048 --- /dev/null +++ b/prdoc/pr_9177.prdoc @@ -0,0 +1,10 @@ +title: align eth-rpc response with geth +doc: +- audience: Runtime Dev + description: |- + - Update serde encoding for eth-rpc to match serialization behavior of Geth +crates: +- name: pallet-revive + bump: patch +- name: pallet-revive-eth-rpc + bump: patch diff --git a/prdoc/pr_9201.prdoc b/prdoc/pr_9201.prdoc new file mode 100644 index 0000000000000..c08444c78683d --- /dev/null +++ b/prdoc/pr_9201.prdoc @@ -0,0 +1,16 @@ +title: '`polkadot-parachain`: fixes and changes related to GetParachainInfo' +doc: +- audience: Node Dev + description: |- + - Provides some updated to the asset-hub-westend-local chain specification, by adding appropriate genesis patch for parachainInfo. + - refactors the logic related to fetching `para_id` with the node, so that when failing to use `GetParachainInfo::parachain_id` we also get a log with the error (before defaulting to `para_id` extracted from chain spec). + - removes comments/deprecation notices throughout the code that introduce para-id flag removal (from chain-spec-builder and support for parsing it from chain specifications) +crates: +- name: polkadot-parachain-bin + bump: patch +- name: polkadot-omni-node-lib + bump: major +- name: polkadot-omni-node + bump: patch +- name: staging-chain-spec-builder + bump: patch diff --git a/prdoc/pr_9316.prdoc b/prdoc/pr_9316.prdoc new file mode 100644 index 0000000000000..dcd1712fa1e84 --- /dev/null +++ b/prdoc/pr_9316.prdoc @@ -0,0 +1,9 @@ +title: Enable `TopicIdTracker` to support multiple flows +doc: +- audience: Runtime Dev + description: This PR enables `TopicIdTracker` to support multiple flows. +crates: +- name: emulated-integration-tests-common + bump: minor +- name: xcm-simulator + bump: minor diff --git a/prdoc/pr_9381.prdoc b/prdoc/pr_9381.prdoc new file mode 100644 index 0000000000000..a3dbed26a78c2 --- /dev/null +++ b/prdoc/pr_9381.prdoc @@ -0,0 +1,8 @@ +title: Replace `log` with `tracing` on `pallet-bridge-relayers` +doc: +- audience: Runtime Dev + description: This PR replaces `log` with `tracing` instrumentation on `pallet-bridge-relayers` + by providing structured logging. +crates: +- name: pallet-bridge-relayers + bump: minor diff --git a/prdoc/pr_9488.prdoc b/prdoc/pr_9488.prdoc new file mode 100644 index 0000000000000..6f0fb26e3078c --- /dev/null +++ b/prdoc/pr_9488.prdoc @@ -0,0 +1,14 @@ +title: 'prdoc: add missing crates bumps' +doc: +- audience: Node Dev + description: + Adds a few crate bumps associated to PRs which missed to bump them due to a corner case missed by the release tooling. +crates: + - name: sp-wasm-interface + bump: major + - name: sp-rpc + bump: patch + - name: sc-storage-monitor + bump: patch + - name: sp-keystore + bump: patch diff --git a/prdoc/pr_9497.prdoc b/prdoc/pr_9497.prdoc new file mode 100644 index 0000000000000..c4f0b0b0bb416 --- /dev/null +++ b/prdoc/pr_9497.prdoc @@ -0,0 +1,12 @@ +title: 'Society pallet supports non-consecutive block provider' +doc: +- audience: Runtime Dev + description: |- + Society pallet correctly handles situations where on_initialize is invoked with block numbers that: + - increase but are not strictly consecutive (e.g., jump from 5 → 10), or + - are repeated (e.g., multiple blocks are built at the same Relay Chain parent block, all reporting the same BlockNumberProvider value). + This situation may occur when the BlockNumberProvider is not local - for example, on a parachain using the Relay Chain block number provider. + +crates: +- name: pallet-society + bump: major diff --git a/prdoc/pr_9501.prdoc b/prdoc/pr_9501.prdoc new file mode 100644 index 0000000000000..995095f0819c0 --- /dev/null +++ b/prdoc/pr_9501.prdoc @@ -0,0 +1,13 @@ +title: '[revive] revm move existing files' +doc: +- audience: Runtime Dev + description: |- + - Move exisiting files in pallet-revive to accomodate the upcoming EVM backend + - Add solc/resolc compilation feature for fixtures +crates: +- name: asset-hub-westend-runtime + bump: patch +- name: pallet-revive + bump: patch +- name: pallet-revive-fixtures + bump: patch diff --git a/prdoc/pr_9504.prdoc b/prdoc/pr_9504.prdoc new file mode 100644 index 0000000000000..0e4eff770f916 --- /dev/null +++ b/prdoc/pr_9504.prdoc @@ -0,0 +1,62 @@ +title: Fix `pallet_session` benchmarks +doc: +- audience: Runtime Dev + description: |- + Fixes the benchmarking code of `pallet_session` such that it works with any `KeyDeposit`. +crates: +- name: westend-runtime + bump: minor +- name: pallet-session-benchmarking + bump: patch +- name: pallet-session + bump: patch +- name: polkadot-sdk + bump: patch +- name: polkadot-runtime-parachains + bump: patch +- name: pallet-babe + bump: patch +- name: pallet-staking + bump: patch +- name: pallet-grandpa + bump: patch +- name: polkadot-runtime-common + bump: patch +- name: pallet-beefy-mmr + bump: patch +- name: pallet-offences-benchmarking + bump: patch +- name: pallet-im-online + bump: patch +- name: pallet-staking-async-ah-client + bump: patch +- name: rococo-runtime + bump: patch +- name: pallet-collator-selection + bump: patch +- name: cumulus-pallet-session-benchmarking + bump: patch +- name: pallet-root-offences + bump: patch +- name: snowbridge-runtime-test-common + bump: patch +- name: asset-hub-rococo-runtime + bump: patch +- name: asset-hub-westend-runtime + bump: patch +- name: bridge-hub-rococo-runtime + bump: patch +- name: bridge-hub-westend-runtime + bump: patch +- name: collectives-westend-runtime + bump: patch +- name: coretime-rococo-runtime + bump: patch +- name: coretime-westend-runtime + bump: patch +- name: people-rococo-runtime + bump: patch +- name: people-westend-runtime + bump: patch +- name: penpal-runtime + bump: patch diff --git a/prdoc/pr_9511.prdoc b/prdoc/pr_9511.prdoc new file mode 100644 index 0000000000000..35aa5f493e047 --- /dev/null +++ b/prdoc/pr_9511.prdoc @@ -0,0 +1,11 @@ +title: 'EPMB/Signed: Make invulnerables non-eject-able' +doc: +- audience: Runtime Dev + description: 'Follow-up to https://github.com/paritytech/polkadot-sdk/pull/8877 + and audits: Make it such that invulnerable accounts cannot be ejected from the + election signed queue altogether. ' +crates: +- name: pallet-election-provider-multi-block + bump: patch +- name: pallet-staking-async + bump: patch diff --git a/prdoc/pr_9539.prdoc b/prdoc/pr_9539.prdoc new file mode 100644 index 0000000000000..edfd6b9bde2f0 --- /dev/null +++ b/prdoc/pr_9539.prdoc @@ -0,0 +1,28 @@ +title: '[XCMP] `take_first_concatenated_xcm()` improvements' +doc: +- audience: Runtime Dev + description: |- + This PR: + - improves `take_first_concatenated_xcm()` avoiding the XCM re-encoding + - makes the benchmarks for `take_first_concatenated_xcm()` more granular, accounting for the number of bytes of the message +crates: +- name: cumulus-pallet-xcmp-queue + bump: major +- name: asset-hub-rococo-runtime + bump: patch +- name: asset-hub-westend-runtime + bump: patch +- name: bridge-hub-rococo-runtime + bump: patch +- name: bridge-hub-westend-runtime + bump: patch +- name: collectives-westend-runtime + bump: patch +- name: coretime-rococo-runtime + bump: patch +- name: coretime-westend-runtime + bump: patch +- name: people-rococo-runtime + bump: patch +- name: people-westend-runtime + bump: patch diff --git a/prdoc/pr_8838.prdoc b/prdoc/stable2506-1/pr_8838.prdoc similarity index 100% rename from prdoc/pr_8838.prdoc rename to prdoc/stable2506-1/pr_8838.prdoc diff --git a/prdoc/pr_8857.prdoc b/prdoc/stable2506-1/pr_8857.prdoc similarity index 100% rename from prdoc/pr_8857.prdoc rename to prdoc/stable2506-1/pr_8857.prdoc diff --git a/prdoc/pr_9179.prdoc b/prdoc/stable2506-1/pr_9179.prdoc similarity index 100% rename from prdoc/pr_9179.prdoc rename to prdoc/stable2506-1/pr_9179.prdoc diff --git a/prdoc/pr_9189.prdoc b/prdoc/stable2506-1/pr_9189.prdoc similarity index 100% rename from prdoc/pr_9189.prdoc rename to prdoc/stable2506-1/pr_9189.prdoc diff --git a/prdoc/pr_9195.prdoc b/prdoc/stable2506-1/pr_9195.prdoc similarity index 100% rename from prdoc/pr_9195.prdoc rename to prdoc/stable2506-1/pr_9195.prdoc diff --git a/prdoc/pr_9250.prdoc b/prdoc/stable2506-1/pr_9250.prdoc similarity index 100% rename from prdoc/pr_9250.prdoc rename to prdoc/stable2506-1/pr_9250.prdoc diff --git a/prdoc/pr_9281.prdoc b/prdoc/stable2506-1/pr_9281.prdoc similarity index 100% rename from prdoc/pr_9281.prdoc rename to prdoc/stable2506-1/pr_9281.prdoc diff --git a/prdoc/pr_9338.prdoc b/prdoc/stable2506-1/pr_9338.prdoc similarity index 100% rename from prdoc/pr_9338.prdoc rename to prdoc/stable2506-1/pr_9338.prdoc diff --git a/prdoc/pr_9354.prdoc b/prdoc/stable2506-1/pr_9354.prdoc similarity index 100% rename from prdoc/pr_9354.prdoc rename to prdoc/stable2506-1/pr_9354.prdoc diff --git a/prdoc/pr_9355.prdoc b/prdoc/stable2506-1/pr_9355.prdoc similarity index 100% rename from prdoc/pr_9355.prdoc rename to prdoc/stable2506-1/pr_9355.prdoc diff --git a/prdoc/pr_9445.prdoc b/prdoc/stable2506-1/pr_9445.prdoc similarity index 100% rename from prdoc/pr_9445.prdoc rename to prdoc/stable2506-1/pr_9445.prdoc diff --git a/prdoc/pr_9489.prdoc b/prdoc/stable2506-1/pr_9489.prdoc similarity index 100% rename from prdoc/pr_9489.prdoc rename to prdoc/stable2506-1/pr_9489.prdoc diff --git a/substrate/bin/utils/chain-spec-builder/README.docify.md b/substrate/bin/utils/chain-spec-builder/README.docify.md index 091814bdc8043..1b0f78d278c55 100644 --- a/substrate/bin/utils/chain-spec-builder/README.docify.md +++ b/substrate/bin/utils/chain-spec-builder/README.docify.md @@ -26,18 +26,19 @@ _Note:_ `chain-spec-builder` binary is published on [crates.io](https://crates.i Please note that below usage is backed by integration tests. The commands' examples are wrapped around by the `bash!(...)` macro calls. - -### Deprecation notice for `CreateCmd`'s `para-id` flag +### Note for `CreateCmd`'s `para-id` flag -`para-id` flag is deprecated. Runtimes relying on generating the chain -specification with this tool should implement `cumulus_primitives_core::GetParachainInfo` -trait, a new runtime API designed to provide the parachain ID from the `parachain-info` -pallet. The `para-id` flag will be removed and nodes support for extracting the -parachain id from the chain specification will stop from `stable2512`. - -For reference, generating a chain specification with a `para_id` field can still -be done until `stable2512` like below: +Runtimes relying on generating the chain specification with this tool should +implement `cumulus_primitives_core::GetParachainInfo` trait, a new runtime API +designed to provide the parachain ID from the `parachain-info` +pallet. The `para-id` flag can be used though if the runtime does not implement +the runtime API, and the parachain id will be fetched by the node from chain +specification. This can be especially useful when syncing a node from a state +where the runtime does not implement `cumulus_primitives_core::GetParachainInfo`. + +For reference, generating a chain specification with a `para_id` field can be +done like below: ```bash chain-spec-builder -c "/dev/stdout" create --relay-chain "dev" --para-id 1000 -r $runtime_path named-preset "staging" diff --git a/substrate/bin/utils/chain-spec-builder/README.md b/substrate/bin/utils/chain-spec-builder/README.md index 509b0fe03bee4..31e8430776497 100644 --- a/substrate/bin/utils/chain-spec-builder/README.md +++ b/substrate/bin/utils/chain-spec-builder/README.md @@ -26,18 +26,19 @@ _Note:_ `chain-spec-builder` binary is published on [crates.io](https://crates.i Please note that below usage is backed by integration tests. The commands' examples are wrapped around by the `bash!(...)` macro calls. - -### Deprecation notice for `CreateCmd`'s `para-id` flag +### Note for `CreateCmd`'s `para-id` flag -`para-id` flag is deprecated. Runtimes relying on generating the chain -specification with this tool should implement `cumulus_primitives_core::GetParachainInfo` -trait, a new runtime API designed to provide the parachain ID from the `parachain-info` -pallet. The `para-id` flag will be removed and nodes support for extracting the -parachain id from the chain specification will stop from `stable2512`. - -For reference, generating a chain specification with a `para_id` field can still -be done until `stable2512` like below: +Runtimes relying on generating the chain specification with this tool should +implement `cumulus_primitives_core::GetParachainInfo` trait, a new runtime API +designed to provide the parachain ID from the `parachain-info` +pallet. The `para-id` flag can be used though if the runtime does not implement +the runtime API, and the parachain id will be fetched by the node from chain +specification. This can be especially useful when syncing a node from a state +where the runtime does not implement `cumulus_primitives_core::GetParachainInfo`. + +For reference, generating a chain specification with a `para_id` field can be +done like below: ```bash chain-spec-builder -c "/dev/stdout" create --relay-chain "dev" --para-id 1000 -r $runtime_path named-preset "staging" diff --git a/substrate/bin/utils/chain-spec-builder/src/lib.rs b/substrate/bin/utils/chain-spec-builder/src/lib.rs index 69986aea80737..116f90d31931e 100644 --- a/substrate/bin/utils/chain-spec-builder/src/lib.rs +++ b/substrate/bin/utils/chain-spec-builder/src/lib.rs @@ -67,17 +67,8 @@ pub struct CreateCmd { /// The chain type. #[arg(value_enum, short = 't', default_value = "live")] chain_type: ChainType, - /// DEPRECATED: The para ID for your chain. - /// - /// This flag will be removed starting with `stable2512`. Runtimes must implement a new API - /// called `cumulus_primitives_core::GetParachainInfo` to still be compatible with node - /// versions starting with `stable2512`. - // TODO: https://github.com/paritytech/polkadot-sdk/issues/8747 - // TODO: https://github.com/paritytech/polkadot-sdk/issues/8740 + /// The para ID for your chain. #[arg(long, value_enum, short = 'p', requires = "relay_chain")] - #[deprecated( - note = "The para_id information is not required anymore and will be removed starting with `stable2512`. Runtimes must implement a new API called `cumulus_primitives_core::GetParachainInfo` to still be compatible with node versions starting with `stable2512`." - )] pub para_id: Option, /// The relay chain you wish to connect to. #[arg(long, value_enum, short = 'c')] @@ -226,11 +217,6 @@ pub struct ParachainExtension { /// The relay chain of the Parachain. pub relay_chain: String, /// The id of the Parachain. - // TODO: https://github.com/paritytech/polkadot-sdk/issues/8747 --> - // TODO: https://github.com/paritytech/polkadot-sdk/issues/8740 --> - #[deprecated( - note = "The para_id information is not required anymore and will be removed starting with `stable2512`. Runtimes must implement a new API called `cumulus_primitives_core::GetParachainInfo` to still be compatible with node versions starting with `stable2512`." - )] pub para_id: Option, } @@ -458,12 +444,8 @@ pub fn generate_chain_spec_for_runtime(cmd: &CreateCmd) -> Result - eprintln!("Note: usage of deprecated `para-id` flag is not recommended. Please consider implementing the `cumulus_primitives_core::GetParachainInfo` runtime API for your runtime. The `para-id` flag will be removed starting with `stable2512`."); serde_json::json!({ "relay_chain": rc, "para_id": para_id, diff --git a/substrate/frame/babe/Cargo.toml b/substrate/frame/babe/Cargo.toml index 0fa83b391145c..ca7d79e4d4ebf 100644 --- a/substrate/frame/babe/Cargo.toml +++ b/substrate/frame/babe/Cargo.toml @@ -73,6 +73,7 @@ runtime-benchmarks = [ "frame-system/runtime-benchmarks", "pallet-balances/runtime-benchmarks", "pallet-offences/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "sp-runtime/runtime-benchmarks", diff --git a/substrate/frame/beefy-mmr/Cargo.toml b/substrate/frame/beefy-mmr/Cargo.toml index 6adf5bcd871f5..c87b723f7cf7b 100644 --- a/substrate/frame/beefy-mmr/Cargo.toml +++ b/substrate/frame/beefy-mmr/Cargo.toml @@ -75,6 +75,7 @@ runtime-benchmarks = [ "frame-system/runtime-benchmarks", "pallet-balances/runtime-benchmarks", "pallet-mmr/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "sp-runtime/runtime-benchmarks", "sp-staking/runtime-benchmarks", ] diff --git a/substrate/frame/election-provider-multi-block/src/signed/mod.rs b/substrate/frame/election-provider-multi-block/src/signed/mod.rs index 9784cf75a5765..1aa0dadb2d452 100644 --- a/substrate/frame/election-provider-multi-block/src/signed/mod.rs +++ b/substrate/frame/election-provider-multi-block/src/signed/mod.rs @@ -452,13 +452,13 @@ pub mod pallet { ) -> Result { let mut sorted_scores = SortedScores::::get(round); - let discarded = if let Some(_) = sorted_scores.iter().position(|(x, _)| x == who) { + let did_eject = if let Some(_) = sorted_scores.iter().position(|(x, _)| x == who) { return Err(Error::::Duplicate.into()); } else { // must be new. debug_assert!(!SubmissionMetadataStorage::::contains_key(round, who)); - let pos = match sorted_scores + let insert_idx = match sorted_scores .binary_search_by_key(&metadata.claimed_score, |(_, y)| *y) { // an equal score exists, unlikely, but could very well happen. We just put them @@ -468,10 +468,23 @@ pub mod pallet { Err(pos) => pos, }; - let record = (who.clone(), metadata.claimed_score); - match sorted_scores.force_insert_keep_right(pos, record) { - Ok(None) => false, - Ok(Some((discarded, _score))) => { + let mut record = (who.clone(), metadata.claimed_score); + if sorted_scores.is_full() { + let remove_idx = sorted_scores + .iter() + .position(|(x, _)| !Pallet::::is_invulnerable(x)) + .ok_or(Error::::QueueFull)?; + if insert_idx > remove_idx { + // we have a better solution + sp_std::mem::swap(&mut sorted_scores[remove_idx], &mut record); + // slicing safety note: + // - `insert_idx` is at most `sorted_scores.len()`, obtained from + // `binary_search_by_key`, valid for the upper bound of slicing. + // - `remove_idx` is a valid index, less then `insert_idx`, obtained from + // `.iter().position()` + sorted_scores[remove_idx..insert_idx].rotate_left(1); + + let discarded = record.0; let maybe_metadata = SubmissionMetadataStorage::::take(round, &discarded).defensive(); // Note: safe to remove unbounded, as at most `Pages` pages are stored. @@ -486,24 +499,27 @@ pub mod pallet { Pallet::::settle_deposit( &discarded, metadata.deposit, - if Pallet::::is_invulnerable(&discarded) { - One::one() - } else { - T::EjectGraceRatio::get() - }, + T::EjectGraceRatio::get(), ); } Pallet::::deposit_event(Event::::Ejected(round, discarded)); true - }, - Err(_) => return Err(Error::::QueueFull.into()), + } else { + // we don't have a better solution + return Err(Error::::QueueFull.into()) + } + } else { + sorted_scores + .try_insert(insert_idx, record) + .expect("length checked above; qed"); + false } }; SortedScores::::insert(round, sorted_scores); SubmissionMetadataStorage::::insert(round, who, metadata); - Ok(discarded) + Ok(did_eject) } /// Submit a page of `solution` to the `page` index of `who`'s submission. @@ -1020,6 +1036,7 @@ impl Pallet { ); debug_assert_eq!(_res, Ok(slash)); Self::deposit_event(Event::::Slashed(current_round, loser.clone(), slash)); + Invulnerables::::mutate(|x| x.retain(|y| y != &loser)); // Try to start verification again if we still have submissions if let crate::types::Phase::SignedValidation(remaining_blocks) = diff --git a/substrate/frame/election-provider-multi-block/src/signed/tests.rs b/substrate/frame/election-provider-multi-block/src/signed/tests.rs index cbd64adf84c7d..085cec58935c4 100644 --- a/substrate/frame/election-provider-multi-block/src/signed/tests.rs +++ b/substrate/frame/election-provider-multi-block/src/signed/tests.rs @@ -29,6 +29,10 @@ use sp_npos_elections::ElectionScore; pub type T = Runtime; +fn score_from(x: u128) -> ElectionScore { + ElectionScore { minimal_stake: x, ..Default::default() } +} + mod calls { use super::*; use sp_runtime::{DispatchError, TokenError::FundsUnavailable}; @@ -213,13 +217,11 @@ mod calls { } #[test] - fn metadata_submission_sorted_based_on_stake() { + fn metadata_submission_sorted_based_on_score() { ExtBuilder::signed().build_and_execute(|| { roll_to_signed_open(); assert_full_snapshot(); - let score_from = |x| ElectionScore { minimal_stake: x, ..Default::default() }; - assert_ok!(SignedPallet::register(RuntimeOrigin::signed(91), score_from(100))); assert_eq!(*Submissions::::leaderboard(0), vec![(91, score_from(100))]); assert_eq!(balances(91), (95, 5)); @@ -1259,6 +1261,8 @@ mod e2e { } mod invulnerables { + use frame_support::hypothetically; + use super::*; fn make_invulnerable(who: AccountId) { @@ -1395,73 +1399,102 @@ mod invulnerables { } #[test] - fn ejected_invulnerable_gets_deposit_back() { - ExtBuilder::signed().max_signed_submissions(2).build_and_execute(|| { + fn invulnerable_cannot_eject_first() { + ExtBuilder::signed().max_signed_submissions(3).build_and_execute(|| { roll_to_signed_open(); assert_full_snapshot(); make_invulnerable(99); - // by default, we pay back 20% of the discarded deposit back + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(99), score_from(100))); + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(98), score_from(150))); + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(97), score_from(200))); + assert_eq!( - ::EjectGraceRatio::get(), - Perbill::from_percent(20) + Submissions::::leaderboard(0), + vec![(99, score_from(100)), (98, score_from(150)), (97, score_from(200))] ); - // submit 99 as invulnerable - assert_ok!(SignedPallet::register( - RuntimeOrigin::signed(99), - ElectionScore { minimal_stake: 100, ..Default::default() } - )); - assert!(matches!( - Submissions::::metadata_of(0, 99).unwrap(), - SubmissionMetadata { deposit: 7, .. } - )); + // inserting someone who would eject 99 won't work. + assert_noop!( + SignedPallet::register(RuntimeOrigin::signed(96), score_from(100)), + Error::::QueueFull, + ); + // inserting someone who would eject 98 will work. + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(96), score_from(155))); + assert_eq!( + Submissions::::leaderboard(0), + vec![(99, score_from(100)), (96, score_from(155)), (97, score_from(200))] + ); + }) + } - // submit 98 as normal - assert_ok!(SignedPallet::register( - RuntimeOrigin::signed(98), - ElectionScore { minimal_stake: 101, ..Default::default() } - )); - assert!(matches!( - Submissions::::metadata_of(0, 98).unwrap(), - SubmissionMetadata { deposit: 5, .. } - )); - let _ = signed_events_since_last_call(); - assert_eq!(balances(99), (93, 7)); - assert_eq!(balances(98), (95, 5)); + #[test] + fn invulnerable_cannot_eject_middle() { + ExtBuilder::signed().max_signed_submissions(3).build_and_execute(|| { + roll_to_signed_open(); + assert_full_snapshot(); + make_invulnerable(99); - // submit 97 and 96 with higher scores, eject both of the previous ones - assert_ok!(SignedPallet::register( - RuntimeOrigin::signed(97), - ElectionScore { minimal_stake: 200, ..Default::default() } - )); - assert_ok!(SignedPallet::register( - RuntimeOrigin::signed(96), - ElectionScore { minimal_stake: 201, ..Default::default() } - )); + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(99), score_from(150))); + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(98), score_from(100))); + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(97), score_from(200))); assert_eq!( - signed_events_since_last_call(), - vec![ - Event::Ejected(0, 99), - Event::Registered( - 0, - 97, - ElectionScore { minimal_stake: 200, sum_stake: 0, sum_stake_squared: 0 } - ), - Event::Ejected(0, 98), - Event::Registered( - 0, - 96, - ElectionScore { minimal_stake: 201, sum_stake: 0, sum_stake_squared: 0 } - ) - ] + Submissions::::leaderboard(0), + vec![(98, score_from(100)), (99, score_from(150)), (97, score_from(200))] ); - // 99 gets everything back - assert_eq!(balances(99), (100, 0)); - // 98 gets 20% x 5 = 1 back - assert_eq!(balances(98), (96, 0)); + // worse than all + assert_noop!( + SignedPallet::register(RuntimeOrigin::signed(96), score_from(50)), + Error::::QueueFull, + ); + + // better than our first item + hypothetically!({ + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(96), score_from(125))); + assert_eq!( + Submissions::::leaderboard(0), + vec![(96, score_from(125)), (99, score_from(150)), (97, score_from(200))] + ); + }); + + // better than inv + hypothetically!({ + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(96), score_from(175))); + assert_eq!( + Submissions::::leaderboard(0), + vec![(99, score_from(150)), (96, score_from(175)), (97, score_from(200))] + ); + }); + + // better than all + hypothetically!({ + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(96), score_from(225))); + assert_eq!( + Submissions::::leaderboard(0), + vec![(99, score_from(150)), (97, score_from(200)), (96, score_from(225))] + ); + }); + }) + } + + #[test] + fn all_invulnerables() { + ExtBuilder::signed().max_signed_submissions(3).build_and_execute(|| { + roll_to_signed_open(); + assert_full_snapshot(); + assert_ok!(SignedPallet::set_invulnerables(RuntimeOrigin::root(), vec![99, 98, 97])); + + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(99), score_from(150))); + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(98), score_from(100))); + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(97), score_from(200))); + + // Nothing can touch our boys now. + assert_noop!( + SignedPallet::register(RuntimeOrigin::signed(96), score_from(1000)), + Error::::QueueFull, + ); }) } @@ -1559,6 +1592,48 @@ mod invulnerables { assert_eq!(new_deposit, 5); // Should not be fixed deposit anymore }); } + + #[test] + fn slashed_invulnerable_is_expelled() { + ExtBuilder::signed().build_and_execute(|| { + roll_to_signed_open(); + assert_full_snapshot(); + make_invulnerable(99); + assert!(Invulnerables::::get().contains(&99)); + + let invalid_score = score_from(777); + assert_ok!(SignedPallet::register(RuntimeOrigin::signed(99), invalid_score)); + + roll_to_signed_validation_open(); + roll_next(); // one block so signed pallet will send start signal. + roll_to_full_verification(); + + // Check that rejection events were properly generated + assert_eq!( + verifier_events_since_last_call(), + vec![ + crate::verifier::Event::Verified(2, 0), // empty page + crate::verifier::Event::Verified(1, 0), // empty page + crate::verifier::Event::Verified(0, 0), // empty page + crate::verifier::Event::VerificationFailed(0, FeasibilityError::InvalidScore), + ] + ); + + // Check that expected events were emitted for the rejection + assert_eq!( + signed_events(), + vec![Event::Registered(0, 99, invalid_score), Event::Slashed(0, 99, 7)] /* slash + * amount + * is indeed + * the invulnerable + * deposit + * (7) ^^^^ */ + ); + + // Verify invulnerable is expelled + assert!(!Invulnerables::::get().contains(&99)); + }); + } } mod defensive_tests { diff --git a/substrate/frame/grandpa/Cargo.toml b/substrate/frame/grandpa/Cargo.toml index 8fe651de43d99..6215d29c5e749 100644 --- a/substrate/frame/grandpa/Cargo.toml +++ b/substrate/frame/grandpa/Cargo.toml @@ -75,6 +75,7 @@ runtime-benchmarks = [ "frame-system/runtime-benchmarks", "pallet-balances/runtime-benchmarks", "pallet-offences/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "sp-runtime/runtime-benchmarks", diff --git a/substrate/frame/im-online/Cargo.toml b/substrate/frame/im-online/Cargo.toml index f00260feac914..d459646e9ee76 100644 --- a/substrate/frame/im-online/Cargo.toml +++ b/substrate/frame/im-online/Cargo.toml @@ -56,6 +56,7 @@ runtime-benchmarks = [ "frame-support/runtime-benchmarks", "frame-system/runtime-benchmarks", "pallet-balances/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "sp-runtime/runtime-benchmarks", "sp-staking/runtime-benchmarks", ] diff --git a/substrate/frame/offences/benchmarking/Cargo.toml b/substrate/frame/offences/benchmarking/Cargo.toml index 27fc5101eff63..fe1b233f66f45 100644 --- a/substrate/frame/offences/benchmarking/Cargo.toml +++ b/substrate/frame/offences/benchmarking/Cargo.toml @@ -73,6 +73,7 @@ runtime-benchmarks = [ "pallet-grandpa/runtime-benchmarks", "pallet-im-online/runtime-benchmarks", "pallet-offences/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "sp-runtime/runtime-benchmarks", diff --git a/substrate/frame/offences/benchmarking/src/inner.rs b/substrate/frame/offences/benchmarking/src/inner.rs index 91c30061957d4..31c99800ae3ed 100644 --- a/substrate/frame/offences/benchmarking/src/inner.rs +++ b/substrate/frame/offences/benchmarking/src/inner.rs @@ -112,6 +112,7 @@ fn create_offender(n: u32, nominators: u32) -> Result, &' ::Keys::decode(&mut sp_runtime::traits::TrailingZeroInput::zeroes()) .unwrap(); let proof: Vec = vec![0, 1, 2, 3]; + Session::::ensure_can_pay_key_deposit(&stash)?; Session::::set_keys(RawOrigin::Signed(stash.clone()).into(), keys, proof)?; let mut individual_exposures = vec![]; diff --git a/substrate/frame/revive/Cargo.toml b/substrate/frame/revive/Cargo.toml index a2be0cd34f862..6a2078dd50c43 100644 --- a/substrate/frame/revive/Cargo.toml +++ b/substrate/frame/revive/Cargo.toml @@ -35,6 +35,7 @@ polkavm = { version = "0.27.0", default-features = false } polkavm-common = { version = "0.27.0", default-features = false, features = ["alloc"] } rand = { workspace = true, optional = true } rand_pcg = { workspace = true, optional = true } +revm = { workspace = true } rlp = { workspace = true } scale-info = { features = ["derive"], workspace = true } serde = { features = ["alloc", "derive"], workspace = true, default-features = false } @@ -98,6 +99,7 @@ std = [ "polkavm-common/std", "polkavm/std", "rand?/std", + "revm/std", "ripemd/std", "rlp/std", "scale-info/std", diff --git a/substrate/frame/revive/fixtures/Cargo.toml b/substrate/frame/revive/fixtures/Cargo.toml index f1a4d7d1969f5..820a9b7952a55 100644 --- a/substrate/frame/revive/fixtures/Cargo.toml +++ b/substrate/frame/revive/fixtures/Cargo.toml @@ -16,6 +16,7 @@ exclude-from-umbrella = true workspace = true [dependencies] +alloy-core = { workspace = true, default-features = true, features = ["sol-types"], optional = true } anyhow = { workspace = true, default-features = true, optional = true } sp-core = { workspace = true, default-features = true, optional = true } sp-io = { workspace = true, default-features = true, optional = true } @@ -23,11 +24,20 @@ sp-io = { workspace = true, default-features = true, optional = true } [build-dependencies] anyhow = { workspace = true, default-features = true } cargo_metadata = { workspace = true } +hex = { workspace = true, features = ["alloc"] } pallet-revive-uapi = { workspace = true } polkavm-linker = { version = "0.27.0" } +serde_json = { workspace = true } toml = { workspace = true } [features] default = ["std"] # only when std is enabled all fixtures are available -std = ["anyhow", "sp-core", "sp-io"] +std = [ + "alloy-core", + "anyhow", + "hex/std", + "serde_json/std", + "sp-core", + "sp-io", +] diff --git a/substrate/frame/revive/fixtures/build.rs b/substrate/frame/revive/fixtures/build.rs index ce9215a165d21..a3030a66afad0 100644 --- a/substrate/frame/revive/fixtures/build.rs +++ b/substrate/frame/revive/fixtures/build.rs @@ -30,15 +30,24 @@ const OVERRIDE_STRIP_ENV_VAR: &str = "PALLET_REVIVE_FIXTURES_STRIP"; const OVERRIDE_OPTIMIZE_ENV_VAR: &str = "PALLET_REVIVE_FIXTURES_OPTIMIZE"; /// A contract entry. +#[derive(Clone)] struct Entry { /// The path to the contract source file. path: PathBuf, + /// The type of the contract (rust or solidity). + contract_type: ContractType, +} + +#[derive(Clone, Copy)] +enum ContractType { + Rust, + Solidity, } impl Entry { /// Create a new contract entry from the given path. - fn new(path: PathBuf) -> Self { - Self { path } + fn new(path: PathBuf, contract_type: ContractType) -> Self { + Self { path, contract_type } } /// Return the path to the contract source file. @@ -55,9 +64,12 @@ impl Entry { .expect("name is valid unicode; qed") } - /// Return the name of the polkavm file. + /// Return the name of the bytecode file. fn out_filename(&self) -> String { - format!("{}.polkavm", self.name()) + match self.contract_type { + ContractType::Rust => format!("{}.polkavm", self.name()), + ContractType::Solidity => format!("{}.resolc.polkavm", self.name()), + } } } @@ -67,16 +79,18 @@ fn collect_entries(contracts_dir: &Path) -> Vec { .expect("src dir exists; qed") .filter_map(|file| { let path = file.expect("file exists; qed").path(); - if path.extension().map_or(true, |ext| ext != "rs") { - return None - } + let extension = path.extension(); - Some(Entry::new(path)) + match extension.and_then(|ext| ext.to_str()) { + Some("rs") => Some(Entry::new(path, ContractType::Rust)), + Some("sol") => Some(Entry::new(path, ContractType::Solidity)), + _ => None, + } }) .collect::>() } -/// Create a `Cargo.toml` to compile the given contract entries. +/// Create a `Cargo.toml` to compile the given Rust contract entries. fn create_cargo_toml<'a>( fixtures_dir: &Path, entries: impl Iterator, @@ -168,7 +182,7 @@ fn invoke_build(current_dir: &Path) -> Result<()> { let build_res = build_command.output().expect("failed to execute process"); if build_res.status.success() { - return Ok(()) + return Ok(()); } let stderr = String::from_utf8_lossy(&build_res.stderr); @@ -192,15 +206,166 @@ fn post_process(input_path: &Path, output_path: &Path) -> Result<()> { Ok(()) } -/// Write the compiled contracts to the given output directory. +/// Compile a Solidity contract using standard JSON interface. +fn compile_with_standard_json( + compiler: &str, + contracts_dir: &Path, + solidity_entries: &[&Entry], +) -> Result { + let mut input_json = serde_json::json!({ + "language": "Solidity", + "sources": {}, + "settings": { + "optimizer": { + "enabled": true, + "runs": 200 + }, + "outputSelection": + + serde_json::json!({ + "*": { + "*": ["evm.bytecode"] + } + }), + + } + }); + + // Add all Solidity files to the input + for entry in solidity_entries { + let source_code = fs::read_to_string(entry.path()) + .with_context(|| format!("Failed to read Solidity source: {}", entry.path()))?; + + let file_key = entry.path().split('/').last().unwrap_or(entry.name()); + input_json["sources"][file_key] = serde_json::json!({ + "content": source_code + }); + } + + let compiler_output = Command::new(compiler) + .current_dir(contracts_dir) + .arg("--standard-json") + .stdin(std::process::Stdio::piped()) + .stdout(std::process::Stdio::piped()) + .stderr(std::process::Stdio::piped()) + .spawn() + .with_context(|| { + format!("Failed to execute {}. Make sure {} is installed.", compiler, compiler) + })?; + + let mut stdin = compiler_output.stdin.as_ref().unwrap(); + stdin + .write_all(input_json.to_string().as_bytes()) + .with_context(|| format!("Failed to write to {} stdin", compiler))?; + let _ = stdin; + + let compiler_result = compiler_output + .wait_with_output() + .with_context(|| format!("Failed to wait for {} output", compiler))?; + + if !compiler_result.status.success() { + let stderr = String::from_utf8_lossy(&compiler_result.stderr); + bail!("{} compilation failed: {}", compiler, stderr); + } + + // Parse JSON output + let compiler_json: serde_json::Value = serde_json::from_slice(&compiler_result.stdout) + .with_context(|| format!("Failed to parse {} JSON output", compiler))?; + + // Abort on errors + if let Some(errors) = compiler_json.get("errors") { + if errors + .as_array() + .unwrap() + .iter() + .any(|object| object.get("severity").unwrap().as_str().unwrap() == "error") + { + bail!( + "failed to compile the Solidity fixtures: {}", + serde_json::to_string_pretty(errors)? + ); + } + } + + Ok(compiler_json) +} + +/// Extract bytecode from compiler JSON output and write binary files. +fn extract_and_write_bytecode( + compiler_json: &serde_json::Value, + out_dir: &Path, + file_suffix: &str, +) -> Result<()> { + if let Some(contracts) = compiler_json["contracts"].as_object() { + for (_file_key, file_contracts) in contracts { + if let Some(contract_map) = file_contracts.as_object() { + for (contract_name, contract_data) in contract_map { + // Navigate through the JSON path to find the bytecode + let mut current = contract_data; + for path_segment in ["evm", "bytecode", "object"] { + if let Some(next) = current.get(path_segment) { + current = next; + } else { + // Skip if path doesn't exist (e.g., contract has no bytecode) + continue; + } + } + + if let Some(bytecode_obj) = current.as_str() { + let bytecode_hex = bytecode_obj.strip_prefix("0x").unwrap_or(bytecode_obj); + let binary_content = hex::decode(bytecode_hex).map_err(|e| { + anyhow::anyhow!("Failed to decode hex for {contract_name}: {e}") + })?; + + let out_path = out_dir.join(format!("{}{}", contract_name, file_suffix)); + fs::write(&out_path, binary_content).with_context(|| { + format!("Failed to write {out_path:?} for {contract_name}") + })?; + } + } + } + } + } + Ok(()) +} + +/// Compile Solidity contracts using both solc and resolc. +fn compile_solidity_contracts( + contracts_dir: &Path, + out_dir: &Path, + entries: &[Entry], +) -> Result<()> { + let solidity_entries: Vec<_> = entries + .iter() + .filter(|entry| matches!(entry.contract_type, ContractType::Solidity)) + .collect(); + + if solidity_entries.is_empty() { + return Ok(()); + } + + // Compile with solc for EVM bytecode + let json = compile_with_standard_json("solc", contracts_dir, &solidity_entries)?; + extract_and_write_bytecode(&json, out_dir, ".sol.bin")?; + + // Compile with resolc for PVM bytecode + let json = compile_with_standard_json("resolc", contracts_dir, &solidity_entries)?; + extract_and_write_bytecode(&json, out_dir, ".resolc.polkavm")?; + + Ok(()) +} + +/// Write the compiled Rust contracts to the given output directory. fn write_output(build_dir: &Path, out_dir: &Path, entries: Vec) -> Result<()> { for entry in entries { - post_process( - &build_dir - .join("target/riscv64emac-unknown-none-polkavm/release") - .join(entry.name()), - &out_dir.join(entry.out_filename()), - )?; + if matches!(entry.contract_type, ContractType::Rust) { + post_process( + &build_dir + .join("target/riscv64emac-unknown-none-polkavm/release") + .join(entry.name()), + &out_dir.join(entry.out_filename()), + )?; + } } Ok(()) @@ -211,7 +376,7 @@ fn create_out_dir() -> Result { let temp_dir: PathBuf = env::var("OUT_DIR").context("Failed to fetch `OUT_DIR` env variable")?.into(); - // this is set in case the user has overriden the target directory + // this is set in case the user has overridden the target directory let out_dir = if let Ok(path) = env::var("CARGO_TARGET_DIR") { let path = PathBuf::from(path); @@ -263,25 +428,46 @@ fn create_out_dir() -> Result { .context(format!("Failed to create output directory: {})", out_dir.display(),))?; } - // write the location of the out dir so it can be found later + Ok(out_dir) +} + +/// Generate the fixture_location.rs file with macros and sol! definitions. +fn generate_fixture_location(temp_dir: &Path, out_dir: &Path, entries: &[Entry]) -> Result<()> { let mut file = fs::File::create(temp_dir.join("fixture_location.rs")) .context("Failed to create fixture_location.rs")?; + write!( file, r#" #[allow(dead_code)] const FIXTURE_DIR: &str = "{0}"; + + #[macro_export] macro_rules! fixture {{ ($name: literal) => {{ include_bytes!(concat!("{0}", "/", $name, ".polkavm")) }}; }} + + #[macro_export] + macro_rules! fixture_resolc {{ + ($name: literal) => {{ + include_bytes!(concat!("{0}", "/", $name, ".resolc.polkavm")) + }}; + }} "#, out_dir.display() ) .context("Failed to write to fixture_location.rs")?; - Ok(out_dir) + // Generate sol! macros for Solidity contracts + for entry in entries.iter().filter(|e| matches!(e.contract_type, ContractType::Solidity)) { + let relative_path = format!("contracts/{}", entry.path().split('/').last().unwrap()); + writeln!(file, r#"alloy_core::sol!("{}");"#, relative_path) + .context("Failed to write sol! macro to fixture_location.rs")?; + } + + Ok(()) } pub fn main() -> Result<()> { @@ -305,12 +491,28 @@ pub fn main() -> Result<()> { let entries = collect_entries(&contracts_dir); if entries.is_empty() { - return Ok(()) + return Ok(()); } - create_cargo_toml(&fixtures_dir, entries.iter(), &build_dir)?; - invoke_build(&build_dir)?; - write_output(&build_dir, &out_dir, entries)?; + // Compile Rust contracts + let rust_entries: Vec<_> = entries + .iter() + .filter(|e| matches!(e.contract_type, ContractType::Rust)) + .collect(); + if !rust_entries.is_empty() { + create_cargo_toml(&fixtures_dir, rust_entries.into_iter(), &build_dir)?; + invoke_build(&build_dir)?; + write_output(&build_dir, &out_dir, entries.clone())?; + } + + // Compile Solidity contracts + compile_solidity_contracts(&contracts_dir, &out_dir, &entries)?; + + let temp_dir: PathBuf = + env::var("OUT_DIR").context("Failed to fetch `OUT_DIR` env variable")?.into(); + + // Generate fixture_location.rs with sol! macros + generate_fixture_location(&temp_dir, &out_dir, &entries)?; Ok(()) } diff --git a/substrate/frame/revive/fixtures/contracts/dummy.polkavm b/substrate/frame/revive/fixtures/contracts/dummy.polkavm deleted file mode 100644 index d970e700ce564..0000000000000 Binary files a/substrate/frame/revive/fixtures/contracts/dummy.polkavm and /dev/null differ diff --git a/substrate/frame/revive/fixtures/contracts/dummy.sol b/substrate/frame/revive/fixtures/contracts/dummy.sol deleted file mode 100644 index e64031b0e0210..0000000000000 --- a/substrate/frame/revive/fixtures/contracts/dummy.sol +++ /dev/null @@ -1,14 +0,0 @@ -// SPDX-License-Identifier: UNLICENSED -pragma solidity >=0.8.2 <0.9.0; - -contract Simple { - uint256 number; - - function store(uint256 num) public { - number = num; - } - - function retrieve() public view returns (uint256) { - return number; - } -} \ No newline at end of file diff --git a/substrate/frame/revive/fixtures/contracts/fake_erc20.sol b/substrate/frame/revive/fixtures/contracts/fake_erc20.sol deleted file mode 100644 index 1c6d0aca5c8c2..0000000000000 --- a/substrate/frame/revive/fixtures/contracts/fake_erc20.sol +++ /dev/null @@ -1,54 +0,0 @@ -// SPDX-License-Identifier: MIT -pragma solidity ^0.8.20; - -contract MyToken { - mapping(address account => uint256) private _balances; - - uint256 private _totalSupply; - - constructor(uint256 total) { - // We mint `total` tokens to the creator of this contract, as - // a sort of genesis. - _mint(msg.sender, total); - } - - function transfer(address to, uint256 value) public virtual returns (uint256) { - address owner = msg.sender; - _transfer(owner, to, value); - return 1243657816489523; - } - - function _transfer(address from, address to, uint256 value) internal { - _update(from, to, value); - } - - function _update(address from, address to, uint256 value) internal virtual { - if (from == address(0)) { - // Overflow check required: The rest of the code assumes that totalSupply never overflows - _totalSupply += value; - } else { - uint256 fromBalance = _balances[from]; - unchecked { - // Overflow not possible: value <= fromBalance <= totalSupply. - _balances[from] = fromBalance - value; - } - } - - if (to == address(0)) { - unchecked { - // Overflow not possible: value <= totalSupply or value <= fromBalance <= totalSupply. - _totalSupply -= value; - } - } else { - unchecked { - // Overflow not possible: balance + value is at most totalSupply, which we know fits into a uint256. - _balances[to] += value; - } - } - } - - function _mint(address account, uint256 value) internal { - _update(address(0), account, value); - } -} - diff --git a/substrate/frame/revive/fixtures/contracts/erc20.polkavm b/substrate/frame/revive/fixtures/erc20/erc20.polkavm similarity index 100% rename from substrate/frame/revive/fixtures/contracts/erc20.polkavm rename to substrate/frame/revive/fixtures/erc20/erc20.polkavm diff --git a/substrate/frame/revive/fixtures/contracts/erc20.sol b/substrate/frame/revive/fixtures/erc20/erc20.sol similarity index 100% rename from substrate/frame/revive/fixtures/contracts/erc20.sol rename to substrate/frame/revive/fixtures/erc20/erc20.sol diff --git a/substrate/frame/revive/fixtures/contracts/expensive_erc20.polkavm b/substrate/frame/revive/fixtures/erc20/expensive_erc20.polkavm similarity index 100% rename from substrate/frame/revive/fixtures/contracts/expensive_erc20.polkavm rename to substrate/frame/revive/fixtures/erc20/expensive_erc20.polkavm diff --git a/substrate/frame/revive/fixtures/contracts/expensive_erc20.sol b/substrate/frame/revive/fixtures/erc20/expensive_erc20.sol similarity index 100% rename from substrate/frame/revive/fixtures/contracts/expensive_erc20.sol rename to substrate/frame/revive/fixtures/erc20/expensive_erc20.sol diff --git a/substrate/frame/revive/fixtures/contracts/fake_erc20.polkavm b/substrate/frame/revive/fixtures/erc20/fake_erc20.polkavm similarity index 100% rename from substrate/frame/revive/fixtures/contracts/fake_erc20.polkavm rename to substrate/frame/revive/fixtures/erc20/fake_erc20.polkavm diff --git a/substrate/frame/revive/fixtures/src/lib.rs b/substrate/frame/revive/fixtures/src/lib.rs index 8d6a8236cd742..022dcb9b43f09 100644 --- a/substrate/frame/revive/fixtures/src/lib.rs +++ b/substrate/frame/revive/fixtures/src/lib.rs @@ -22,16 +22,47 @@ extern crate alloc; // generated file that tells us where to find the fixtures include!(concat!(env!("OUT_DIR"), "/fixture_location.rs")); -/// Load a given polkavm module and returns a polkavm binary contents along with its hash. +/// Enum for different fixture types +#[derive(Debug, Clone, Copy, PartialEq, Eq)] +pub enum FixtureType { + /// Polkavm (compiled Rust contracts) + Rust, + /// Resolc (compiled Solidity contracts to Polkavm) + Resolc, + /// Solc (compiled Solidity contracts to EVM bytecode) + Solc, +} + #[cfg(feature = "std")] -pub fn compile_module(fixture_name: &str) -> anyhow::Result<(Vec, sp_core::H256)> { +impl FixtureType { + fn file_extension(&self) -> &'static str { + match self { + Self::Rust => ".polkavm", + Self::Resolc => ".resolc.polkavm", + Self::Solc => ".sol.bin", + } + } +} + +/// Load a fixture module with the specified type and return binary contents along with its hash. +#[cfg(feature = "std")] +pub fn compile_module_with_type( + fixture_name: &str, + fixture_type: FixtureType, +) -> anyhow::Result<(Vec, sp_core::H256)> { let out_dir: std::path::PathBuf = FIXTURE_DIR.into(); - let fixture_path = out_dir.join(format!("{fixture_name}.polkavm")); + let fixture_path = out_dir.join(format!("{fixture_name}{}", fixture_type.file_extension())); let binary = std::fs::read(fixture_path)?; let code_hash = sp_io::hashing::keccak_256(&binary); Ok((binary, sp_core::H256(code_hash))) } +/// Load a given polkavm module and returns a polkavm binary contents along with its hash. +#[cfg(feature = "std")] +pub fn compile_module(fixture_name: &str) -> anyhow::Result<(Vec, sp_core::H256)> { + compile_module_with_type(fixture_name, FixtureType::Rust) +} + /// Fixtures used in runtime benchmarks. /// /// We explicitly include those fixtures into the binary to make them diff --git a/substrate/frame/revive/rpc/revive_chain.metadata b/substrate/frame/revive/rpc/revive_chain.metadata index 4c4148fa0b7cf..cb98c4653acce 100644 Binary files a/substrate/frame/revive/rpc/revive_chain.metadata and b/substrate/frame/revive/rpc/revive_chain.metadata differ diff --git a/substrate/frame/revive/rpc/src/client.rs b/substrate/frame/revive/rpc/src/client.rs index f10e442316847..38786c1183146 100644 --- a/substrate/frame/revive/rpc/src/client.rs +++ b/substrate/frame/revive/rpc/src/client.rs @@ -665,8 +665,7 @@ impl Client { transactions_root: extrinsics_root, number: header.number.into(), timestamp: timestamp.into(), - difficulty: Some(0u32.into()), - base_fee_per_gas: runtime_api.gas_price().await.ok(), + base_fee_per_gas: runtime_api.gas_price().await.ok().unwrap_or_default(), gas_limit, gas_used, receipts_root: extrinsics_root, diff --git a/substrate/frame/revive/rpc/src/client/storage_api.rs b/substrate/frame/revive/rpc/src/client/storage_api.rs index db053751d5f32..d4b27d7162552 100644 --- a/substrate/frame/revive/rpc/src/client/storage_api.rs +++ b/substrate/frame/revive/rpc/src/client/storage_api.rs @@ -16,7 +16,11 @@ // limitations under the License. use crate::{ - subxt_client::{self, runtime_types::pallet_revive::storage::ContractInfo, SrcChainConfig}, + subxt_client::{ + self, + runtime_types::pallet_revive::storage::{AccountType, ContractInfo}, + SrcChainConfig, + }, ClientError, H160, }; use subxt::{storage::Storage, OnlineClient}; @@ -39,12 +43,16 @@ impl StorageApi { // TODO: remove once subxt is updated let contract_address: subxt::utils::H160 = contract_address.0.into(); - let query = subxt_client::storage().revive().contract_info_of(contract_address); + let query = subxt_client::storage().revive().account_info_of(contract_address); let Some(info) = self.0.fetch(&query).await? else { return Err(ClientError::ContractNotFound); }; - Ok(info) + let AccountType::Contract(contract_info) = info.account_type else { + return Err(ClientError::ContractNotFound); + }; + + Ok(contract_info) } /// Get the contract trie id for the given contract address. diff --git a/substrate/frame/revive/rpc/src/example.rs b/substrate/frame/revive/rpc/src/example.rs index 804b94badd8d5..f97003b65816e 100644 --- a/substrate/frame/revive/rpc/src/example.rs +++ b/substrate/frame/revive/rpc/src/example.rs @@ -62,7 +62,7 @@ impl SubmittedTransaction { ); return Ok(receipt) } else { - anyhow::bail!("Transaction failed") + anyhow::bail!("Transaction failed receipt: {receipt:?}") } } } @@ -180,7 +180,7 @@ impl TransactionBuilder { let hash = client .send_raw_transaction(bytes.into()) .await - .with_context(|| "transaction failed")?; + .with_context(|| "send_raw_transaction failed")?; Ok(SubmittedTransaction { tx: GenericTransaction::from_signed(signed_tx, gas_price, Some(from)), diff --git a/substrate/frame/revive/rpc/src/fee_history_provider.rs b/substrate/frame/revive/rpc/src/fee_history_provider.rs index 5f4483a0453f1..3ed6f63bf7e69 100644 --- a/substrate/frame/revive/rpc/src/fee_history_provider.rs +++ b/substrate/frame/revive/rpc/src/fee_history_provider.rs @@ -47,7 +47,7 @@ impl FeeHistoryProvider { let block_number: SubstrateBlockNumber = block.number.try_into().expect("Block number is always valid"); - let base_fee = block.base_fee_per_gas.unwrap_or_default().as_u128(); + let base_fee = block.base_fee_per_gas.as_u128(); let gas_used = block.gas_used.as_u128(); let gas_used_ratio = (gas_used as f64) / (block.gas_limit.as_u128() as f64); let mut result = FeeHistoryCacheItem { base_fee, gas_used_ratio, rewards: vec![] }; @@ -160,7 +160,7 @@ impl FeeHistoryProvider { async fn test_update_fee_history() { let block = Block { number: U256::from(200u64), - base_fee_per_gas: Some(U256::from(1000u64)), + base_fee_per_gas: U256::from(1000u64), gas_used: U256::from(600u64), gas_limit: U256::from(1200u64), ..Default::default() diff --git a/substrate/frame/revive/rpc/src/receipt_provider.rs b/substrate/frame/revive/rpc/src/receipt_provider.rs index fd4c9e3854b43..01374d5763b26 100644 --- a/substrate/frame/revive/rpc/src/receipt_provider.rs +++ b/substrate/frame/revive/rpc/src/receipt_provider.rs @@ -381,7 +381,7 @@ impl ReceiptProvider { topics, transaction_hash: H256::from_slice(&transaction_hash), transaction_index: U256::from(transaction_index as u64), - removed: None, + removed: false, }) }) .fetch_all(&self.pool) diff --git a/substrate/frame/revive/src/benchmarking.rs b/substrate/frame/revive/src/benchmarking.rs index 84819744b2ffb..8d7fd221ec6cc 100644 --- a/substrate/frame/revive/src/benchmarking.rs +++ b/substrate/frame/revive/src/benchmarking.rs @@ -27,6 +27,7 @@ use crate::{ self, run::builtin as run_builtin_precompile, BenchmarkSystem, BuiltinPrecompile, ISystem, }, storage::WriteOutcome, + vm::pvm, Pallet as Contracts, *, }; use alloc::{vec, vec::Vec}; @@ -79,7 +80,7 @@ macro_rules! build_runtime( let $contract = setup.contract(); let input = setup.data(); let (mut ext, _) = setup.ext(); - let mut $runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, input); + let mut $runtime = $crate::vm::pvm::Runtime::<_, [u8]>::new(&mut ext, input); }; ); @@ -654,7 +655,7 @@ mod benchmarks { let mut setup = CallSetup::::default(); setup.set_origin(Origin::Root); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::new(&mut ext, vec![]); let result; #[block] @@ -793,7 +794,7 @@ mod benchmarks { let (mut ext, _) = setup.ext(); ext.override_export(crate::exec::ExportedFunction::Constructor); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, input); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, input); let result; #[block] @@ -833,7 +834,7 @@ mod benchmarks { fn seal_return_data_size() { let mut setup = CallSetup::::default(); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::new(&mut ext, vec![]); let mut memory = memory!(vec![],); *runtime.ext().last_frame_output_mut() = ExecReturnValue { data: vec![42; 256], ..Default::default() }; @@ -849,7 +850,7 @@ mod benchmarks { fn seal_call_data_size() { let mut setup = CallSetup::::default(); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::new(&mut ext, vec![42u8; 128 as usize]); + let mut runtime = pvm::Runtime::new(&mut ext, vec![42u8; 128 as usize]); let mut memory = memory!(vec![0u8; 4],); let result; #[block] @@ -962,7 +963,7 @@ mod benchmarks { let (mut ext, _) = setup.ext(); ext.set_block_number(BlockNumberFor::::from(1u32)); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, input); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, input); let block_hash = H256::from([1; 32]); frame_system::BlockHash::::insert( @@ -1013,7 +1014,7 @@ mod benchmarks { fn seal_copy_to_contract(n: Linear<0, { limits::code::BLOB_BYTES - 4 }>) { let mut setup = CallSetup::::default(); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::new(&mut ext, vec![]); let mut memory = memory!(n.encode(), vec![0u8; n as usize],); let result; #[block] @@ -1036,7 +1037,7 @@ mod benchmarks { fn seal_call_data_load() { let mut setup = CallSetup::::default(); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::new(&mut ext, vec![42u8; 32]); + let mut runtime = pvm::Runtime::new(&mut ext, vec![42u8; 32]); let mut memory = memory!(vec![0u8; 32],); let result; #[block] @@ -1051,7 +1052,7 @@ mod benchmarks { fn seal_call_data_copy(n: Linear<0, { limits::code::BLOB_BYTES }>) { let mut setup = CallSetup::::default(); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::new(&mut ext, vec![42u8; n as usize]); + let mut runtime = pvm::Runtime::new(&mut ext, vec![42u8; n as usize]); let mut memory = memory!(vec![0u8; n as usize],); let result; #[block] @@ -1072,7 +1073,10 @@ mod benchmarks { result = runtime.bench_seal_return(memory.as_mut_slice(), 0, 0, n); } - assert!(matches!(result, Err(crate::vm::TrapReason::Return(crate::vm::ReturnData { .. })))); + assert!(matches!( + result, + Err(crate::vm::pvm::TrapReason::Return(crate::vm::pvm::ReturnData { .. })) + )); } #[benchmark(pov_mode = Measured)] @@ -1087,7 +1091,7 @@ mod benchmarks { result = runtime.bench_terminate(memory.as_mut_slice(), 0); } - assert!(matches!(result, Err(crate::vm::TrapReason::Termination))); + assert!(matches!(result, Err(crate::vm::pvm::TrapReason::Termination))); Ok(()) } @@ -1391,7 +1395,7 @@ mod benchmarks { let value = Some(vec![42u8; max_value_len as _]); let mut setup = CallSetup::::default(); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, vec![]); runtime.ext().transient_storage().meter().current_mut().limit = u32::MAX; let result; #[block] @@ -1414,7 +1418,7 @@ mod benchmarks { let mut setup = CallSetup::::default(); setup.set_transient_storage_size(limits::TRANSIENT_STORAGE_BYTES); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, vec![]); runtime.ext().transient_storage().meter().current_mut().limit = u32::MAX; let result; #[block] @@ -1436,7 +1440,7 @@ mod benchmarks { let mut setup = CallSetup::::default(); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, vec![]); runtime.ext().transient_storage().meter().current_mut().limit = u32::MAX; runtime .ext() @@ -1462,7 +1466,7 @@ mod benchmarks { let mut setup = CallSetup::::default(); setup.set_transient_storage_size(limits::TRANSIENT_STORAGE_BYTES); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, vec![]); runtime.ext().transient_storage().meter().current_mut().limit = u32::MAX; runtime .ext() @@ -1489,7 +1493,7 @@ mod benchmarks { let mut setup = CallSetup::::default(); setup.set_transient_storage_size(limits::TRANSIENT_STORAGE_BYTES); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, vec![]); runtime.ext().transient_storage().meter().current_mut().limit = u32::MAX; runtime.ext().transient_storage().start_transaction(); runtime @@ -1702,7 +1706,7 @@ mod benchmarks { setup.set_balance(value + 1u32.into() + Pallet::::min_balance()); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, vec![]); let mut memory = memory!(callee_bytes, deposit_bytes, value_bytes,); let result; @@ -1759,7 +1763,7 @@ mod benchmarks { setup.set_storage_deposit_limit(deposit); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, vec![]); let mut memory = memory!(callee_bytes, deposit_bytes, value_bytes, input_bytes,); let mut do_benchmark = || { @@ -1805,7 +1809,7 @@ mod benchmarks { setup.set_origin(Origin::from_account_id(setup.contract().account_id.clone())); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, vec![]); let mut memory = memory!(address_bytes, deposit_bytes,); let result; @@ -1856,7 +1860,7 @@ mod benchmarks { let account_id = &setup.contract().account_id.clone(); let (mut ext, _) = setup.ext(); - let mut runtime = crate::vm::Runtime::<_, [u8]>::new(&mut ext, vec![]); + let mut runtime = pvm::Runtime::<_, [u8]>::new(&mut ext, vec![]); let input = vec![42u8; i as _]; let input_len = hash_bytes.len() as u32 + input.len() as u32; @@ -2076,7 +2080,9 @@ mod benchmarks { fn bn128_add() { use hex_literal::hex; let input = hex!("089142debb13c461f61523586a60732d8b69c5b38a3380a74da7b2961d867dbf2d5fc7bbc013c16d7945f190b232eacc25da675c0eb093fe6b9f1b4b4e107b3625f8c89ea3437f44f8fc8b6bfbb6312074dc6f983809a5e809ff4e1d076dd5850b38c7ced6e4daef9c4347f370d6d8b58f4b1d8dc61a3c59d651a0644a2a27cf").to_vec(); - let expected = hex!("0a6678fd675aa4d8f0d03a1feb921a27f38ebdcb860cc083653519655acd6d79172fd5b3b2bfdd44e43bcec3eace9347608f9f0a16f1e184cb3f52e6f259cbeb"); + let expected = hex!( + "0a6678fd675aa4d8f0d03a1feb921a27f38ebdcb860cc083653519655acd6d79172fd5b3b2bfdd44e43bcec3eace9347608f9f0a16f1e184cb3f52e6f259cbeb" + ); let mut call_setup = CallSetup::::default(); let (mut ext, _) = call_setup.ext(); @@ -2094,7 +2100,9 @@ mod benchmarks { fn bn128_mul() { use hex_literal::hex; let input = hex!("089142debb13c461f61523586a60732d8b69c5b38a3380a74da7b2961d867dbf2d5fc7bbc013c16d7945f190b232eacc25da675c0eb093fe6b9f1b4b4e107b36ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff").to_vec(); - let expected = hex!("0bf982b98a2757878c051bfe7eee228b12bc69274b918f08d9fcb21e9184ddc10b17c77cbf3c19d5d27e18cbd4a8c336afb488d0e92c18d56e64dd4ea5c437e6"); + let expected = hex!( + "0bf982b98a2757878c051bfe7eee228b12bc69274b918f08d9fcb21e9184ddc10b17c77cbf3c19d5d27e18cbd4a8c336afb488d0e92c18d56e64dd4ea5c437e6" + ); let mut call_setup = CallSetup::::default(); let (mut ext, _) = call_setup.ext(); @@ -2161,7 +2169,9 @@ mod benchmarks { #[benchmark(pov_mode = Measured)] fn blake2f(n: Linear<0, 1200>) { use hex_literal::hex; - let input = hex!("48c9bdf267e6096a3ba7ca8485ae67bb2bf894fe72f36e3cf1361d5f3af54fa5d182e6ad7f520e511f6c3e2b8c68059b6bbd41fbabd9831f79217e1319cde05b61626300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000300000000000000000000000000000001"); + let input = hex!( + "48c9bdf267e6096a3ba7ca8485ae67bb2bf894fe72f36e3cf1361d5f3af54fa5d182e6ad7f520e511f6c3e2b8c68059b6bbd41fbabd9831f79217e1319cde05b61626300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000300000000000000000000000000000001" + ); let input = n.to_be_bytes().to_vec().into_iter().chain(input.to_vec()).collect::>(); let mut call_setup = CallSetup::::default(); let (mut ext, _) = call_setup.ext(); diff --git a/substrate/frame/revive/src/call_builder.rs b/substrate/frame/revive/src/call_builder.rs index 683cd5d5db803..1213dc874d4e5 100644 --- a/substrate/frame/revive/src/call_builder.rs +++ b/substrate/frame/revive/src/call_builder.rs @@ -31,7 +31,7 @@ use crate::{ limits, storage::meter::Meter, transient_storage::MeterEntry, - vm::{PreparedCall, Runtime}, + vm::pvm::{PreparedCall, Runtime}, AccountInfo, BalanceOf, BalanceWithDust, BumpNonce, Code, CodeInfoOf, Config, ContractBlob, ContractInfo, DepositLimit, Error, GasMeter, MomentOf, Origin, Pallet as Contracts, PristineCode, Weight, diff --git a/substrate/frame/revive/src/evm/api/debug_rpc_types.rs b/substrate/frame/revive/src/evm/api/debug_rpc_types.rs index 737c0a2c4361f..7dbfc254a769a 100644 --- a/substrate/frame/revive/src/evm/api/debug_rpc_types.rs +++ b/substrate/frame/revive/src/evm/api/debug_rpc_types.rs @@ -258,13 +258,13 @@ where #[derive( TypeInfo, Default, Encode, Decode, Serialize, Deserialize, Clone, Debug, Eq, PartialEq, )] +#[serde(rename_all = "camelCase")] pub struct CallTrace { /// Address of the sender. pub from: H160, /// Amount of gas provided for the call. pub gas: Gas, /// Amount of gas used. - #[serde(rename = "gasUsed")] pub gas_used: Gas, /// Address of the receiver. pub to: H160, @@ -277,7 +277,7 @@ pub struct CallTrace { #[serde(skip_serializing_if = "Option::is_none")] pub error: Option, /// The revert reason, if the call reverted. - #[serde(rename = "revertReason", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub revert_reason: Option, /// List of sub-calls. #[serde(skip_serializing_if = "Vec::is_empty")] @@ -313,9 +313,9 @@ pub struct CallLog { /// A transaction trace #[derive(Serialize, Deserialize, Clone, Debug)] +#[serde(rename_all = "camelCase")] pub struct TransactionTrace { /// The transaction hash. - #[serde(rename = "txHash")] pub tx_hash: H256, /// The trace of the transaction. #[serde(rename = "result")] diff --git a/substrate/frame/revive/src/evm/api/rlp_codec.rs b/substrate/frame/revive/src/evm/api/rlp_codec.rs index 4094c963ac204..1ed5397de9573 100644 --- a/substrate/frame/revive/src/evm/api/rlp_codec.rs +++ b/substrate/frame/revive/src/evm/api/rlp_codec.rs @@ -27,6 +27,10 @@ impl TransactionUnsigned { use TransactionUnsigned::*; let mut s = rlp::RlpStream::new(); match self { + Transaction7702Unsigned(ref tx) => { + s.append(&tx.r#type.value()); + s.append(tx); + }, Transaction2930Unsigned(ref tx) => { s.append(&tx.r#type.value()); s.append(tx); @@ -54,6 +58,7 @@ impl TransactionSigned { use TransactionSigned::*; use TransactionUnsigned::*; match self { + Transaction7702Signed(tx) => Transaction7702Unsigned(tx.transaction_7702_unsigned), Transaction2930Signed(tx) => Transaction2930Unsigned(tx.transaction_2930_unsigned), Transaction1559Signed(tx) => Transaction1559Unsigned(tx.transaction_1559_unsigned), Transaction4844Signed(tx) => Transaction4844Unsigned(tx.transaction_4844_unsigned), @@ -67,6 +72,10 @@ impl TransactionSigned { use TransactionSigned::*; let mut s = rlp::RlpStream::new(); match self { + Transaction7702Signed(ref tx) => { + s.append(&tx.transaction_7702_unsigned.r#type.value()); + s.append(tx); + }, Transaction2930Signed(ref tx) => { s.append(&tx.transaction_2930_unsigned.r#type.value()); s.append(tx); @@ -198,6 +207,31 @@ impl Decodable for AccessListEntry { } } +impl Encodable for AuthorizationListEntry { + fn rlp_append(&self, s: &mut rlp::RlpStream) { + s.begin_list(6); + s.append(&self.chain_id); + s.append(&self.address); + s.append(&self.nonce); + s.append(&self.y_parity); + s.append(&self.r); + s.append(&self.s); + } +} + +impl Decodable for AuthorizationListEntry { + fn decode(rlp: &rlp::Rlp) -> Result { + Ok(AuthorizationListEntry { + chain_id: rlp.val_at(0)?, + address: rlp.val_at(1)?, + nonce: rlp.val_at(2)?, + y_parity: rlp.val_at(3)?, + r: rlp.val_at(4)?, + s: rlp.val_at(5)?, + }) + } +} + /// See impl Encodable for Transaction1559Unsigned { fn rlp_append(&self, s: &mut rlp::RlpStream) { @@ -344,7 +378,23 @@ impl Decodable for Transaction2930Signed { } } -//See https://eips.ethereum.org/EIPS/eip-4844 +//See https://eips.ethereum.org/EIPS/eip-7702 +impl Encodable for Transaction7702Unsigned { + fn rlp_append(&self, s: &mut rlp::RlpStream) { + s.begin_list(10); + s.append(&self.chain_id); + s.append(&self.nonce); + s.append(&self.max_priority_fee_per_gas); + s.append(&self.max_fee_per_gas); + s.append(&self.gas); + s.append(&self.to); + s.append(&self.value); + s.append(&self.input.0); + s.append_list(&self.access_list); + s.append_list(&self.authorization_list); + } +} + impl Encodable for Transaction4844Unsigned { fn rlp_append(&self, s: &mut rlp::RlpStream) { s.begin_list(11); @@ -362,6 +412,27 @@ impl Encodable for Transaction4844Unsigned { } } +//See https://eips.ethereum.org/EIPS/eip-7702 +impl Encodable for Transaction7702Signed { + fn rlp_append(&self, s: &mut rlp::RlpStream) { + let tx = &self.transaction_7702_unsigned; + s.begin_list(13); + s.append(&tx.chain_id); + s.append(&tx.nonce); + s.append(&tx.max_priority_fee_per_gas); + s.append(&tx.max_fee_per_gas); + s.append(&tx.gas); + s.append(&tx.to); + s.append(&tx.value); + s.append(&tx.input.0); + s.append_list(&tx.access_list); + s.append_list(&tx.authorization_list); + s.append(&self.y_parity); + s.append(&self.r); + s.append(&self.s); + } +} + //See https://eips.ethereum.org/EIPS/eip-4844 impl Encodable for Transaction4844Signed { fn rlp_append(&self, s: &mut rlp::RlpStream) { diff --git a/substrate/frame/revive/src/evm/api/rpc_types.rs b/substrate/frame/revive/src/evm/api/rpc_types.rs index 195c1c5fd4623..09b9f67271504 100644 --- a/substrate/frame/revive/src/evm/api/rpc_types.rs +++ b/substrate/frame/revive/src/evm/api/rpc_types.rs @@ -32,6 +32,7 @@ impl From for TransactionUnsigned { fn from(tx: TransactionSigned) -> Self { use TransactionSigned::*; match tx { + Transaction7702Signed(tx) => tx.transaction_7702_unsigned.into(), Transaction4844Signed(tx) => tx.transaction_4844_unsigned.into(), Transaction1559Signed(tx) => tx.transaction_1559_unsigned.into(), Transaction2930Signed(tx) => tx.transaction_2930_unsigned.into(), @@ -281,6 +282,26 @@ impl GenericTransaction { access_list: Some(tx.access_list), ..Default::default() }, + Transaction7702Unsigned(tx) => GenericTransaction { + from, + r#type: Some(tx.r#type.as_byte()), + chain_id: Some(tx.chain_id), + input: tx.input.into(), + nonce: Some(tx.nonce), + value: Some(tx.value), + to: tx.to, + gas: Some(tx.gas), + gas_price: Some( + base_gas_price + .saturating_add(tx.max_priority_fee_per_gas) + .min(tx.max_fee_per_gas), + ), + access_list: Some(tx.access_list), + authorization_list: tx.authorization_list, + max_fee_per_gas: Some(tx.max_fee_per_gas), + max_priority_fee_per_gas: Some(tx.max_priority_fee_per_gas), + ..Default::default() + }, } } @@ -339,6 +360,21 @@ impl GenericTransaction { blob_versioned_hashes: self.blob_versioned_hashes, } .into()), + TYPE_EIP7702 => Ok(Transaction7702Unsigned { + r#type: TypeEip7702 {}, + chain_id: self.chain_id.unwrap_or_default(), + input: self.input.to_bytes(), + nonce: self.nonce.unwrap_or_default(), + value: self.value.unwrap_or_default(), + to: self.to, + gas: self.gas.unwrap_or_default(), + gas_price: self.max_fee_per_gas.unwrap_or_default(), + max_fee_per_gas: self.max_fee_per_gas.unwrap_or_default(), + max_priority_fee_per_gas: self.max_priority_fee_per_gas.unwrap_or_default(), + access_list: self.access_list.unwrap_or_default(), + authorization_list: self.authorization_list, + } + .into()), _ => Err(()), } } @@ -387,3 +423,34 @@ fn from_unsigned_works_for_1559() { let tx2 = generic.try_into_unsigned().unwrap(); assert_eq!(tx, tx2); } + +#[test] +fn from_unsigned_works_for_7702() { + let base_gas_price = U256::from(10); + let tx = TransactionUnsigned::from(Transaction7702Unsigned { + chain_id: U256::from(1), + input: Bytes::from(vec![1u8]), + nonce: U256::from(1), + value: U256::from(1), + to: Some(H160::zero()), + gas: U256::from(1), + gas_price: U256::from(20), + max_fee_per_gas: U256::from(20), + max_priority_fee_per_gas: U256::from(1), + authorization_list: vec![AuthorizationListEntry { + chain_id: U256::from(1), + address: H160::from_low_u64_be(42), + nonce: U256::from(0), + y_parity: U256::from(1), + r: U256::from(1), + s: U256::from(2), + }], + ..Default::default() + }); + + let generic = GenericTransaction::from_unsigned(tx.clone(), base_gas_price, None); + assert_eq!(generic.gas_price, Some(U256::from(11))); + + let tx2 = generic.try_into_unsigned().unwrap(); + assert_eq!(tx, tx2); +} diff --git a/substrate/frame/revive/src/evm/api/rpc_types_gen.rs b/substrate/frame/revive/src/evm/api/rpc_types_gen.rs index 549dde9dea954..7ca087ff53fe4 100644 --- a/substrate/frame/revive/src/evm/api/rpc_types_gen.rs +++ b/substrate/frame/revive/src/evm/api/rpc_types_gen.rs @@ -17,7 +17,7 @@ //! Generated JSON-RPC types. #![allow(missing_docs)] -use super::{byte::*, TypeEip1559, TypeEip2930, TypeEip4844, TypeLegacy}; +use super::{byte::*, TypeEip1559, TypeEip2930, TypeEip4844, TypeEip7702, TypeLegacy}; use alloc::vec::Vec; use codec::{Decode, Encode}; use derive_more::{From, TryInto}; @@ -75,76 +75,64 @@ fn deserialize_input_or_data<'d, D: Deserializer<'d>>(d: D) -> Result, + pub base_fee_per_gas: U256, /// Blob gas used - #[serde(rename = "blobGasUsed", skip_serializing_if = "Option::is_none")] - pub blob_gas_used: Option, + pub blob_gas_used: U256, /// Difficulty - #[serde(skip_serializing_if = "Option::is_none")] - pub difficulty: Option, + pub difficulty: U256, /// Excess blob gas - #[serde(rename = "excessBlobGas", skip_serializing_if = "Option::is_none")] - pub excess_blob_gas: Option, + pub excess_blob_gas: U256, /// Extra data - #[serde(rename = "extraData")] pub extra_data: Bytes, /// Gas limit - #[serde(rename = "gasLimit")] pub gas_limit: U256, /// Gas used - #[serde(rename = "gasUsed")] pub gas_used: U256, /// Hash pub hash: H256, /// Bloom filter - #[serde(rename = "logsBloom")] pub logs_bloom: Bytes256, /// Coinbase pub miner: Address, /// Mix hash - #[serde(rename = "mixHash")] pub mix_hash: H256, /// Nonce pub nonce: Bytes8, /// Number pub number: U256, /// Parent Beacon Block Root - #[serde(rename = "parentBeaconBlockRoot", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub parent_beacon_block_root: Option, /// Parent block hash - #[serde(rename = "parentHash")] pub parent_hash: H256, /// Receipts root - #[serde(rename = "receiptsRoot")] pub receipts_root: H256, + /// Requests root + #[serde(skip_serializing_if = "Option::is_none")] + pub requests_hash: Option, /// Ommers hash - #[serde(rename = "sha3Uncles")] pub sha_3_uncles: H256, /// Block size pub size: U256, /// State root - #[serde(rename = "stateRoot")] pub state_root: H256, /// Timestamp pub timestamp: U256, /// Total difficulty - #[serde(rename = "totalDifficulty", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub total_difficulty: Option, pub transactions: HashesOrTransactionInfos, /// Transactions root - #[serde(rename = "transactionsRoot")] pub transactions_root: H256, /// Uncles pub uncles: Vec, /// Withdrawals - #[serde(default, skip_serializing_if = "Vec::is_empty")] pub withdrawals: Vec, /// Withdrawals root - #[serde(rename = "withdrawalsRoot", skip_serializing_if = "Option::is_none")] - pub withdrawals_root: Option, + pub withdrawals_root: H256, } /// Block number or tag @@ -221,17 +209,18 @@ impl<'a> serde::Deserialize<'a> for BlockNumberOrTagOrHash { /// filter #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct Filter { /// Address(es) pub address: Option, /// from block - #[serde(rename = "fromBlock", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub from_block: Option, /// to block - #[serde(rename = "toBlock", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub to_block: Option, /// Restricts the logs returned to the single block - #[serde(rename = "blockHash", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub block_hash: Option, /// Topics #[serde(skip_serializing_if = "Option::is_none")] @@ -257,14 +246,19 @@ impl Default for FilterResults { #[derive( Debug, Default, Clone, Encode, Decode, TypeInfo, Serialize, Deserialize, Eq, PartialEq, )] +#[serde(rename_all = "camelCase")] pub struct GenericTransaction { /// accessList /// EIP-2930 access list - #[serde(rename = "accessList", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub access_list: Option, + /// authorizationList + /// List of account code authorizations (EIP-7702) + #[serde(default, skip_serializing_if = "Vec::is_empty")] + pub authorization_list: Vec, /// blobVersionedHashes /// List of versioned blob hashes associated with the transaction's EIP-4844 data blobs. - #[serde(rename = "blobVersionedHashes", default, skip_serializing_if = "Vec::is_empty")] + #[serde(default)] pub blob_versioned_hashes: Vec, /// blobs /// Raw blob data. @@ -272,7 +266,7 @@ pub struct GenericTransaction { pub blobs: Vec, /// chainId /// Chain ID that this transaction is valid on. - #[serde(rename = "chainId", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub chain_id: Option, /// from address #[serde(skip_serializing_if = "Option::is_none")] @@ -282,23 +276,23 @@ pub struct GenericTransaction { pub gas: Option, /// gas price /// The gas price willing to be paid by the sender in wei - #[serde(rename = "gasPrice", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub gas_price: Option, /// input data #[serde(flatten, deserialize_with = "deserialize_input_or_data")] pub input: InputOrData, /// max fee per blob gas /// The maximum total fee per gas the sender is willing to pay for blob gas in wei - #[serde(rename = "maxFeePerBlobGas", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub max_fee_per_blob_gas: Option, /// max fee per gas /// The maximum total fee per gas the sender is willing to pay (includes the network / base fee /// and miner / priority fee) in wei - #[serde(rename = "maxFeePerGas", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub max_fee_per_gas: Option, /// max priority fee per gas /// Maximum fee per gas the sender is willing to pay to miners in wei - #[serde(rename = "maxPriorityFeePerGas", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub max_priority_fee_per_gas: Option, /// nonce #[serde(skip_serializing_if = "Option::is_none")] @@ -315,47 +309,41 @@ pub struct GenericTransaction { /// Receipt information #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct ReceiptInfo { /// blob gas price /// The actual value per gas deducted from the sender's account for blob gas. Only specified /// for blob transactions as defined by EIP-4844. - #[serde(rename = "blobGasPrice", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub blob_gas_price: Option, /// blob gas used /// The amount of blob gas used for this specific transaction. Only specified for blob /// transactions as defined by EIP-4844. - #[serde(rename = "blobGasUsed", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub blob_gas_used: Option, /// block hash - #[serde(rename = "blockHash")] pub block_hash: H256, /// block number - #[serde(rename = "blockNumber")] pub block_number: U256, /// contract address /// The contract address created, if the transaction was a contract creation, otherwise null. - #[serde(rename = "contractAddress")] pub contract_address: Option
, /// cumulative gas used /// The sum of gas used by this transaction and all preceding transactions in the same block. - #[serde(rename = "cumulativeGasUsed")] pub cumulative_gas_used: U256, /// effective gas price /// The actual value per gas deducted from the sender's account. Before EIP-1559, this is equal /// to the transaction's gas price. After, it is equal to baseFeePerGas + min(maxFeePerGas - /// baseFeePerGas, maxPriorityFeePerGas). - #[serde(rename = "effectiveGasPrice")] pub effective_gas_price: U256, /// from pub from: Address, /// gas used /// The amount of gas used for this specific transaction alone. - #[serde(rename = "gasUsed")] pub gas_used: U256, /// logs pub logs: Vec, /// logs bloom - #[serde(rename = "logsBloom")] pub logs_bloom: Bytes256, /// state root /// The post-transaction state root. Only specified for transactions included before the @@ -371,10 +359,8 @@ pub struct ReceiptInfo { /// Address of the receiver or null in a contract creation transaction. pub to: Option
, /// transaction hash - #[serde(rename = "transactionHash")] pub transaction_hash: H256, /// transaction index - #[serde(rename = "transactionIndex")] pub transaction_index: U256, /// type #[serde(skip_serializing_if = "Option::is_none")] @@ -399,19 +385,17 @@ impl Default for SyncingStatus { /// Transaction information #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct TransactionInfo { /// block hash - #[serde(rename = "blockHash")] pub block_hash: H256, /// block number - #[serde(rename = "blockNumber")] pub block_number: U256, /// from address pub from: Address, /// transaction hash pub hash: H256, /// transaction index - #[serde(rename = "transactionIndex")] pub transaction_index: U256, #[serde(flatten)] pub transaction_signed: TransactionSigned, @@ -420,6 +404,7 @@ pub struct TransactionInfo { #[derive(Debug, Clone, Serialize, Deserialize, From, TryInto, Eq, PartialEq)] #[serde(untagged)] pub enum TransactionUnsigned { + Transaction7702Unsigned(Transaction7702Unsigned), Transaction4844Unsigned(Transaction4844Unsigned), Transaction1559Unsigned(Transaction1559Unsigned), Transaction2930Unsigned(Transaction2930Unsigned), @@ -463,17 +448,13 @@ pub type Addresses = Vec
; /// transition is finalized, any call querying for `finalized` or `safe` block MUST be responded to /// with `-39001: Unknown block` error #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "lowercase")] pub enum BlockTag { - #[serde(rename = "earliest")] Earliest, - #[serde(rename = "finalized")] Finalized, - #[serde(rename = "safe")] Safe, - #[serde(rename = "latest")] #[default] Latest, - #[serde(rename = "pending")] Pending, } @@ -496,59 +477,55 @@ impl Default for HashesOrTransactionInfos { /// log #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct Log { /// address pub address: Address, /// block hash - #[serde(rename = "blockHash")] pub block_hash: H256, /// block number - #[serde(rename = "blockNumber")] pub block_number: U256, /// data #[serde(skip_serializing_if = "Option::is_none")] pub data: Option, /// log index - #[serde(rename = "logIndex")] pub log_index: U256, /// removed - #[serde(skip_serializing_if = "Option::is_none")] - pub removed: Option, + #[serde(default)] + pub removed: bool, /// topics - #[serde(default, skip_serializing_if = "Vec::is_empty")] + #[serde(default)] pub topics: Vec, /// transaction hash - #[serde(rename = "transactionHash")] pub transaction_hash: H256, /// transaction index - #[serde(rename = "transactionIndex")] pub transaction_index: U256, } /// Syncing progress #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct SyncingProgress { /// Current block - #[serde(rename = "currentBlock", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub current_block: Option, /// Highest block - #[serde(rename = "highestBlock", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub highest_block: Option, /// Starting block - #[serde(rename = "startingBlock", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub starting_block: Option, } /// EIP-1559 transaction. #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct Transaction1559Unsigned { /// accessList /// EIP-2930 access list - #[serde(rename = "accessList")] pub access_list: AccessList, /// chainId /// Chain ID that this transaction is valid on. - #[serde(rename = "chainId")] pub chain_id: U256, /// gas limit pub gas: U256, @@ -556,18 +533,15 @@ pub struct Transaction1559Unsigned { /// The effective gas price paid by the sender in wei. For transactions not yet included in a /// block, this value should be set equal to the max fee per gas. This field is DEPRECATED, /// please transition to using effectiveGasPrice in the receipt object going forward. - #[serde(rename = "gasPrice")] pub gas_price: U256, /// input data pub input: Bytes, /// max fee per gas /// The maximum total fee per gas the sender is willing to pay (includes the network / base fee /// and miner / priority fee) in wei - #[serde(rename = "maxFeePerGas")] pub max_fee_per_gas: U256, /// max priority fee per gas /// Maximum fee per gas the sender is willing to pay to miners in wei - #[serde(rename = "maxPriorityFeePerGas")] pub max_priority_fee_per_gas: U256, /// nonce pub nonce: U256, @@ -581,20 +555,18 @@ pub struct Transaction1559Unsigned { /// EIP-2930 transaction. #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct Transaction2930Unsigned { /// accessList /// EIP-2930 access list - #[serde(rename = "accessList")] pub access_list: AccessList, /// chainId /// Chain ID that this transaction is valid on. - #[serde(rename = "chainId")] pub chain_id: U256, /// gas limit pub gas: U256, /// gas price /// The gas price willing to be paid by the sender in wei - #[serde(rename = "gasPrice")] pub gas_price: U256, /// input data pub input: Bytes, @@ -610,18 +582,16 @@ pub struct Transaction2930Unsigned { /// EIP-4844 transaction. #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct Transaction4844Unsigned { /// accessList /// EIP-2930 access list - #[serde(rename = "accessList")] pub access_list: AccessList, /// blobVersionedHashes /// List of versioned blob hashes associated with the transaction's EIP-4844 data blobs. - #[serde(rename = "blobVersionedHashes")] pub blob_versioned_hashes: Vec, /// chainId /// Chain ID that this transaction is valid on. - #[serde(rename = "chainId")] pub chain_id: U256, /// gas limit pub gas: U256, @@ -629,16 +599,13 @@ pub struct Transaction4844Unsigned { pub input: Bytes, /// max fee per blob gas /// The maximum total fee per gas the sender is willing to pay for blob gas in wei - #[serde(rename = "maxFeePerBlobGas")] pub max_fee_per_blob_gas: U256, /// max fee per gas /// The maximum total fee per gas the sender is willing to pay (includes the network / base fee /// and miner / priority fee) in wei - #[serde(rename = "maxFeePerGas")] pub max_fee_per_gas: U256, /// max priority fee per gas /// Maximum fee per gas the sender is willing to pay to miners in wei - #[serde(rename = "maxPriorityFeePerGas")] pub max_priority_fee_per_gas: U256, /// nonce pub nonce: U256, @@ -652,16 +619,16 @@ pub struct Transaction4844Unsigned { /// Legacy transaction. #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct TransactionLegacyUnsigned { /// chainId /// Chain ID that this transaction is valid on. - #[serde(rename = "chainId", skip_serializing_if = "Option::is_none")] + #[serde(skip_serializing_if = "Option::is_none")] pub chain_id: Option, /// gas limit pub gas: U256, /// gas price /// The gas price willing to be paid by the sender in wei - #[serde(rename = "gasPrice")] pub gas_price: U256, /// input data pub input: Bytes, @@ -675,9 +642,71 @@ pub struct TransactionLegacyUnsigned { pub value: U256, } +/// EIP-7702 transaction. +#[derive( + Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq, TypeInfo, Encode, Decode, +)] +#[serde(rename_all = "camelCase")] +pub struct Transaction7702Unsigned { + /// accessList + /// EIP-2930 access list + pub access_list: AccessList, + /// authorizationList + /// List of account code authorizations + pub authorization_list: Vec, + /// chainId + /// Chain ID that this transaction is valid on. + pub chain_id: U256, + /// gas limit + pub gas: U256, + /// gas price + /// The effective gas price paid by the sender in wei. For transactions not yet included in a + /// block, this value should be set equal to the max fee per gas. This field is DEPRECATED, + /// please transition to using effectiveGasPrice in the receipt object going forward. + pub gas_price: U256, + /// input data + pub input: Bytes, + /// max fee per gas + /// The maximum total fee per gas the sender is willing to pay (includes the network / base fee + /// and miner / priority fee) in wei + pub max_fee_per_gas: U256, + /// max priority fee per gas + /// Maximum fee per gas the sender is willing to pay to miners in wei + pub max_priority_fee_per_gas: U256, + /// nonce + pub nonce: U256, + /// to address + pub to: Option
, + /// type + pub r#type: TypeEip7702, + /// value + pub value: U256, +} + +/// Authorization list entry for EIP-7702 +#[derive( + Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq, TypeInfo, Encode, Decode, +)] +#[serde(rename_all = "camelCase")] +pub struct AuthorizationListEntry { + /// Chain ID that this authorization is valid on + pub chain_id: U256, + /// Address to authorize + pub address: Address, + /// Nonce of the authorization + pub nonce: U256, + /// y-parity of the signature + pub y_parity: U256, + /// r component of signature + pub r: U256, + /// s component of signature + pub s: U256, +} + #[derive(Debug, Clone, Serialize, Deserialize, From, TryInto, Eq, PartialEq)] #[serde(untagged)] pub enum TransactionSigned { + Transaction7702Signed(Transaction7702Signed), Transaction4844Signed(Transaction4844Signed), Transaction1559Signed(Transaction1559Signed), Transaction2930Signed(Transaction2930Signed), @@ -689,8 +718,29 @@ impl Default for TransactionSigned { } } +impl TransactionSigned { + /// Get the effective gas price. + pub fn effective_gas_price(&self, base_gas_price: U256) -> U256 { + match &self { + TransactionSigned::TransactionLegacySigned(tx) => + tx.transaction_legacy_unsigned.gas_price, + TransactionSigned::Transaction7702Signed(tx) => base_gas_price + .saturating_add(tx.transaction_7702_unsigned.max_priority_fee_per_gas) + .min(tx.transaction_7702_unsigned.max_fee_per_gas), + TransactionSigned::Transaction4844Signed(tx) => base_gas_price + .saturating_add(tx.transaction_4844_unsigned.max_priority_fee_per_gas) + .min(tx.transaction_4844_unsigned.max_fee_per_blob_gas), + TransactionSigned::Transaction1559Signed(tx) => base_gas_price + .saturating_add(tx.transaction_1559_unsigned.max_priority_fee_per_gas) + .min(tx.transaction_1559_unsigned.max_fee_per_gas), + TransactionSigned::Transaction2930Signed(tx) => tx.transaction_2930_unsigned.gas_price, + } + } +} + /// Validator withdrawal #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct Withdrawal { /// recipient address for withdrawal value pub address: Address, @@ -699,7 +749,6 @@ pub struct Withdrawal { /// index of withdrawal pub index: U256, /// index of validator that generated withdrawal - #[serde(rename = "validatorIndex")] pub validator_index: U256, } @@ -707,9 +756,9 @@ pub struct Withdrawal { #[derive( Debug, Default, Clone, Encode, Decode, TypeInfo, Serialize, Deserialize, Eq, PartialEq, )] +#[serde(rename_all = "camelCase")] pub struct AccessListEntry { pub address: Address, - #[serde(rename = "storageKeys")] pub storage_keys: Vec, } @@ -728,8 +777,31 @@ impl Default for FilterTopic { } } +/// Signed 7702 Transaction +#[derive( + Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq, TypeInfo, Encode, Decode, +)] +#[serde(rename_all = "camelCase")] +pub struct Transaction7702Signed { + #[serde(flatten)] + pub transaction_7702_unsigned: Transaction7702Unsigned, + /// r + pub r: U256, + /// s + pub s: U256, + /// v + /// For backwards compatibility, `v` is optionally provided as an alternative to `yParity`. + /// This field is DEPRECATED and all use of it should migrate to `yParity`. + #[serde(skip_serializing_if = "Option::is_none")] + pub v: Option, + /// yParity + /// The parity (0 for even, 1 for odd) of the y-value of the secp256k1 signature. + pub y_parity: U256, +} + /// Signed 1559 Transaction #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct Transaction1559Signed { #[serde(flatten)] pub transaction_1559_unsigned: Transaction1559Unsigned, @@ -744,12 +816,12 @@ pub struct Transaction1559Signed { pub v: Option, /// yParity /// The parity (0 for even, 1 for odd) of the y-value of the secp256k1 signature. - #[serde(rename = "yParity")] pub y_parity: U256, } /// Signed 2930 Transaction #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct Transaction2930Signed { #[serde(flatten)] pub transaction_2930_unsigned: Transaction2930Unsigned, @@ -764,12 +836,12 @@ pub struct Transaction2930Signed { pub v: Option, /// yParity /// The parity (0 for even, 1 for odd) of the y-value of the secp256k1 signature. - #[serde(rename = "yParity")] pub y_parity: U256, } /// Signed 4844 Transaction #[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] +#[serde(rename_all = "camelCase")] pub struct Transaction4844Signed { #[serde(flatten)] pub transaction_4844_unsigned: Transaction4844Unsigned, @@ -779,7 +851,6 @@ pub struct Transaction4844Signed { pub s: U256, /// yParity /// The parity (0 for even, 1 for odd) of the y-value of the secp256k1 signature. - #[serde(rename = "yParity")] pub y_parity: U256, } @@ -821,3 +892,53 @@ pub struct FeeHistoryResult { #[serde(default, skip_serializing_if = "Vec::is_empty")] pub reward: Vec>, } + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn test_block_serialization_roundtrip() { + let json_input = r#"{ + "baseFeePerGas": "0x126f2347", + "blobGasUsed": "0x100000", + "difficulty": "0x0", + "excessBlobGas": "0x0", + "extraData": "0x546974616e2028746974616e6275696c6465722e78797a29", + "gasLimit": "0x2aca2c9", + "gasUsed": "0x1c06043", + "hash": "0xe6064637def8a5a9a90c8a666005975e4a6c46acf8af57e1f2adb20dfced133a", + "logsBloom": "0xbf7bf1afcf57ea95fbb5c6fd8db37db9dbffec27cfc6a39b3417e7786defd7e3d6fd577ecddd5676eee8bf79df8faddcefa7e169def77f7e7d6dbbfd1dfef9aebd9e707b4c4ed979fda2cdeeb96b3bfed5d5fabb68ff9e7f2dfb075eff643a93feebbc07877f0dff66fedf4ede0fbcfbf56f98a1626eaed77ed4e6be388f162f9b2deeff1eefa93bdacbf3fbbd7b6757cddb7ae5b3f9b7af9c3bbff7e7f6ddef9f2dff7f17997ea6867675c29fcbe6bf725efbffe1507589bfd47a3bf7b6f5dfde50776fd94fe772d2c7b6b58baf554de55c176f27efa6fdcff7f17689bafa7f7c7bf4fd5fb9b05c2f4ed785f17ac9779feeaf1f5bbdadfc42ebad367fdcf7ad", + "miner": "0x4838b106fce9647bdf1e7877bf73ce8b0bad5f97", + "mixHash": "0x7e53d2d6772895d024eb00da80213aec81fb4a15bec34a5a39403ad6162274af", + "nonce": "0x0000000000000000", + "number": "0x1606672", + "parentBeaconBlockRoot": "0xd9ef51c8f4155f238ba66df0d35a4d0a6bb043c0dacb5c5dbd5a231bbd4c8a01", + "parentHash": "0x37b527c98c86436f292d4e19fac3aba6d8c7768684ea972f50adc305fd9a1475", + "receiptsRoot": "0x2abab67c41b350435eb34f9dc0478dd7d262f35544cecf62a85af2da075bd38d", + "requestsHash": "0xe3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", + "sha3Uncles": "0x1dcc4de8dec75d7aab85b567b6ccd41ad312451b948a7413f0a142fd40d49347", + "size": "0x29e6c", + "stateRoot": "0x5159c56472adff9a760275ac63524a71f5645ede822a5547dd9ad333586d5157", + "timestamp": "0x6895a93f", + "transactions": [], + "transactionsRoot": "0xfb0b9f5b28bc927db98d82e18070d2b17434c31bd2773c5dd699e96fa76a34cd", + "uncles": [], + "withdrawals": [], + "withdrawalsRoot": "0x531480435633d56a52433b33f41ac9322f51a2df3364c4c112236fc6ac583118" + }"#; + + // Deserialize the JSON into a Block + let block: Block = serde_json::from_str(json_input).expect("Failed to deserialize block"); + + // Serialize it back to JSON + let serialized = serde_json::to_string(&block).expect("Failed to serialize block"); + + // Deserialize again to ensure roundtrip consistency + let block_roundtrip: Block = + serde_json::from_str(&serialized).expect("Failed to deserialize roundtrip block"); + + // Verify that deserializing and serializing leads to the same result + assert_eq!(block, block_roundtrip); + } +} diff --git a/substrate/frame/revive/src/evm/api/signature.rs b/substrate/frame/revive/src/evm/api/signature.rs index de4ac428ffe4e..21cb943385b6a 100644 --- a/substrate/frame/revive/src/evm/api/signature.rs +++ b/substrate/frame/revive/src/evm/api/signature.rs @@ -42,6 +42,8 @@ impl TransactionUnsigned { match tx { TransactionSigned::TransactionLegacySigned(signed) => Self::TransactionLegacyUnsigned(signed.transaction_legacy_unsigned), + TransactionSigned::Transaction7702Signed(signed) => + Self::Transaction7702Unsigned(signed.transaction_7702_unsigned), TransactionSigned::Transaction4844Signed(signed) => Self::Transaction4844Unsigned(signed.transaction_4844_unsigned), TransactionSigned::Transaction1559Signed(signed) => @@ -58,6 +60,15 @@ impl TransactionUnsigned { let recovery_id = signature[64]; match self { + TransactionUnsigned::Transaction7702Unsigned(transaction_7702_unsigned) => + Transaction7702Signed { + transaction_7702_unsigned, + r, + s, + v: None, + y_parity: U256::from(recovery_id), + } + .into(), TransactionUnsigned::Transaction2930Unsigned(transaction_2930_unsigned) => Transaction2930Signed { transaction_2930_unsigned, @@ -108,6 +119,7 @@ impl TransactionSigned { use TransactionSigned::*; let (r, s, v) = match self { TransactionLegacySigned(tx) => (tx.r, tx.s, tx.extract_recovery_id().ok_or(())?), + Transaction7702Signed(tx) => (tx.r, tx.s, tx.y_parity.try_into().map_err(|_| ())?), Transaction4844Signed(tx) => (tx.r, tx.s, tx.y_parity.try_into().map_err(|_| ())?), Transaction1559Signed(tx) => (tx.r, tx.s, tx.y_parity.try_into().map_err(|_| ())?), Transaction2930Signed(tx) => (tx.r, tx.s, tx.y_parity.try_into().map_err(|_| ())?), @@ -129,6 +141,11 @@ impl TransactionSigned { let tx = &tx.transaction_legacy_unsigned; s.append(tx); }, + Transaction7702Signed(tx) => { + let tx = &tx.transaction_7702_unsigned; + s.append(&tx.r#type.value()); + s.append(tx); + }, Transaction4844Signed(tx) => { let tx = &tx.transaction_4844_unsigned; s.append(&tx.r#type.value()); diff --git a/substrate/frame/revive/src/evm/api/type_id.rs b/substrate/frame/revive/src/evm/api/type_id.rs index c6e018a379b37..81cf44d857625 100644 --- a/substrate/frame/revive/src/evm/api/type_id.rs +++ b/substrate/frame/revive/src/evm/api/type_id.rs @@ -118,6 +118,7 @@ transaction_type!(TypeLegacy, 0); transaction_type!(TypeEip2930, 1); transaction_type!(TypeEip1559, 2); transaction_type!(TypeEip4844, 3); +transaction_type!(TypeEip7702, 4); #[test] fn transaction_type() { diff --git a/substrate/frame/revive/src/evm/runtime.rs b/substrate/frame/revive/src/evm/runtime.rs index 48380f83899bd..5aed60859485c 100644 --- a/substrate/frame/revive/src/evm/runtime.rs +++ b/substrate/frame/revive/src/evm/runtime.rs @@ -294,6 +294,23 @@ pub trait EthExtra { InvalidTransaction::Call })?; + // Check transaction type and reject unsupported transaction types + match &tx { + crate::evm::api::TransactionSigned::Transaction1559Signed(_) | + crate::evm::api::TransactionSigned::Transaction2930Signed(_) | + crate::evm::api::TransactionSigned::TransactionLegacySigned(_) => { + // Supported transaction types, continue processing + }, + crate::evm::api::TransactionSigned::Transaction7702Signed(_) => { + log::debug!(target: LOG_TARGET, "EIP-7702 transactions are not supported"); + return Err(InvalidTransaction::Call); + }, + crate::evm::api::TransactionSigned::Transaction4844Signed(_) => { + log::debug!(target: LOG_TARGET, "EIP-4844 transactions are not supported"); + return Err(InvalidTransaction::Call); + }, + } + let signer_addr = tx.recover_eth_address().map_err(|err| { log::debug!(target: LOG_TARGET, "Failed to recover signer: {err:?}"); InvalidTransaction::BadProof diff --git a/substrate/frame/revive/src/exec.rs b/substrate/frame/revive/src/exec.rs index ec277d562f825..4cd9c6d93dca0 100644 --- a/substrate/frame/revive/src/exec.rs +++ b/substrate/frame/revive/src/exec.rs @@ -61,6 +61,9 @@ use sp_runtime::{ #[cfg(test)] mod tests; +#[cfg(test)] +pub mod mock_ext; + pub type AccountIdOf = ::AccountId; pub type MomentOf = <::Time as Time>::Moment; pub type ExecResult = Result; @@ -474,6 +477,11 @@ pub trait Executable: Sized { /// The code hash of the executable. fn code_hash(&self) -> &H256; + + /// Returns true if the executable is a PVM blob. + fn is_pvm(&self) -> bool { + self.code().starts_with(&polkavm_common::program::BLOB_MAGIC) + } } /// The complete call stack of a contract execution. @@ -567,6 +575,13 @@ impl, Env> ExecutableOrPrecompile { } } + fn is_pvm(&self) -> bool { + match self { + Self::Executable(e) => e.is_pvm(), + _ => false, + } + } + fn as_precompile(&self) -> Option<&PrecompileInstance> { if let Self::Precompile { instance, .. } = self { Some(instance) @@ -1087,6 +1102,7 @@ where ) -> Result<(), ExecError> { let frame = self.top_frame(); let entry_point = frame.entry_point; + let is_pvm = executable.is_pvm(); if_tracing(|tracer| { tracer.enter_child_span( @@ -1157,12 +1173,14 @@ where >::inc_account_nonce(caller.account_id()?); } // The incremented refcount should be visible to the constructor. - >::increment_refcount( - *executable - .as_executable() - .expect("Precompiles cannot be instantiated; qed") - .code_hash(), - )?; + if is_pvm { + >::increment_refcount( + *executable + .as_executable() + .expect("Precompiles cannot be instantiated; qed") + .code_hash(), + )?; + } } // Every non delegate call or instantiate also optionally transfers the balance. @@ -1229,7 +1247,8 @@ where // The deposit we charge for a contract depends on the size of the immutable data. // Hence we need to delay charging the base deposit after execution. if entry_point == ExportedFunction::Constructor { - let deposit = frame.contract_info().update_base_deposit(code_deposit); + let contract_info = frame.contract_info(); + let deposit = contract_info.update_base_deposit(code_deposit); frame .nested_storage .charge_deposit(frame.account_id.clone(), StorageDeposit::Charge(deposit)); @@ -2075,6 +2094,8 @@ mod sealing { use super::*; pub trait Sealed {} - impl<'a, T: Config, E> Sealed for Stack<'a, T, E> {} + + #[cfg(test)] + impl sealing::Sealed for mock_ext::MockExt {} } diff --git a/substrate/frame/revive/src/exec/mock_ext.rs b/substrate/frame/revive/src/exec/mock_ext.rs new file mode 100644 index 0000000000000..63b10c60eedda --- /dev/null +++ b/substrate/frame/revive/src/exec/mock_ext.rs @@ -0,0 +1,259 @@ +// This file is part of Substrate. + +// Copyright (C) Parity Technologies (UK) Ltd. +// SPDX-License-Identifier: Apache-2.0 + +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#![cfg(test)] + +use crate::{ + exec::{AccountIdOf, ExecError, Ext, Key, Origin, PrecompileExt, PrecompileWithInfoExt}, + gas::GasMeter, + precompiles::Diff, + storage::{ContractInfo, WriteOutcome}, + transient_storage::TransientStorage, + Config, ExecReturnValue, ImmutableData, +}; +use alloc::vec::Vec; +use core::marker::PhantomData; +use frame_support::{dispatch::DispatchResult, weights::Weight}; +use sp_core::{H160, H256, U256}; +use sp_runtime::DispatchError; + +/// Mock implementation of the Ext trait that panics for all methods +pub struct MockExt { + gas_meter: GasMeter, + _phantom: PhantomData, +} + +impl PrecompileExt for MockExt { + type T = T; + + fn call( + &mut self, + _gas_limit: Weight, + _deposit_limit: U256, + _to: &H160, + _value: U256, + _input_data: Vec, + _allows_reentry: bool, + _read_only: bool, + ) -> Result<(), ExecError> { + panic!("MockExt::call") + } + + fn get_transient_storage(&self, _key: &Key) -> Option> { + panic!("MockExt::get_transient_storage") + } + + fn get_transient_storage_size(&self, _key: &Key) -> Option { + panic!("MockExt::get_transient_storage_size") + } + + fn set_transient_storage( + &mut self, + _key: &Key, + _value: Option>, + _take_old: bool, + ) -> Result { + panic!("MockExt::set_transient_storage") + } + + fn caller(&self) -> Origin { + panic!("MockExt::caller") + } + + fn origin(&self) -> &Origin { + panic!("MockExt::origin") + } + + fn code_hash(&self, _address: &H160) -> H256 { + panic!("MockExt::code_hash") + } + + fn code_size(&self, _address: &H160) -> u64 { + panic!("MockExt::code_size") + } + + fn caller_is_origin(&self) -> bool { + panic!("MockExt::caller_is_origin") + } + + fn caller_is_root(&self) -> bool { + panic!("MockExt::caller_is_root") + } + + fn account_id(&self) -> &AccountIdOf { + panic!("MockExt::account_id") + } + + fn balance(&self) -> U256 { + panic!("MockExt::balance") + } + + fn balance_of(&self, _address: &H160) -> U256 { + panic!("MockExt::balance_of") + } + + fn value_transferred(&self) -> U256 { + panic!("MockExt::value_transferred") + } + + fn now(&self) -> U256 { + panic!("MockExt::now") + } + + fn minimum_balance(&self) -> U256 { + panic!("MockExt::minimum_balance") + } + + fn deposit_event(&mut self, _topics: Vec, _data: Vec) { + panic!("MockExt::deposit_event") + } + + fn block_number(&self) -> U256 { + panic!("MockExt::block_number") + } + + fn block_hash(&self, _block_number: U256) -> Option { + panic!("MockExt::block_hash") + } + + fn block_author(&self) -> Option { + panic!("MockExt::block_author") + } + + fn max_value_size(&self) -> u32 { + panic!("MockExt::max_value_size") + } + + fn get_weight_price(&self, _weight: Weight) -> U256 { + panic!("MockExt::get_weight_price") + } + + fn gas_meter(&self) -> &GasMeter { + &self.gas_meter + } + + fn gas_meter_mut(&mut self) -> &mut GasMeter { + &mut self.gas_meter + } + + fn ecdsa_recover( + &self, + _signature: &[u8; 65], + _message_hash: &[u8; 32], + ) -> Result<[u8; 33], ()> { + panic!("MockExt::ecdsa_recover") + } + + fn sr25519_verify(&self, _signature: &[u8; 64], _message: &[u8], _pub_key: &[u8; 32]) -> bool { + panic!("MockExt::sr25519_verify") + } + + fn ecdsa_to_eth_address(&self, _pk: &[u8; 33]) -> Result<[u8; 20], ()> { + panic!("MockExt::ecdsa_to_eth_address") + } + + #[cfg(any(test, feature = "runtime-benchmarks"))] + fn contract_info(&mut self) -> &mut ContractInfo { + panic!("MockExt::contract_info") + } + + #[cfg(any(feature = "runtime-benchmarks", test))] + fn transient_storage(&mut self) -> &mut TransientStorage { + panic!("MockExt::transient_storage") + } + + fn is_read_only(&self) -> bool { + panic!("MockExt::is_read_only") + } + + fn last_frame_output(&self) -> &ExecReturnValue { + panic!("MockExt::last_frame_output") + } + + fn last_frame_output_mut(&mut self) -> &mut ExecReturnValue { + panic!("MockExt::last_frame_output_mut") + } +} + +impl PrecompileWithInfoExt for MockExt { + fn get_storage(&mut self, _key: &Key) -> Option> { + panic!("MockExt::get_storage") + } + + fn get_storage_size(&mut self, _key: &Key) -> Option { + panic!("MockExt::get_storage_size") + } + + fn set_storage( + &mut self, + _key: &Key, + _value: Option>, + _take_old: bool, + ) -> Result { + panic!("MockExt::set_storage") + } + + fn charge_storage(&mut self, _diff: &Diff) {} + + fn instantiate( + &mut self, + _gas_limit: Weight, + _deposit_limit: U256, + _code: H256, + _value: U256, + _input_data: Vec, + _salt: Option<&[u8; 32]>, + ) -> Result { + panic!("MockExt::instantiate") + } +} + +impl Ext for MockExt { + fn delegate_call( + &mut self, + _gas_limit: Weight, + _deposit_limit: U256, + _address: H160, + _input_data: Vec, + ) -> Result<(), ExecError> { + panic!("MockExt::delegate_call") + } + + fn terminate(&mut self, _beneficiary: &H160) -> DispatchResult { + panic!("MockExt::terminate") + } + + fn own_code_hash(&mut self) -> &H256 { + panic!("MockExt::own_code_hash") + } + + fn set_code_hash(&mut self, _hash: H256) -> DispatchResult { + panic!("MockExt::set_code_hash") + } + + fn immutable_data_len(&mut self) -> u32 { + panic!("MockExt::immutable_data_len") + } + + fn get_immutable_data(&mut self) -> Result { + panic!("MockExt::get_immutable_data") + } + + fn set_immutable_data(&mut self, _data: ImmutableData) -> Result<(), DispatchError> { + panic!("MockExt::set_immutable_data") + } +} diff --git a/substrate/frame/revive/src/exec/tests.rs b/substrate/frame/revive/src/exec/tests.rs index 381abc7c26117..9b1995e2db7ef 100644 --- a/substrate/frame/revive/src/exec/tests.rs +++ b/substrate/frame/revive/src/exec/tests.rs @@ -176,6 +176,10 @@ impl Executable for MockExecutable { self.code_hash.as_ref() } + fn is_pvm(&self) -> bool { + true + } + fn code_hash(&self) -> &H256 { &self.code_hash } diff --git a/substrate/frame/revive/src/impl_fungibles.rs b/substrate/frame/revive/src/impl_fungibles.rs index 55c42a5091098..404690c6765b4 100644 --- a/substrate/frame/revive/src/impl_fungibles.rs +++ b/substrate/frame/revive/src/impl_fungibles.rs @@ -302,13 +302,14 @@ mod tests { AccountInfoOf, Code, }; use frame_support::assert_ok; + const ERC20_PVM_CODE: &[u8] = include_bytes!("../fixtures/erc20/erc20.polkavm"); #[test] fn call_erc20_contract() { ExtBuilder::default().existential_deposit(1).build().execute_with(|| { let _ = <::Currency as fungible::Mutate<_>>::set_balance(&ALICE, 1_000_000); - let code = include_bytes!("../fixtures/contracts/erc20.polkavm").to_vec(); + let code = ERC20_PVM_CODE.to_vec(); let amount = EU256::from(1000); let constructor_data = sol_data::Uint::<256>::abi_encode(&amount); let Contract { addr, .. } = BareInstantiateBuilder::::bare_instantiate( @@ -333,7 +334,7 @@ mod tests { ExtBuilder::default().existential_deposit(1).build().execute_with(|| { let _ = <::Currency as fungible::Mutate<_>>::set_balance(&ALICE, 1_000_000); - let code = include_bytes!("../fixtures/contracts/erc20.polkavm").to_vec(); + let code = ERC20_PVM_CODE.to_vec(); let amount = 1000; let constructor_data = sol_data::Uint::<256>::abi_encode(&EU256::from(amount)); let Contract { addr, .. } = BareInstantiateBuilder::::bare_instantiate( @@ -353,7 +354,7 @@ mod tests { ExtBuilder::default().existential_deposit(1).build().execute_with(|| { let _ = <::Currency as fungible::Mutate<_>>::set_balance(&ALICE, 1_000_000); - let code = include_bytes!("../fixtures/contracts/erc20.polkavm").to_vec(); + let code = ERC20_PVM_CODE.to_vec(); let amount = 1000; let constructor_data = sol_data::Uint::<256>::abi_encode(&EU256::from(amount)); let Contract { addr, .. } = BareInstantiateBuilder::::bare_instantiate( @@ -371,7 +372,7 @@ mod tests { ExtBuilder::default().existential_deposit(1).build().execute_with(|| { let _ = <::Currency as fungible::Mutate<_>>::set_balance(&ALICE, 1_000_000); - let code = include_bytes!("../fixtures/contracts/erc20.polkavm").to_vec(); + let code = ERC20_PVM_CODE.to_vec(); let amount = 1000; let constructor_data = sol_data::Uint::<256>::abi_encode(&(EU256::from(amount * 2))); let Contract { addr, .. } = BareInstantiateBuilder::::bare_instantiate( @@ -407,7 +408,7 @@ mod tests { &checking_account, 1_000_000, ); - let code = include_bytes!("../fixtures/contracts/erc20.polkavm").to_vec(); + let code = ERC20_PVM_CODE.to_vec(); let amount = 1000; let constructor_data = sol_data::Uint::<256>::abi_encode(&EU256::from(amount)); // We're instantiating the contract with the `CheckingAccount` so it has `amount` in it. diff --git a/substrate/frame/revive/src/lib.rs b/substrate/frame/revive/src/lib.rs index 8b2d7f76e716a..11c69bfdfe9e3 100644 --- a/substrate/frame/revive/src/lib.rs +++ b/substrate/frame/revive/src/lib.rs @@ -102,7 +102,7 @@ pub use sp_runtime; pub use weights::WeightInfo; #[cfg(doc)] -pub use crate::vm::SyscallDoc; +pub use crate::vm::pvm::SyscallDoc; pub type BalanceOf = <::Currency as Inspect<::AccountId>>::Balance; @@ -1135,9 +1135,9 @@ where if_tracing(|t| t.instantiate_code(&code, salt.as_ref())); let (executable, upload_deposit) = match code { - Code::Upload(code) => { + Code::Upload(code) if code.starts_with(&polkavm_common::program::BLOB_MAGIC) => { let upload_account = T::UploadOrigin::ensure_origin(origin)?; - let (executable, upload_deposit) = Self::try_upload_code( + let (executable, upload_deposit) = Self::try_upload_pvm_code( upload_account, code, storage_deposit_limit, @@ -1146,6 +1146,7 @@ where storage_deposit_limit.saturating_reduce(upload_deposit); (executable, upload_deposit) }, + Code::Upload(_code) => return Err(>::CodeRejected.into()), Code::Existing(code_hash) => (ContractBlob::from_storage(code_hash, &mut gas_meter)?, Default::default()), }; @@ -1245,10 +1246,10 @@ where err == Error::::StorageDepositLimitExhausted.into() { let balance = Self::evm_balance(&from); - return Err(EthTransactError::Message( - format!("insufficient funds for gas * price + value: address {from:?} have {balance} (supplied gas {})", - tx.gas.unwrap_or_default())) - ); + return Err(EthTransactError::Message(format!( + "insufficient funds for gas * price + value: address {from:?} have {balance} (supplied gas {})", + tx.gas.unwrap_or_default() + ))); } return Err(EthTransactError::Message(format!( @@ -1331,16 +1332,20 @@ where // A contract deployment None => { // Extract code and data from the input. - let (code, data) = match polkavm::ProgramBlob::blob_length(&input) { - Some(blob_len) => blob_len - .try_into() - .ok() - .and_then(|blob_len| (input.split_at_checked(blob_len))) - .unwrap_or_else(|| (&input[..], &[][..])), - _ => { - log::debug!(target: LOG_TARGET, "Failed to extract polkavm blob length"); - (&input[..], &[][..]) - }, + let (code, data) = if input.starts_with(&polkavm_common::program::BLOB_MAGIC) { + match polkavm::ProgramBlob::blob_length(&input) { + Some(blob_len) => blob_len + .try_into() + .ok() + .and_then(|blob_len| (input.split_at_checked(blob_len))) + .unwrap_or_else(|| (&input[..], &[][..])), + _ => { + log::debug!(target: LOG_TARGET, "Failed to extract polkavm blob length"); + (&input[..], &[][..]) + }, + } + } else { + return Err(EthTransactError::Message("Invalid transaction".into())); }; // Dry run the call. @@ -1501,7 +1506,8 @@ where storage_deposit_limit: BalanceOf, ) -> CodeUploadResult> { let origin = T::UploadOrigin::ensure_origin(origin)?; - let (module, deposit) = Self::try_upload_code(origin, code, storage_deposit_limit, false)?; + let (module, deposit) = + Self::try_upload_pvm_code(origin, code, storage_deposit_limit, false)?; Ok(CodeUploadReturnValue { code_hash: *module.code_hash(), deposit }) } @@ -1528,13 +1534,13 @@ where } /// Uploads new code and returns the Vm binary contract blob and deposit amount collected. - fn try_upload_code( + fn try_upload_pvm_code( origin: T::AccountId, code: Vec, storage_deposit_limit: BalanceOf, skip_transfer: bool, ) -> Result<(ContractBlob, BalanceOf), DispatchError> { - let mut module = ContractBlob::from_code(code, origin)?; + let mut module = ContractBlob::from_pvm_code(code, origin)?; let deposit = module.store_code(skip_transfer)?; ensure!(storage_deposit_limit >= deposit, >::StorageDepositLimitExhausted); Ok((module, deposit)) diff --git a/substrate/frame/revive/src/tests.rs b/substrate/frame/revive/src/tests.rs index 0cee2e3d9499a..9b3a3c10a932c 100644 --- a/substrate/frame/revive/src/tests.rs +++ b/substrate/frame/revive/src/tests.rs @@ -17,49 +17,24 @@ mod pallet_dummy; mod precompiles; +mod pvm; -use self::test_utils::{ensure_stored, expected_deposit}; use crate::{ - self as pallet_revive, - address::{create1, create2, AddressMapper}, - evm::{runtime::GAS_PRICE, CallTrace, CallTracer, CallType, GenericTransaction}, - exec::Key, - limits, - storage::DeletionQueueManager, - test_utils::{builder::Contract, *}, - tests::test_utils::{get_contract, get_contract_checked}, - tracing::trace, - weights::WeightInfo, - AccountId32Mapper, AccountInfo, AccountInfoOf, BalanceOf, BalanceWithDust, BumpNonce, Code, - CodeInfoOf, Config, ContractInfo, DeletionQueueCounter, DepositLimit, Error, EthTransactError, - HoldReason, Origin, Pallet, PristineCode, StorageDeposit, H160, + self as pallet_revive, test_utils::*, AccountId32Mapper, BalanceOf, BalanceWithDust, + CodeInfoOf, Config, Origin, Pallet, }; -use assert_matches::assert_matches; -use codec::Encode; use frame_support::{ - assert_err, assert_err_ignore_postinfo, assert_noop, assert_ok, derive_impl, + assert_ok, derive_impl, pallet_prelude::EnsureOrigin, parameter_types, - storage::child, - traits::{ - fungible::{BalancedHold, Inspect, Mutate, MutateHold}, - tokens::Preservation, - ConstU32, ConstU64, FindAuthor, OnIdle, OnInitialize, StorageVersion, - }, - weights::{constants::WEIGHT_REF_TIME_PER_SECOND, FixedFee, IdentityFee, Weight, WeightMeter}, + traits::{ConstU32, ConstU64, FindAuthor, StorageVersion}, + weights::{constants::WEIGHT_REF_TIME_PER_SECOND, FixedFee, IdentityFee, Weight}, }; -use frame_system::{EventRecord, Phase}; -use pallet_revive_fixtures::compile_module; -use pallet_revive_uapi::{ReturnErrorCode as RuntimeReturnCode, ReturnFlags}; use pallet_transaction_payment::{ConstFeeMultiplier, Multiplier}; -use pretty_assertions::{assert_eq, assert_ne}; -use sp_core::{Get, U256}; -use sp_io::hashing::blake2_256; use sp_keystore::{testing::MemoryKeystore, KeystoreExt}; use sp_runtime::{ - testing::H256, - traits::{BlakeTwo256, Convert, IdentityLookup, One, Zero}, - AccountId32, BuildStorage, DispatchError, Perbill, TokenError, + traits::{BlakeTwo256, Convert, IdentityLookup, One}, + AccountId32, BuildStorage, Perbill, }; type Block = frame_system::mocking::MockBlock; @@ -78,12 +53,14 @@ frame_support::construct_runtime!( } ); +#[macro_export] macro_rules! assert_return_code { ( $x:expr , $y:expr $(,)? ) => {{ assert_eq!(u32::from_le_bytes($x.data[..].try_into().unwrap()), $y as u32); }}; } +#[macro_export] macro_rules! assert_refcount { ( $code_hash:expr , $should:expr $(,)? ) => {{ let is = crate::CodeInfoOf::::get($code_hash).map(|m| m.refcount()).unwrap(); @@ -194,7 +171,7 @@ pub mod test_utils { } } -mod builder { +pub(crate) mod builder { use super::Test; use crate::{ test_utils::{builder::*, ALICE}, @@ -457,4844 +434,3 @@ impl Default for Origin { Self::Signed(ALICE) } } - -#[test] -fn transfer_with_dust_works() { - struct TestCase { - description: &'static str, - from_balance: BalanceWithDust, - to_balance: BalanceWithDust, - amount: BalanceWithDust, - expected_from_balance: BalanceWithDust, - expected_to_balance: BalanceWithDust, - total_issuance_diff: i64, - } - - let plank: u32 = ::NativeToEthRatio::get(); - - let test_cases = vec![ - TestCase { - description: "without dust", - from_balance: BalanceWithDust::new_unchecked::(100, 0), - to_balance: BalanceWithDust::new_unchecked::(0, 0), - amount: BalanceWithDust::new_unchecked::(1, 0), - expected_from_balance: BalanceWithDust::new_unchecked::(99, 0), - expected_to_balance: BalanceWithDust::new_unchecked::(1, 0), - total_issuance_diff: 0, - }, - TestCase { - description: "with dust", - from_balance: BalanceWithDust::new_unchecked::(100, 0), - to_balance: BalanceWithDust::new_unchecked::(0, 0), - amount: BalanceWithDust::new_unchecked::(1, 10), - expected_from_balance: BalanceWithDust::new_unchecked::(98, plank - 10), - expected_to_balance: BalanceWithDust::new_unchecked::(1, 10), - total_issuance_diff: 1, - }, - TestCase { - description: "just dust", - from_balance: BalanceWithDust::new_unchecked::(100, 0), - to_balance: BalanceWithDust::new_unchecked::(0, 0), - amount: BalanceWithDust::new_unchecked::(0, 10), - expected_from_balance: BalanceWithDust::new_unchecked::(99, plank - 10), - expected_to_balance: BalanceWithDust::new_unchecked::(0, 10), - total_issuance_diff: 1, - }, - TestCase { - description: "with existing dust", - from_balance: BalanceWithDust::new_unchecked::(100, 5), - to_balance: BalanceWithDust::new_unchecked::(0, plank - 5), - amount: BalanceWithDust::new_unchecked::(1, 10), - expected_from_balance: BalanceWithDust::new_unchecked::(98, plank - 5), - expected_to_balance: BalanceWithDust::new_unchecked::(2, 5), - total_issuance_diff: 0, - }, - TestCase { - description: "with enough existing dust", - from_balance: BalanceWithDust::new_unchecked::(100, 10), - to_balance: BalanceWithDust::new_unchecked::(0, plank - 10), - amount: BalanceWithDust::new_unchecked::(1, 10), - expected_from_balance: BalanceWithDust::new_unchecked::(99, 0), - expected_to_balance: BalanceWithDust::new_unchecked::(2, 0), - total_issuance_diff: -1, - }, - TestCase { - description: "receiver dust less than 1 plank", - from_balance: BalanceWithDust::new_unchecked::(100, plank / 10), - to_balance: BalanceWithDust::new_unchecked::(0, plank / 2), - amount: BalanceWithDust::new_unchecked::(1, plank / 10 * 3), - expected_from_balance: BalanceWithDust::new_unchecked::(98, plank / 10 * 8), - expected_to_balance: BalanceWithDust::new_unchecked::(1, plank / 10 * 8), - total_issuance_diff: 1, - }, - ]; - - for TestCase { - description, - from_balance, - to_balance, - amount, - expected_from_balance, - expected_to_balance, - total_issuance_diff, - } in test_cases.into_iter() - { - ExtBuilder::default().build().execute_with(|| { - test_utils::set_balance_with_dust(&ALICE_ADDR, from_balance); - test_utils::set_balance_with_dust(&BOB_ADDR, to_balance); - - let total_issuance = ::Currency::total_issuance(); - let evm_value = Pallet::::convert_native_to_evm(amount); - - let (value, dust) = amount.deconstruct(); - assert_eq!(Pallet::::has_dust(evm_value), !dust.is_zero()); - assert_eq!(Pallet::::has_balance(evm_value), !value.is_zero()); - - let result = - builder::bare_call(BOB_ADDR).evm_value(evm_value).build_and_unwrap_result(); - assert_eq!(result, Default::default(), "{description} tx failed"); - - assert_eq!( - Pallet::::evm_balance(&ALICE_ADDR), - Pallet::::convert_native_to_evm(expected_from_balance), - "{description}: invalid from balance" - ); - - assert_eq!( - Pallet::::evm_balance(&BOB_ADDR), - Pallet::::convert_native_to_evm(expected_to_balance), - "{description}: invalid to balance" - ); - - assert_eq!( - total_issuance as i64 - total_issuance_diff, - ::Currency::total_issuance() as i64, - "{description}: total issuance should match" - ); - }); - } -} - -#[test] -fn eth_call_transfer_with_dust_works() { - let (binary, _) = compile_module("dummy").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); - - let balance = - Pallet::::convert_native_to_evm(BalanceWithDust::new_unchecked::(100, 10)); - assert_ok!(builder::eth_call(addr).value(balance).build()); - - assert_eq!(Pallet::::evm_balance(&addr), balance); - }); -} - -#[test] -fn contract_call_transfer_with_dust_works() { - let (binary_caller, _code_hash_caller) = compile_module("call_with_value").unwrap(); - let (binary_callee, _code_hash_callee) = compile_module("dummy").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let Contract { addr: addr_caller, .. } = - builder::bare_instantiate(Code::Upload(binary_caller)) - .native_value(200) - .build_and_unwrap_contract(); - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); - - let balance = - Pallet::::convert_native_to_evm(BalanceWithDust::new_unchecked::(100, 10)); - assert_ok!(builder::call(addr_caller).data((balance, addr_callee).encode()).build()); - - assert_eq!(Pallet::::evm_balance(&addr_callee), balance); - }); -} - -#[test] -fn deposit_limit_enforced_on_plain_transfer() { - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let _ = ::Currency::set_balance(&BOB, 1_000_000); - - // sending balance to a new account should fail when the limit is lower than the ed - let result = builder::bare_call(CHARLIE_ADDR) - .native_value(1) - .storage_deposit_limit(190.into()) - .build(); - assert_err!(result.result, >::StorageDepositLimitExhausted); - assert_eq!(result.storage_deposit, StorageDeposit::Charge(0)); - assert_eq!(test_utils::get_balance(&CHARLIE), 0); - - // works when the account is prefunded - let result = builder::bare_call(BOB_ADDR) - .native_value(1) - .storage_deposit_limit(0.into()) - .build(); - assert_ok!(result.result); - assert_eq!(result.storage_deposit, StorageDeposit::Charge(0)); - assert_eq!(test_utils::get_balance(&BOB), 1_000_001); - - // also works allowing enough deposit - let result = builder::bare_call(CHARLIE_ADDR) - .native_value(1) - .storage_deposit_limit(200.into()) - .build(); - assert_ok!(result.result); - assert_eq!(result.storage_deposit, StorageDeposit::Charge(200)); - assert_eq!(test_utils::get_balance(&CHARLIE), 201); - }); -} - -#[test] -fn instantiate_and_call_and_deposit_event() { - let (binary, code_hash) = compile_module("event_and_return_on_deploy").unwrap(); - - ExtBuilder::default().existential_deposit(1).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let min_balance = Contracts::min_balance(); - let value = 100; - - // We determine the storage deposit limit after uploading because it depends on ALICEs - // free balance which is changed by uploading a module. - assert_ok!(Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - binary, - deposit_limit::(), - )); - - // Drop previous events - initialize_block(2); - - // Check at the end to get hash on error easily - let Contract { addr, account_id } = builder::bare_instantiate(Code::Existing(code_hash)) - .native_value(value) - .build_and_unwrap_contract(); - assert!(AccountInfoOf::::contains_key(&addr)); - - let hold_balance = test_utils::contract_base_deposit(&addr); - - assert_eq!( - System::events(), - vec![ - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::System(frame_system::Event::NewAccount { - account: account_id.clone() - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Endowed { - account: account_id.clone(), - free_balance: min_balance, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { - from: ALICE, - to: account_id.clone(), - amount: min_balance, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { - from: ALICE, - to: account_id.clone(), - amount: value, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Contracts(crate::Event::ContractEmitted { - contract: addr, - data: vec![1, 2, 3, 4], - topics: vec![H256::repeat_byte(42)], - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Contracts(crate::Event::Instantiated { - deployer: ALICE_ADDR, - contract: addr - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { - reason: ::RuntimeHoldReason::Contracts( - HoldReason::StorageDepositReserve, - ), - source: ALICE, - dest: account_id.clone(), - transferred: hold_balance, - }), - topics: vec![], - }, - ] - ); - }); -} - -#[test] -fn create1_address_from_extrinsic() { - let (binary, code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().existential_deposit(1).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - assert_ok!(Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - binary.clone(), - deposit_limit::(), - )); - - assert_eq!(System::account_nonce(&ALICE), 0); - System::inc_account_nonce(&ALICE); - - for nonce in 1..3 { - let Contract { addr, .. } = builder::bare_instantiate(Code::Existing(code_hash)) - .salt(None) - .build_and_unwrap_contract(); - assert!(AccountInfoOf::::contains_key(&addr)); - assert_eq!( - addr, - create1(&::AddressMapper::to_address(&ALICE), nonce - 1) - ); - } - assert_eq!(System::account_nonce(&ALICE), 3); - - for nonce in 3..6 { - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary.clone())) - .salt(None) - .build_and_unwrap_contract(); - assert!(AccountInfoOf::::contains_key(&addr)); - assert_eq!( - addr, - create1(&::AddressMapper::to_address(&ALICE), nonce - 1) - ); - } - assert_eq!(System::account_nonce(&ALICE), 6); - }); -} - -#[test] -fn deposit_event_max_value_limit() { - let (binary, _code_hash) = compile_module("event_size").unwrap(); - - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - // Create - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(30_000) - .build_and_unwrap_contract(); - - // Call contract with allowed storage value. - assert_ok!(builder::call(addr) - .gas_limit(GAS_LIMIT.set_ref_time(GAS_LIMIT.ref_time() * 2)) // we are copying a huge buffer, - .data(limits::PAYLOAD_BYTES.encode()) - .build()); - - // Call contract with too large a storage value. - assert_err_ignore_postinfo!( - builder::call(addr).data((limits::PAYLOAD_BYTES + 1).encode()).build(), - Error::::ValueTooLarge, - ); - }); -} - -// Fail out of fuel (ref_time weight) in the engine. -#[test] -fn run_out_of_fuel_engine() { - let (binary, _code_hash) = compile_module("run_out_of_gas").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(100 * min_balance) - .build_and_unwrap_contract(); - - // Call the contract with a fixed gas limit. It must run out of gas because it just - // loops forever. - assert_err_ignore_postinfo!( - builder::call(addr) - .gas_limit(Weight::from_parts(10_000_000_000, u64::MAX)) - .build(), - Error::::OutOfGas, - ); - }); -} - -// Fail out of fuel (ref_time weight) in the host. -#[test] -fn run_out_of_fuel_host() { - use crate::precompiles::Precompile; - use alloy_core::sol_types::SolInterface; - use precompiles::{INoInfo, NoInfo}; - - let precompile_addr = H160(NoInfo::::MATCHER.base_address()); - let input = INoInfo::INoInfoCalls::consumeMaxGas(INoInfo::consumeMaxGasCall {}).abi_encode(); - - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); - let result = builder::bare_call(precompile_addr).data(input).build().result; - assert_err!(result, >::OutOfGas); - }); -} - -#[test] -fn gas_syncs_work() { - let (code, _code_hash) = compile_module("caller_is_origin_n").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let contract = builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - let result = builder::bare_call(contract.addr).data(0u32.encode()).build(); - assert_ok!(result.result); - let engine_consumed_noop = result.gas_consumed.ref_time(); - - let result = builder::bare_call(contract.addr).data(1u32.encode()).build(); - assert_ok!(result.result); - let gas_consumed_once = result.gas_consumed.ref_time(); - let host_consumed_once = ::WeightInfo::seal_caller_is_origin().ref_time(); - let engine_consumed_once = gas_consumed_once - host_consumed_once - engine_consumed_noop; - - let result = builder::bare_call(contract.addr).data(2u32.encode()).build(); - assert_ok!(result.result); - let gas_consumed_twice = result.gas_consumed.ref_time(); - let host_consumed_twice = host_consumed_once * 2; - let engine_consumed_twice = gas_consumed_twice - host_consumed_twice - engine_consumed_noop; - - // Second contract just repeats first contract's instructions twice. - // If runtime syncs gas with the engine properly, this should pass. - assert_eq!(engine_consumed_twice, engine_consumed_once * 2); - }); -} - -/// Check that contracts with the same account id have different trie ids. -/// Check the `Nonce` storage item for more information. -#[test] -fn instantiate_unique_trie_id() { - let (binary, code_hash) = compile_module("self_destruct").unwrap(); - - ExtBuilder::default().existential_deposit(500).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, deposit_limit::()) - .unwrap(); - - // Instantiate the contract and store its trie id for later comparison. - let Contract { addr, .. } = - builder::bare_instantiate(Code::Existing(code_hash)).build_and_unwrap_contract(); - let trie_id = get_contract(&addr).trie_id; - - // Try to instantiate it again without termination should yield an error. - assert_err_ignore_postinfo!( - builder::instantiate(code_hash).build(), - >::DuplicateContract, - ); - - // Terminate the contract. - assert_ok!(builder::call(addr).build()); - - // Re-Instantiate after termination. - assert_ok!(builder::instantiate(code_hash).build()); - - // Trie ids shouldn't match or we might have a collision - assert_ne!(trie_id, get_contract(&addr).trie_id); - }); -} - -#[test] -fn storage_work() { - let (code, _code_hash) = compile_module("storage").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let min_balance = Contracts::min_balance(); - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - builder::bare_call(addr).build_and_unwrap_result(); - }); -} - -#[test] -fn storage_max_value_limit() { - let (binary, _code_hash) = compile_module("storage_size").unwrap(); - - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - // Create - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(30_000) - .build_and_unwrap_contract(); - get_contract(&addr); - - // Call contract with allowed storage value. - assert_ok!(builder::call(addr) - .gas_limit(GAS_LIMIT.set_ref_time(GAS_LIMIT.ref_time() * 2)) // we are copying a huge buffer - .data(limits::PAYLOAD_BYTES.encode()) - .build()); - - // Call contract with too large a storage value. - assert_err_ignore_postinfo!( - builder::call(addr).data((limits::PAYLOAD_BYTES + 1).encode()).build(), - Error::::ValueTooLarge, - ); - }); -} - -#[test] -fn clear_storage_on_zero_value() { - let (code, _code_hash) = compile_module("clear_storage_on_zero_value").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let min_balance = Contracts::min_balance(); - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - builder::bare_call(addr).build_and_unwrap_result(); - }); -} - -#[test] -fn transient_storage_work() { - let (code, _code_hash) = compile_module("transient_storage").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let min_balance = Contracts::min_balance(); - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - builder::bare_call(addr).build_and_unwrap_result(); - }); -} - -#[test] -fn transient_storage_limit_in_call() { - let (binary_caller, _code_hash_caller) = - compile_module("create_transient_storage_and_call").unwrap(); - let (binary_callee, _code_hash_callee) = compile_module("set_transient_storage").unwrap(); - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create both contracts: Constructors do nothing. - let Contract { addr: addr_caller, .. } = - builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); - - // Call contracts with storage values within the limit. - // Caller and Callee contracts each set a transient storage value of size 100. - assert_ok!(builder::call(addr_caller) - .data((100u32, 100u32, &addr_callee).encode()) - .build(),); - - // Call a contract with a storage value that is too large. - // Limit exceeded in the caller contract. - assert_err_ignore_postinfo!( - builder::call(addr_caller) - .data((4u32 * 1024u32, 200u32, &addr_callee).encode()) - .build(), - >::OutOfTransientStorage, - ); - - // Call a contract with a storage value that is too large. - // Limit exceeded in the callee contract. - assert_err_ignore_postinfo!( - builder::call(addr_caller) - .data((50u32, 4 * 1024u32, &addr_callee).encode()) - .build(), - >::ContractTrapped - ); - }); -} - -#[test] -fn deploy_and_call_other_contract() { - let (caller_binary, _caller_code_hash) = compile_module("caller_contract").unwrap(); - let (callee_binary, callee_code_hash) = compile_module("return_with_data").unwrap(); - let code_load_weight = crate::vm::code_load_weight(callee_binary.len() as u32); - - ExtBuilder::default().existential_deposit(1).build().execute_with(|| { - let min_balance = Contracts::min_balance(); - - // Create - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let Contract { addr: caller_addr, account_id: caller_account } = - builder::bare_instantiate(Code::Upload(caller_binary)) - .native_value(100_000) - .build_and_unwrap_contract(); - - let callee_addr = create2( - &caller_addr, - &callee_binary, - &[0, 1, 34, 51, 68, 85, 102, 119], // hard coded in binary - &[0u8; 32], - ); - let callee_account = ::AddressMapper::to_account_id(&callee_addr); - - Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - callee_binary, - deposit_limit::(), - ) - .unwrap(); - - // Drop previous events - initialize_block(2); - - // Call BOB contract, which attempts to instantiate and call the callee contract and - // makes various assertions on the results from those calls. - assert_ok!(builder::call(caller_addr) - .data( - (callee_code_hash, code_load_weight.ref_time(), code_load_weight.proof_size()) - .encode() - ) - .build()); - - assert_eq!( - System::events(), - vec![ - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::System(frame_system::Event::NewAccount { - account: callee_account.clone() - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Endowed { - account: callee_account.clone(), - free_balance: min_balance, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { - from: ALICE, - to: callee_account.clone(), - amount: min_balance, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { - from: caller_account.clone(), - to: callee_account.clone(), - amount: 32768 // hardcoded in binary - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { - from: caller_account.clone(), - to: callee_account.clone(), - amount: 32768, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { - reason: ::RuntimeHoldReason::Contracts( - HoldReason::StorageDepositReserve, - ), - source: ALICE, - dest: callee_account.clone(), - transferred: 555, - }), - topics: vec![], - }, - ] - ); - }); -} - -#[test] -fn delegate_call() { - let (caller_binary, _caller_code_hash) = compile_module("delegate_call").unwrap(); - let (callee_binary, _callee_code_hash) = compile_module("delegate_call_lib").unwrap(); - - ExtBuilder::default().existential_deposit(500).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Instantiate the 'caller' - let Contract { addr: caller_addr, .. } = - builder::bare_instantiate(Code::Upload(caller_binary)) - .native_value(300_000) - .build_and_unwrap_contract(); - - // Instantiate the 'callee' - let Contract { addr: callee_addr, .. } = - builder::bare_instantiate(Code::Upload(callee_binary)) - .native_value(100_000) - .build_and_unwrap_contract(); - - assert_ok!(builder::call(caller_addr) - .value(1337) - .data((callee_addr, u64::MAX, u64::MAX).encode()) - .build()); - }); -} - -#[test] -fn delegate_call_non_existant_is_noop() { - let (caller_binary, _caller_code_hash) = compile_module("delegate_call_simple").unwrap(); - - ExtBuilder::default().existential_deposit(500).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Instantiate the 'caller' - let Contract { addr: caller_addr, .. } = - builder::bare_instantiate(Code::Upload(caller_binary)) - .native_value(300_000) - .build_and_unwrap_contract(); - - assert_ok!(builder::call(caller_addr) - .value(1337) - .data((BOB_ADDR, u64::MAX, u64::MAX).encode()) - .build()); - - assert_eq!(test_utils::get_balance(&BOB_FALLBACK), 0); - }); -} - -#[test] -fn delegate_call_with_weight_limit() { - let (caller_binary, _caller_code_hash) = compile_module("delegate_call").unwrap(); - let (callee_binary, _callee_code_hash) = compile_module("delegate_call_lib").unwrap(); - - ExtBuilder::default().existential_deposit(500).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Instantiate the 'caller' - let Contract { addr: caller_addr, .. } = - builder::bare_instantiate(Code::Upload(caller_binary)) - .native_value(300_000) - .build_and_unwrap_contract(); - - // Instantiate the 'callee' - let Contract { addr: callee_addr, .. } = - builder::bare_instantiate(Code::Upload(callee_binary)) - .native_value(100_000) - .build_and_unwrap_contract(); - - // fails, not enough weight - assert_err!( - builder::bare_call(caller_addr) - .native_value(1337) - .data((callee_addr, 100u64, 100u64).encode()) - .build() - .result, - Error::::ContractTrapped, - ); - - assert_ok!(builder::call(caller_addr) - .value(1337) - .data((callee_addr, 500_000_000u64, 100_000u64).encode()) - .build()); - }); -} - -#[test] -fn delegate_call_with_deposit_limit() { - let (caller_binary, _caller_code_hash) = compile_module("delegate_call_deposit_limit").unwrap(); - let (callee_binary, _callee_code_hash) = compile_module("delegate_call_lib").unwrap(); - - ExtBuilder::default().existential_deposit(500).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Instantiate the 'caller' - let Contract { addr: caller_addr, .. } = - builder::bare_instantiate(Code::Upload(caller_binary)) - .native_value(300_000) - .build_and_unwrap_contract(); - - // Instantiate the 'callee' - let Contract { addr: callee_addr, .. } = - builder::bare_instantiate(Code::Upload(callee_binary)) - .native_value(100_000) - .build_and_unwrap_contract(); - - // Delegate call will write 1 storage and deposit of 2 (1 item) + 32 (bytes) is required. - // + 32 + 16 for blake2_128concat - // Fails, not enough deposit - let ret = builder::bare_call(caller_addr) - .native_value(1337) - .data((callee_addr, 81u64).encode()) - .build_and_unwrap_result(); - assert_return_code!(ret, RuntimeReturnCode::OutOfResources); - - assert_ok!(builder::call(caller_addr) - .value(1337) - .data((callee_addr, 82u64).encode()) - .build()); - }); -} - -#[test] -fn transfer_expendable_cannot_kill_account() { - let (binary, _code_hash) = compile_module("dummy").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Instantiate the BOB contract. - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(1_000) - .build_and_unwrap_contract(); - - // Check that the BOB contract has been instantiated. - get_contract(&addr); - - let account = ::AddressMapper::to_account_id(&addr); - let total_balance = ::Currency::total_balance(&account); - - assert_eq!( - test_utils::get_balance_on_hold(&HoldReason::StorageDepositReserve.into(), &account), - test_utils::contract_base_deposit(&addr) - ); - - // Some or the total balance is held, so it can't be transferred. - assert_err!( - <::Currency as Mutate>::transfer( - &account, - &ALICE, - total_balance, - Preservation::Expendable, - ), - TokenError::FundsUnavailable, - ); - - assert_eq!(::Currency::total_balance(&account), total_balance); - }); -} - -#[test] -fn cannot_self_destruct_through_draining() { - let (binary, _code_hash) = compile_module("drain").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let value = 1_000; - let min_balance = Contracts::min_balance(); - - // Instantiate the BOB contract. - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(value) - .build_and_unwrap_contract(); - let account = ::AddressMapper::to_account_id(&addr); - - // Check that the BOB contract has been instantiated. - get_contract(&addr); - - // Call BOB which makes it send all funds to the zero address - // The contract code asserts that the transfer fails with the correct error code - assert_ok!(builder::call(addr).build()); - - // Make sure the account wasn't remove by sending all free balance away. - assert_eq!( - ::Currency::total_balance(&account), - value + test_utils::contract_base_deposit(&addr) + min_balance, - ); - }); -} - -#[test] -fn cannot_self_destruct_through_storage_refund_after_price_change() { - let (binary, _code_hash) = compile_module("store_call").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let min_balance = Contracts::min_balance(); - - // Instantiate the BOB contract. - let contract = builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); - let info_deposit = test_utils::contract_base_deposit(&contract.addr); - - // Check that the contract has been instantiated and has the minimum balance - assert_eq!(get_contract(&contract.addr).total_deposit(), info_deposit); - assert_eq!(get_contract(&contract.addr).extra_deposit(), 0); - assert_eq!( - ::Currency::total_balance(&contract.account_id), - info_deposit + min_balance - ); - - // Create 100 (16 + 32 bytes for key for blake128 concat) bytes of storage with a - // price of per byte and a single storage item of price 2 - assert_ok!(builder::call(contract.addr).data(100u32.to_le_bytes().to_vec()).build()); - assert_eq!(get_contract(&contract.addr).total_deposit(), info_deposit + 100 + 16 + 32 + 2); - - // Increase the byte price and trigger a refund. This should not have any influence - // because the removal is pro rata and exactly those 100 bytes should have been - // removed as we didn't delete the key. - DEPOSIT_PER_BYTE.with(|c| *c.borrow_mut() = 500); - assert_ok!(builder::call(contract.addr).data(0u32.to_le_bytes().to_vec()).build()); - - // Make sure the account wasn't removed by the refund - assert_eq!( - ::Currency::total_balance(&contract.account_id), - get_contract(&contract.addr).total_deposit() + min_balance, - ); - // + 1 because due to fixed point arithmetic we can sometimes refund - // one unit to little - assert_eq!(get_contract(&contract.addr).extra_deposit(), 16 + 32 + 2 + 1); - }); -} - -#[test] -fn cannot_self_destruct_while_live() { - let (binary, _code_hash) = compile_module("self_destruct").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Instantiate the BOB contract. - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(100_000) - .build_and_unwrap_contract(); - - // Check that the BOB contract has been instantiated. - get_contract(&addr); - - // Call BOB with input data, forcing it make a recursive call to itself to - // self-destruct, resulting in a trap. - assert_err_ignore_postinfo!( - builder::call(addr).data(vec![0]).build(), - Error::::ContractTrapped, - ); - - // Check that BOB is still there. - get_contract(&addr); - }); -} - -#[test] -fn self_destruct_works() { - let (binary, code_hash) = compile_module("self_destruct").unwrap(); - ExtBuilder::default().existential_deposit(1_000).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let _ = ::Currency::set_balance(&DJANGO_FALLBACK, 1_000_000); - let min_balance = Contracts::min_balance(); - - // Instantiate the BOB contract. - let contract = builder::bare_instantiate(Code::Upload(binary)) - .native_value(100_000) - .build_and_unwrap_contract(); - - let hold_balance = test_utils::contract_base_deposit(&contract.addr); - - // Check that the BOB contract has been instantiated. - let _ = get_contract(&contract.addr); - - // Drop all previous events - initialize_block(2); - - // Call BOB without input data which triggers termination. - assert_matches!(builder::call(contract.addr).build(), Ok(_)); - - // Check that code is still there but refcount dropped to zero. - assert_refcount!(&code_hash, 0); - - // Check that account is gone - assert!(get_contract_checked(&contract.addr).is_none()); - assert_eq!(::Currency::total_balance(&contract.account_id), 0); - - // Check that the beneficiary (django) got remaining balance. - assert_eq!( - ::Currency::free_balance(DJANGO_FALLBACK), - 1_000_000 + 100_000 + min_balance - ); - - // Check that the Alice is missing Django's benefit. Within ALICE's total balance - // there's also the code upload deposit held. - assert_eq!( - ::Currency::total_balance(&ALICE), - 1_000_000 - (100_000 + min_balance) - ); - - pretty_assertions::assert_eq!( - System::events(), - vec![ - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::TransferOnHold { - reason: ::RuntimeHoldReason::Contracts( - HoldReason::StorageDepositReserve, - ), - source: contract.account_id.clone(), - dest: ALICE, - amount: hold_balance, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::System(frame_system::Event::KilledAccount { - account: contract.account_id.clone() - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { - from: contract.account_id.clone(), - to: DJANGO_FALLBACK, - amount: 100_000 + min_balance, - }), - topics: vec![], - }, - ], - ); - }); -} - -// This tests that one contract cannot prevent another from self-destructing by sending it -// additional funds after it has been drained. -#[test] -fn destroy_contract_and_transfer_funds() { - let (callee_binary, callee_code_hash) = compile_module("self_destruct").unwrap(); - let (caller_binary, _caller_code_hash) = compile_module("destroy_and_transfer").unwrap(); - - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - // Create code hash for bob to instantiate - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - callee_binary.clone(), - deposit_limit::(), - ) - .unwrap(); - - // This deploys the BOB contract, which in turn deploys the CHARLIE contract during - // construction. - let Contract { addr: addr_bob, .. } = - builder::bare_instantiate(Code::Upload(caller_binary)) - .native_value(200_000) - .data(callee_code_hash.as_ref().to_vec()) - .build_and_unwrap_contract(); - - // Check that the CHARLIE contract has been instantiated. - let salt = [47; 32]; // hard coded in fixture. - let addr_charlie = create2(&addr_bob, &callee_binary, &[], &salt); - get_contract(&addr_charlie); - - // Call BOB, which calls CHARLIE, forcing CHARLIE to self-destruct. - assert_ok!(builder::call(addr_bob).data(addr_charlie.encode()).build()); - - // Check that CHARLIE has moved on to the great beyond (ie. died). - assert!(get_contract_checked(&addr_charlie).is_none()); - }); -} - -#[test] -fn cannot_self_destruct_in_constructor() { - let (binary, _) = compile_module("self_destructing_constructor").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Fail to instantiate the BOB because the constructor calls seal_terminate. - assert_err_ignore_postinfo!( - builder::instantiate_with_code(binary).value(100_000).build(), - Error::::TerminatedInConstructor, - ); - }); -} - -#[test] -fn crypto_hash_keccak_256() { - let (binary, _code_hash) = compile_module("crypto_hash_keccak_256").unwrap(); - - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Instantiate the CRYPTO_HASH_KECCAK_256 contract. - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(100_000) - .build_and_unwrap_contract(); - // Perform the call. - let input = b"_DEAD_BEEF"; - use sp_io::hashing::*; - // Wraps a hash function into a more dynamic form usable for testing. - macro_rules! dyn_hash_fn { - ($name:ident) => { - Box::new(|input| $name(input).as_ref().to_vec().into_boxed_slice()) - }; - } - // The hash function and its associated output byte lengths. - let hash_fn: Box Box<[u8]>> = dyn_hash_fn!(keccak_256); - let expected_size: usize = 32; - // Test the hash function for the input: "_DEAD_BEEF" - let result = builder::bare_call(addr).data(input.to_vec()).build_and_unwrap_result(); - assert!(!result.did_revert()); - let expected = hash_fn(input.as_ref()); - assert_eq!(&result.data[..expected_size], &*expected); - }) -} - -#[test] -fn transfer_return_code() { - let (binary, _code_hash) = compile_module("transfer_return_code").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); - - let contract = builder::bare_instantiate(Code::Upload(binary)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - // Contract has only the minimal balance so any transfer will fail. - ::Currency::set_balance(&contract.account_id, min_balance); - let result = builder::bare_call(contract.addr).build_and_unwrap_result(); - assert_return_code!(result, RuntimeReturnCode::TransferFailed); - }); -} - -#[test] -fn call_return_code() { - use test_utils::u256_bytes; - - let (caller_code, _caller_hash) = compile_module("call_return_code").unwrap(); - let (callee_code, _callee_hash) = compile_module("ok_trap_revert").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); - let _ = ::Currency::set_balance(&CHARLIE, 1000 * min_balance); - - let bob = builder::bare_instantiate(Code::Upload(caller_code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - // BOB cannot pay the ed which is needed to pull DJANGO into existence - // this does trap the caller instead of returning an error code - // reasoning is that this error state does not exist on eth where - // ed does not exist. We hide this fact from the contract. - let result = builder::bare_call(bob.addr) - .data((DJANGO_ADDR, u256_bytes(1)).encode()) - .origin(RuntimeOrigin::signed(BOB)) - .build(); - assert_err!(result.result, >::StorageDepositNotEnoughFunds); - - // Contract calls into Django which is no valid contract - // This will be a balance transfer into a new account - // with more than the contract has which will make the transfer fail - let value = Pallet::::convert_native_to_evm(min_balance * 200); - let result = builder::bare_call(bob.addr) - .data( - AsRef::<[u8]>::as_ref(&DJANGO_ADDR) - .iter() - .chain(&value.to_little_endian()) - .cloned() - .collect(), - ) - .build_and_unwrap_result(); - assert_return_code!(result, RuntimeReturnCode::TransferFailed); - - // Sending below the minimum balance should result in success. - // The ED is charged from the call origin. - let alice_before = test_utils::get_balance(&ALICE_FALLBACK); - assert_eq!(test_utils::get_balance(&DJANGO_FALLBACK), 0); - - let value = Pallet::::convert_native_to_evm(1u64); - let result = builder::bare_call(bob.addr) - .data( - AsRef::<[u8]>::as_ref(&DJANGO_ADDR) - .iter() - .chain(&value.to_little_endian()) - .cloned() - .collect(), - ) - .build_and_unwrap_result(); - assert_return_code!(result, RuntimeReturnCode::Success); - assert_eq!(test_utils::get_balance(&DJANGO_FALLBACK), min_balance + 1); - assert_eq!(test_utils::get_balance(&ALICE_FALLBACK), alice_before - min_balance); - - let django = builder::bare_instantiate(Code::Upload(callee_code)) - .origin(RuntimeOrigin::signed(CHARLIE)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - // Sending more than the contract has will make the transfer fail. - let value = Pallet::::convert_native_to_evm(min_balance * 300); - let result = builder::bare_call(bob.addr) - .data( - AsRef::<[u8]>::as_ref(&django.addr) - .iter() - .chain(&value.to_little_endian()) - .chain(&0u32.to_le_bytes()) - .cloned() - .collect(), - ) - .build_and_unwrap_result(); - assert_return_code!(result, RuntimeReturnCode::TransferFailed); - - // Contract has enough balance but callee reverts because "1" is passed. - ::Currency::set_balance(&bob.account_id, min_balance + 1000); - let value = Pallet::::convert_native_to_evm(5u64); - let result = builder::bare_call(bob.addr) - .data( - AsRef::<[u8]>::as_ref(&django.addr) - .iter() - .chain(&value.to_little_endian()) - .chain(&1u32.to_le_bytes()) - .cloned() - .collect(), - ) - .build_and_unwrap_result(); - assert_return_code!(result, RuntimeReturnCode::CalleeReverted); - - // Contract has enough balance but callee traps because "2" is passed. - let result = builder::bare_call(bob.addr) - .data( - AsRef::<[u8]>::as_ref(&django.addr) - .iter() - .chain(&value.to_little_endian()) - .chain(&2u32.to_le_bytes()) - .cloned() - .collect(), - ) - .build_and_unwrap_result(); - assert_return_code!(result, RuntimeReturnCode::CalleeTrapped); - }); -} - -#[test] -fn instantiate_return_code() { - let (caller_code, _caller_hash) = compile_module("instantiate_return_code").unwrap(); - let (callee_code, callee_hash) = compile_module("ok_trap_revert").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); - let _ = ::Currency::set_balance(&CHARLIE, 1000 * min_balance); - let callee_hash = callee_hash.as_ref().to_vec(); - - assert_ok!(builder::instantiate_with_code(callee_code).value(min_balance * 100).build()); - - let contract = builder::bare_instantiate(Code::Upload(caller_code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - // bob cannot pay the ED to create the contract as he has no money - // this traps the caller rather than returning an error - let result = builder::bare_call(contract.addr) - .data(callee_hash.iter().chain(&0u32.to_le_bytes()).cloned().collect()) - .origin(RuntimeOrigin::signed(BOB)) - .build(); - assert_err!(result.result, >::StorageDepositNotEnoughFunds); - - // Contract has only the minimal balance so any transfer will fail. - ::Currency::set_balance(&contract.account_id, min_balance); - let result = builder::bare_call(contract.addr) - .data(callee_hash.iter().chain(&0u32.to_le_bytes()).cloned().collect()) - .build_and_unwrap_result(); - assert_return_code!(result, RuntimeReturnCode::TransferFailed); - - // Contract has enough balance but the passed code hash is invalid - ::Currency::set_balance(&contract.account_id, min_balance + 10_000); - let result = builder::bare_call(contract.addr).data(vec![0; 36]).build(); - assert_err!(result.result, >::CodeNotFound); - - // Contract has enough balance but callee reverts because "1" is passed. - let result = builder::bare_call(contract.addr) - .data(callee_hash.iter().chain(&1u32.to_le_bytes()).cloned().collect()) - .build_and_unwrap_result(); - assert_return_code!(result, RuntimeReturnCode::CalleeReverted); - - // Contract has enough balance but callee traps because "2" is passed. - let result = builder::bare_call(contract.addr) - .data(callee_hash.iter().chain(&2u32.to_le_bytes()).cloned().collect()) - .build_and_unwrap_result(); - assert_return_code!(result, RuntimeReturnCode::CalleeTrapped); - - // Contract instantiation succeeds - let result = builder::bare_call(contract.addr) - .data(callee_hash.iter().chain(&0u32.to_le_bytes()).cloned().collect()) - .build_and_unwrap_result(); - assert_return_code!(result, 0); - - // Contract instantiation fails because the same salt is being used again. - let result = builder::bare_call(contract.addr) - .data(callee_hash.iter().chain(&0u32.to_le_bytes()).cloned().collect()) - .build_and_unwrap_result(); - assert_return_code!(result, RuntimeReturnCode::DuplicateContractAddress); - }); -} - -#[test] -fn lazy_removal_works() { - let (code, _hash) = compile_module("self_destruct").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); - - let contract = builder::bare_instantiate(Code::Upload(code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - let info = get_contract(&contract.addr); - let trie = &info.child_trie_info(); - - // Put value into the contracts child trie - child::put(trie, &[99], &42); - - // Terminate the contract - assert_ok!(builder::call(contract.addr).build()); - - // Contract info should be gone - assert!(!>::contains_key(&contract.addr)); - - // But value should be still there as the lazy removal did not run, yet. - assert_matches!(child::get(trie, &[99]), Some(42)); - - // Run the lazy removal - Contracts::on_idle(System::block_number(), Weight::MAX); - - // Value should be gone now - assert_matches!(child::get::(trie, &[99]), None); - }); -} - -#[test] -fn lazy_batch_removal_works() { - let (code, _hash) = compile_module("self_destruct").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); - let mut tries: Vec = vec![]; - - for i in 0..3u8 { - let contract = builder::bare_instantiate(Code::Upload(code.clone())) - .native_value(min_balance * 100) - .salt(Some([i; 32])) - .build_and_unwrap_contract(); - - let info = get_contract(&contract.addr); - let trie = &info.child_trie_info(); - - // Put value into the contracts child trie - child::put(trie, &[99], &42); - - // Terminate the contract. Contract info should be gone, but value should be still - // there as the lazy removal did not run, yet. - assert_ok!(builder::call(contract.addr).build()); - - assert!(!>::contains_key(&contract.addr)); - assert_matches!(child::get(trie, &[99]), Some(42)); - - tries.push(trie.clone()) - } - - // Run single lazy removal - Contracts::on_idle(System::block_number(), Weight::MAX); - - // The single lazy removal should have removed all queued tries - for trie in tries.iter() { - assert_matches!(child::get::(trie, &[99]), None); - } - }); -} - -#[test] -fn ref_time_left_api_works() { - let (code, _) = compile_module("ref_time_left").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create fixture: Constructor calls ref_time_left twice and asserts it to decrease - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // Call the contract: It echoes back the ref_time returned by the ref_time_left API. - let received = builder::bare_call(addr).build_and_unwrap_result(); - assert_eq!(received.flags, ReturnFlags::empty()); - - let returned_value = u64::from_le_bytes(received.data[..8].try_into().unwrap()); - assert!(returned_value > 0); - assert!(returned_value < GAS_LIMIT.ref_time()); - }); -} - -#[test] -fn lazy_removal_partial_remove_works() { - let (code, _hash) = compile_module("self_destruct").unwrap(); - - // We create a contract with some extra keys above the weight limit - let extra_keys = 7u32; - let mut meter = WeightMeter::with_limit(Weight::from_parts(5_000_000_000, 100 * 1024)); - let (weight_per_key, max_keys) = ContractInfo::::deletion_budget(&meter); - let vals: Vec<_> = (0..max_keys + extra_keys) - .map(|i| (blake2_256(&i.encode()), (i as u32), (i as u32).encode())) - .collect(); - - let mut ext = ExtBuilder::default().existential_deposit(50).build(); - - let trie = ext.execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); - - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - let info = get_contract(&addr); - - // Put value into the contracts child trie - for val in &vals { - info.write(&Key::Fix(val.0), Some(val.2.clone()), None, false).unwrap(); - } - AccountInfo::::insert_contract(&addr, info.clone()); - - // Terminate the contract - assert_ok!(builder::call(addr).build()); - - // Contract info should be gone - assert!(!>::contains_key(&addr)); - - let trie = info.child_trie_info(); - - // But value should be still there as the lazy removal did not run, yet. - for val in &vals { - assert_eq!(child::get::(&trie, &blake2_256(&val.0)), Some(val.1)); - } - - trie.clone() - }); - - // The lazy removal limit only applies to the backend but not to the overlay. - // This commits all keys from the overlay to the backend. - ext.commit_all().unwrap(); - - ext.execute_with(|| { - // Run the lazy removal - ContractInfo::::process_deletion_queue_batch(&mut meter); - - // Weight should be exhausted because we could not even delete all keys - assert!(!meter.can_consume(weight_per_key)); - - let mut num_deleted = 0u32; - let mut num_remaining = 0u32; - - for val in &vals { - match child::get::(&trie, &blake2_256(&val.0)) { - None => num_deleted += 1, - Some(x) if x == val.1 => num_remaining += 1, - Some(_) => panic!("Unexpected value in contract storage"), - } - } - - // All but one key is removed - assert_eq!(num_deleted + num_remaining, vals.len() as u32); - assert_eq!(num_deleted, max_keys); - assert_eq!(num_remaining, extra_keys); - }); -} - -#[test] -fn lazy_removal_does_no_run_on_low_remaining_weight() { - let (code, _hash) = compile_module("self_destruct").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); - - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - let info = get_contract(&addr); - let trie = &info.child_trie_info(); - - // Put value into the contracts child trie - child::put(trie, &[99], &42); - - // Terminate the contract - assert_ok!(builder::call(addr).build()); - - // Contract info should be gone - assert!(!>::contains_key(&addr)); - - // But value should be still there as the lazy removal did not run, yet. - assert_matches!(child::get(trie, &[99]), Some(42)); - - // Assign a remaining weight which is too low for a successful deletion of the contract - let low_remaining_weight = - <::WeightInfo as WeightInfo>::on_process_deletion_queue_batch(); - - // Run the lazy removal - Contracts::on_idle(System::block_number(), low_remaining_weight); - - // Value should still be there, since remaining weight was too low for removal - assert_matches!(child::get::(trie, &[99]), Some(42)); - - // Run the lazy removal while deletion_queue is not full - Contracts::on_initialize(System::block_number()); - - // Value should still be there, since deletion_queue was not full - assert_matches!(child::get::(trie, &[99]), Some(42)); - - // Run on_idle with max remaining weight, this should remove the value - Contracts::on_idle(System::block_number(), Weight::MAX); - - // Value should be gone - assert_matches!(child::get::(trie, &[99]), None); - }); -} - -#[test] -fn lazy_removal_does_not_use_all_weight() { - let (code, _hash) = compile_module("self_destruct").unwrap(); - - let mut meter = WeightMeter::with_limit(Weight::from_parts(5_000_000_000, 100 * 1024)); - let mut ext = ExtBuilder::default().existential_deposit(50).build(); - - let (trie, vals, weight_per_key) = ext.execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); - - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - let info = get_contract(&addr); - let (weight_per_key, max_keys) = ContractInfo::::deletion_budget(&meter); - assert!(max_keys > 0); - - // We create a contract with one less storage item than we can remove within the limit - let vals: Vec<_> = (0..max_keys - 1) - .map(|i| (blake2_256(&i.encode()), (i as u32), (i as u32).encode())) - .collect(); - - // Put value into the contracts child trie - for val in &vals { - info.write(&Key::Fix(val.0), Some(val.2.clone()), None, false).unwrap(); - } - AccountInfo::::insert_contract(&addr, info.clone()); - - // Terminate the contract - assert_ok!(builder::call(addr).build()); - - // Contract info should be gone - assert!(!>::contains_key(&addr)); - - let trie = info.child_trie_info(); - - // But value should be still there as the lazy removal did not run, yet. - for val in &vals { - assert_eq!(child::get::(&trie, &blake2_256(&val.0)), Some(val.1)); - } - - (trie, vals, weight_per_key) - }); - - // The lazy removal limit only applies to the backend but not to the overlay. - // This commits all keys from the overlay to the backend. - ext.commit_all().unwrap(); - - ext.execute_with(|| { - // Run the lazy removal - ContractInfo::::process_deletion_queue_batch(&mut meter); - let base_weight = - <::WeightInfo as WeightInfo>::on_process_deletion_queue_batch(); - assert_eq!(meter.consumed(), weight_per_key.mul(vals.len() as _) + base_weight); - - // All the keys are removed - for val in vals { - assert_eq!(child::get::(&trie, &blake2_256(&val.0)), None); - } - }); -} - -#[test] -fn deletion_queue_ring_buffer_overflow() { - let (code, _hash) = compile_module("self_destruct").unwrap(); - let mut ext = ExtBuilder::default().existential_deposit(50).build(); - - // setup the deletion queue with custom counters - ext.execute_with(|| { - let queue = DeletionQueueManager::from_test_values(u32::MAX - 1, u32::MAX - 1); - >::set(queue); - }); - - // commit the changes to the storage - ext.commit_all().unwrap(); - - ext.execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); - let mut tries: Vec = vec![]; - - // add 3 contracts to the deletion queue - for i in 0..3u8 { - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code.clone())) - .native_value(min_balance * 100) - .salt(Some([i; 32])) - .build_and_unwrap_contract(); - - let info = get_contract(&addr); - let trie = &info.child_trie_info(); - - // Put value into the contracts child trie - child::put(trie, &[99], &42); - - // Terminate the contract. Contract info should be gone, but value should be still - // there as the lazy removal did not run, yet. - assert_ok!(builder::call(addr).build()); - - assert!(!>::contains_key(&addr)); - assert_matches!(child::get(trie, &[99]), Some(42)); - - tries.push(trie.clone()) - } - - // Run single lazy removal - Contracts::on_idle(System::block_number(), Weight::MAX); - - // The single lazy removal should have removed all queued tries - for trie in tries.iter() { - assert_matches!(child::get::(trie, &[99]), None); - } - - // insert and delete counter values should go from u32::MAX - 1 to 1 - assert_eq!(>::get().as_test_tuple(), (1, 1)); - }) -} -#[test] -fn refcounter() { - let (binary, code_hash) = compile_module("self_destruct").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let min_balance = Contracts::min_balance(); - - // Create two contracts with the same code and check that they do in fact share it. - let Contract { addr: addr0, .. } = builder::bare_instantiate(Code::Upload(binary.clone())) - .native_value(min_balance * 100) - .salt(Some([0; 32])) - .build_and_unwrap_contract(); - let Contract { addr: addr1, .. } = builder::bare_instantiate(Code::Upload(binary.clone())) - .native_value(min_balance * 100) - .salt(Some([1; 32])) - .build_and_unwrap_contract(); - assert_refcount!(code_hash, 2); - - // Sharing should also work with the usual instantiate call - let Contract { addr: addr2, .. } = builder::bare_instantiate(Code::Existing(code_hash)) - .native_value(min_balance * 100) - .salt(Some([2; 32])) - .build_and_unwrap_contract(); - assert_refcount!(code_hash, 3); - - // Terminating one contract should decrement the refcount - assert_ok!(builder::call(addr0).build()); - assert_refcount!(code_hash, 2); - - // remove another one - assert_ok!(builder::call(addr1).build()); - assert_refcount!(code_hash, 1); - - // Pristine code should still be there - PristineCode::::get(code_hash).unwrap(); - - // remove the last contract - assert_ok!(builder::call(addr2).build()); - assert_refcount!(code_hash, 0); - - // refcount is `0` but code should still exists because it needs to be removed manually - assert!(crate::PristineCode::::contains_key(&code_hash)); - }); -} - -#[test] -fn gas_estimation_for_subcalls() { - let (caller_code, _caller_hash) = compile_module("call_with_limit").unwrap(); - let (dummy_code, _callee_hash) = compile_module("dummy").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 2_000 * min_balance); - - let Contract { addr: addr_caller, .. } = - builder::bare_instantiate(Code::Upload(caller_code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - let Contract { addr: addr_dummy, .. } = builder::bare_instantiate(Code::Upload(dummy_code)) - .native_value(min_balance * 100) - .build_and_unwrap_contract(); - - // Run the test for all of those weight limits for the subcall - let weights = [ - Weight::MAX, - GAS_LIMIT, - GAS_LIMIT * 2, - GAS_LIMIT / 5, - Weight::from_parts(u64::MAX, GAS_LIMIT.proof_size()), - Weight::from_parts(GAS_LIMIT.ref_time(), u64::MAX), - ]; - - let (sub_addr, sub_input) = (addr_dummy.as_ref(), vec![]); - - for weight in weights { - let input: Vec = sub_addr - .iter() - .cloned() - .chain(weight.ref_time().to_le_bytes()) - .chain(weight.proof_size().to_le_bytes()) - .chain(sub_input.clone()) - .collect(); - - // Call in order to determine the gas that is required for this call - let result_orig = builder::bare_call(addr_caller).data(input.clone()).build(); - assert_ok!(&result_orig.result); - assert_eq!(result_orig.gas_required, result_orig.gas_consumed); - - // Make the same call using the estimated gas. Should succeed. - let result = builder::bare_call(addr_caller) - .gas_limit(result_orig.gas_required) - .storage_deposit_limit(result_orig.storage_deposit.charge_or_zero().into()) - .data(input.clone()) - .build(); - assert_ok!(&result.result); - - // Check that it fails with too little ref_time - let result = builder::bare_call(addr_caller) - .gas_limit(result_orig.gas_required.sub_ref_time(1)) - .storage_deposit_limit(result_orig.storage_deposit.charge_or_zero().into()) - .data(input.clone()) - .build(); - assert_err!(result.result, >::OutOfGas); - - // Check that it fails with too little proof_size - let result = builder::bare_call(addr_caller) - .gas_limit(result_orig.gas_required.sub_proof_size(1)) - .storage_deposit_limit(result_orig.storage_deposit.charge_or_zero().into()) - .data(input.clone()) - .build(); - assert_err!(result.result, >::OutOfGas); - } - }); -} - -#[test] -fn call_runtime_reentrancy_guarded() { - use crate::precompiles::Precompile; - use alloy_core::sol_types::SolInterface; - use precompiles::{INoInfo, NoInfo}; - - let precompile_addr = H160(NoInfo::::MATCHER.base_address()); - - let (callee_code, _callee_hash) = compile_module("dummy").unwrap(); - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let min_balance = Contracts::min_balance(); - let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); - let _ = ::Currency::set_balance(&CHARLIE, 1000 * min_balance); - - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(callee_code)) - .native_value(min_balance * 100) - .salt(Some([1; 32])) - .build_and_unwrap_contract(); - - // Call pallet_revive call() dispatchable - let call = RuntimeCall::Contracts(crate::Call::call { - dest: addr_callee, - value: 0, - gas_limit: GAS_LIMIT / 3, - storage_deposit_limit: deposit_limit::(), - data: vec![], - }) - .encode(); - - // Call runtime to re-enter back to contracts engine by - // calling dummy contract - let result = builder::bare_call(precompile_addr) - .data( - INoInfo::INoInfoCalls::callRuntime(INoInfo::callRuntimeCall { call: call.into() }) - .abi_encode(), - ) - .build(); - // Call to runtime should fail because of the re-entrancy guard - assert_err!(result.result, >::ReenteredPallet); - }); -} - -#[test] -fn sr25519_verify() { - let (binary, _code_hash) = compile_module("sr25519_verify").unwrap(); - - ExtBuilder::default().existential_deposit(50).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Instantiate the sr25519_verify contract. - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(100_000) - .build_and_unwrap_contract(); - - let call_with = |message: &[u8; 11]| { - // Alice's signature for "hello world" - #[rustfmt::skip] - let signature: [u8; 64] = [ - 184, 49, 74, 238, 78, 165, 102, 252, 22, 92, 156, 176, 124, 118, 168, 116, 247, - 99, 0, 94, 2, 45, 9, 170, 73, 222, 182, 74, 60, 32, 75, 64, 98, 174, 69, 55, 83, - 85, 180, 98, 208, 75, 231, 57, 205, 62, 4, 105, 26, 136, 172, 17, 123, 99, 90, 255, - 228, 54, 115, 63, 30, 207, 205, 131, - ]; - - // Alice's public key - #[rustfmt::skip] - let public_key: [u8; 32] = [ - 212, 53, 147, 199, 21, 253, 211, 28, 97, 20, 26, 189, 4, 169, 159, 214, 130, 44, - 133, 88, 133, 76, 205, 227, 154, 86, 132, 231, 165, 109, 162, 125, - ]; - - let mut params = vec![]; - params.extend_from_slice(&signature); - params.extend_from_slice(&public_key); - params.extend_from_slice(message); - - builder::bare_call(addr).data(params).build_and_unwrap_result() - }; - - // verification should succeed for "hello world" - assert_return_code!(call_with(&b"hello world"), RuntimeReturnCode::Success); - - // verification should fail for other messages - assert_return_code!(call_with(&b"hello worlD"), RuntimeReturnCode::Sr25519VerifyFailed); - }); -} - -#[test] -fn upload_code_works() { - let (binary, code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Drop previous events - initialize_block(2); - - assert!(!PristineCode::::contains_key(&code_hash)); - assert_ok!(Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, 1_000,)); - // Ensure the contract was stored and get expected deposit amount to be reserved. - expected_deposit(ensure_stored(code_hash)); - }); -} - -#[test] -fn upload_code_limit_too_low() { - let (binary, _code_hash) = compile_module("dummy").unwrap(); - let deposit_expected = expected_deposit(binary.len()); - let deposit_insufficient = deposit_expected.saturating_sub(1); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Drop previous events - initialize_block(2); - - assert_noop!( - Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, deposit_insufficient,), - >::StorageDepositLimitExhausted, - ); - - assert_eq!(System::events(), vec![]); - }); -} - -#[test] -fn upload_code_not_enough_balance() { - let (binary, _code_hash) = compile_module("dummy").unwrap(); - let deposit_expected = expected_deposit(binary.len()); - let deposit_insufficient = deposit_expected.saturating_sub(1); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, deposit_insufficient); - - // Drop previous events - initialize_block(2); - - assert_noop!( - Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, 1_000,), - >::StorageDepositNotEnoughFunds, - ); - - assert_eq!(System::events(), vec![]); - }); -} - -#[test] -fn remove_code_works() { - let (binary, code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Drop previous events - initialize_block(2); - - assert_ok!(Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, 1_000,)); - // Ensure the contract was stored and get expected deposit amount to be reserved. - expected_deposit(ensure_stored(code_hash)); - assert_ok!(Contracts::remove_code(RuntimeOrigin::signed(ALICE), code_hash)); - }); -} - -#[test] -fn remove_code_wrong_origin() { - let (binary, code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Drop previous events - initialize_block(2); - - assert_ok!(Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, 1_000,)); - // Ensure the contract was stored and get expected deposit amount to be reserved. - expected_deposit(ensure_stored(code_hash)); - - assert_noop!( - Contracts::remove_code(RuntimeOrigin::signed(BOB), code_hash), - sp_runtime::traits::BadOrigin, - ); - }); -} - -#[test] -fn remove_code_in_use() { - let (binary, code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - assert_ok!(builder::instantiate_with_code(binary).build()); - - // Drop previous events - initialize_block(2); - - assert_noop!( - Contracts::remove_code(RuntimeOrigin::signed(ALICE), code_hash), - >::CodeInUse, - ); - - assert_eq!(System::events(), vec![]); - }); -} - -#[test] -fn remove_code_not_found() { - let (_binary, code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Drop previous events - initialize_block(2); - - assert_noop!( - Contracts::remove_code(RuntimeOrigin::signed(ALICE), code_hash), - >::CodeNotFound, - ); - - assert_eq!(System::events(), vec![]); - }); -} - -#[test] -fn instantiate_with_zero_balance_works() { - let (binary, code_hash) = compile_module("dummy").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let min_balance = Contracts::min_balance(); - - // Drop previous events - initialize_block(2); - - // Instantiate the BOB contract. - let Contract { addr, account_id } = - builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); - - // Ensure the contract was stored and get expected deposit amount to be reserved. - expected_deposit(ensure_stored(code_hash)); - - // Make sure the account exists even though no free balance was send - assert_eq!(::Currency::free_balance(&account_id), min_balance); - assert_eq!( - ::Currency::total_balance(&account_id), - min_balance + test_utils::contract_base_deposit(&addr) - ); - - assert_eq!( - System::events(), - vec![ - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Held { - reason: ::RuntimeHoldReason::Contracts( - HoldReason::CodeUploadDepositReserve, - ), - who: ALICE, - amount: 776, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::System(frame_system::Event::NewAccount { - account: account_id.clone(), - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Endowed { - account: account_id.clone(), - free_balance: min_balance, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { - from: ALICE, - to: account_id.clone(), - amount: min_balance, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Contracts(crate::Event::Instantiated { - deployer: ALICE_ADDR, - contract: addr, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { - reason: ::RuntimeHoldReason::Contracts( - HoldReason::StorageDepositReserve, - ), - source: ALICE, - dest: account_id, - transferred: 336, - }), - topics: vec![], - }, - ] - ); - }); -} - -#[test] -fn instantiate_with_below_existential_deposit_works() { - let (binary, code_hash) = compile_module("dummy").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let min_balance = Contracts::min_balance(); - let value = 50; - - // Drop previous events - initialize_block(2); - - // Instantiate the BOB contract. - let Contract { addr, account_id } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(value) - .build_and_unwrap_contract(); - - // Ensure the contract was stored and get expected deposit amount to be reserved. - expected_deposit(ensure_stored(code_hash)); - // Make sure the account exists even though not enough free balance was send - assert_eq!(::Currency::free_balance(&account_id), min_balance + value); - assert_eq!( - ::Currency::total_balance(&account_id), - min_balance + value + test_utils::contract_base_deposit(&addr) - ); - - assert_eq!( - System::events(), - vec![ - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Held { - reason: ::RuntimeHoldReason::Contracts( - HoldReason::CodeUploadDepositReserve, - ), - who: ALICE, - amount: 776, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::System(frame_system::Event::NewAccount { - account: account_id.clone() - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Endowed { - account: account_id.clone(), - free_balance: min_balance, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { - from: ALICE, - to: account_id.clone(), - amount: min_balance, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { - from: ALICE, - to: account_id.clone(), - amount: 50, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Contracts(crate::Event::Instantiated { - deployer: ALICE_ADDR, - contract: addr, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { - reason: ::RuntimeHoldReason::Contracts( - HoldReason::StorageDepositReserve, - ), - source: ALICE, - dest: account_id.clone(), - transferred: 336, - }), - topics: vec![], - }, - ] - ); - }); -} - -#[test] -fn storage_deposit_works() { - let (binary, _code_hash) = compile_module("multi_store").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let Contract { addr, account_id } = - builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); - - let mut deposit = test_utils::contract_base_deposit(&addr); - - // Drop previous events - initialize_block(2); - - // Create storage - assert_ok!(builder::call(addr).value(42).data((50u32, 20u32).encode()).build()); - // 4 is for creating 2 storage items - // 48 is for each of the keys - let charged0 = 4 + 50 + 20 + 48 + 48; - deposit += charged0; - assert_eq!(get_contract(&addr).total_deposit(), deposit); - - // Add more storage (but also remove some) - assert_ok!(builder::call(addr).data((100u32, 10u32).encode()).build()); - let charged1 = 50 - 10; - deposit += charged1; - assert_eq!(get_contract(&addr).total_deposit(), deposit); - - // Remove more storage (but also add some) - assert_ok!(builder::call(addr).data((10u32, 20u32).encode()).build()); - // -1 for numeric instability - let refunded0 = 90 - 10 - 1; - deposit -= refunded0; - assert_eq!(get_contract(&addr).total_deposit(), deposit); - - assert_eq!( - System::events(), - vec![ - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { - from: ALICE, - to: account_id.clone(), - amount: 42, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { - reason: ::RuntimeHoldReason::Contracts( - HoldReason::StorageDepositReserve, - ), - source: ALICE, - dest: account_id.clone(), - transferred: charged0, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { - reason: ::RuntimeHoldReason::Contracts( - HoldReason::StorageDepositReserve, - ), - source: ALICE, - dest: account_id.clone(), - transferred: charged1, - }), - topics: vec![], - }, - EventRecord { - phase: Phase::Initialization, - event: RuntimeEvent::Balances(pallet_balances::Event::TransferOnHold { - reason: ::RuntimeHoldReason::Contracts( - HoldReason::StorageDepositReserve, - ), - source: account_id.clone(), - dest: ALICE, - amount: refunded0, - }), - topics: vec![], - }, - ] - ); - }); -} - -#[test] -fn storage_deposit_callee_works() { - let (binary_caller, _code_hash_caller) = compile_module("call").unwrap(); - let (binary_callee, _code_hash_callee) = compile_module("store_call").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create both contracts: Constructors do nothing. - let Contract { addr: addr_caller, .. } = - builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); - - assert_ok!(builder::call(addr_caller).data((100u32, &addr_callee).encode()).build()); - - let callee = get_contract(&addr_callee); - let deposit = DepositPerByte::get() * 100 + DepositPerItem::get() * 1 + 48; - - assert_eq!(Pallet::::evm_balance(&addr_caller), U256::zero()); - assert_eq!( - callee.total_deposit(), - deposit + test_utils::contract_base_deposit(&addr_callee) - ); - }); -} - -#[test] -fn set_code_extrinsic() { - let (binary, code_hash) = compile_module("dummy").unwrap(); - let (new_binary, new_code_hash) = compile_module("crypto_hash_keccak_256").unwrap(); - - assert_ne!(code_hash, new_code_hash); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); - - assert_ok!(Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - new_binary, - deposit_limit::(), - )); - - // Drop previous events - initialize_block(2); - - assert_eq!(get_contract(&addr).code_hash, code_hash); - assert_refcount!(&code_hash, 1); - assert_refcount!(&new_code_hash, 0); - - // only root can execute this extrinsic - assert_noop!( - Contracts::set_code(RuntimeOrigin::signed(ALICE), addr, new_code_hash), - sp_runtime::traits::BadOrigin, - ); - assert_eq!(get_contract(&addr).code_hash, code_hash); - assert_refcount!(&code_hash, 1); - assert_refcount!(&new_code_hash, 0); - assert_eq!(System::events(), vec![]); - - // contract must exist - assert_noop!( - Contracts::set_code(RuntimeOrigin::root(), BOB_ADDR, new_code_hash), - >::ContractNotFound, - ); - assert_eq!(get_contract(&addr).code_hash, code_hash); - assert_refcount!(&code_hash, 1); - assert_refcount!(&new_code_hash, 0); - assert_eq!(System::events(), vec![]); - - // new code hash must exist - assert_noop!( - Contracts::set_code(RuntimeOrigin::root(), addr, Default::default()), - >::CodeNotFound, - ); - assert_eq!(get_contract(&addr).code_hash, code_hash); - assert_refcount!(&code_hash, 1); - assert_refcount!(&new_code_hash, 0); - assert_eq!(System::events(), vec![]); - - // successful call - assert_ok!(Contracts::set_code(RuntimeOrigin::root(), addr, new_code_hash)); - assert_eq!(get_contract(&addr).code_hash, new_code_hash); - assert_refcount!(&code_hash, 0); - assert_refcount!(&new_code_hash, 1); - }); -} - -#[test] -fn slash_cannot_kill_account() { - let (binary, _code_hash) = compile_module("dummy").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let value = 700; - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let min_balance = Contracts::min_balance(); - - let Contract { addr, account_id } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(value) - .build_and_unwrap_contract(); - - // Drop previous events - initialize_block(2); - - let info_deposit = test_utils::contract_base_deposit(&addr); - - assert_eq!( - test_utils::get_balance_on_hold(&HoldReason::StorageDepositReserve.into(), &account_id), - info_deposit - ); - - assert_eq!( - ::Currency::total_balance(&account_id), - info_deposit + value + min_balance - ); - - // Try to destroy the account of the contract by slashing the total balance. - // The account does not get destroyed because slashing only affects the balance held - // under certain `reason`. Slashing can for example happen if the contract takes part - // in staking. - let _ = ::Currency::slash( - &HoldReason::StorageDepositReserve.into(), - &account_id, - ::Currency::total_balance(&account_id), - ); - - // Slashing only removed the balance held. - assert_eq!(::Currency::total_balance(&account_id), value + min_balance); - }); -} - -#[test] -fn contract_reverted() { - let (binary, code_hash) = compile_module("return_with_data").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let flags = ReturnFlags::REVERT; - let buffer = [4u8, 8, 15, 16, 23, 42]; - let input = (flags.bits(), buffer).encode(); - - // We just upload the code for later use - assert_ok!(Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - binary.clone(), - deposit_limit::(), - )); - - // Calling extrinsic: revert leads to an error - assert_err_ignore_postinfo!( - builder::instantiate(code_hash).data(input.clone()).build(), - >::ContractReverted, - ); - - // Calling extrinsic: revert leads to an error - assert_err_ignore_postinfo!( - builder::instantiate_with_code(binary).data(input.clone()).build(), - >::ContractReverted, - ); - - // Calling directly: revert leads to success but the flags indicate the error - // This is just a different way of transporting the error that allows the read out - // the `data` which is only there on success. Obviously, the contract isn't - // instantiated. - let result = builder::bare_instantiate(Code::Existing(code_hash)) - .data(input.clone()) - .build_and_unwrap_result(); - assert_eq!(result.result.flags, flags); - assert_eq!(result.result.data, buffer); - assert!(!>::contains_key(result.addr)); - - // Pass empty flags and therefore successfully instantiate the contract for later use. - let Contract { addr, .. } = builder::bare_instantiate(Code::Existing(code_hash)) - .data(ReturnFlags::empty().bits().encode()) - .build_and_unwrap_contract(); - - // Calling extrinsic: revert leads to an error - assert_err_ignore_postinfo!( - builder::call(addr).data(input.clone()).build(), - >::ContractReverted, - ); - - // Calling directly: revert leads to success but the flags indicate the error - let result = builder::bare_call(addr).data(input).build_and_unwrap_result(); - assert_eq!(result.flags, flags); - assert_eq!(result.data, buffer); - }); -} - -#[test] -fn set_code_hash() { - let (binary, _) = compile_module("set_code_hash").unwrap(); - let (new_binary, new_code_hash) = compile_module("new_set_code_hash_contract").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Instantiate the 'caller' - let Contract { addr: contract_addr, .. } = builder::bare_instantiate(Code::Upload(binary)) - .native_value(300_000) - .build_and_unwrap_contract(); - // upload new code - assert_ok!(Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - new_binary.clone(), - deposit_limit::(), - )); - - System::reset_events(); - - // First call sets new code_hash and returns 1 - let result = builder::bare_call(contract_addr) - .data(new_code_hash.as_ref().to_vec()) - .build_and_unwrap_result(); - assert_return_code!(result, 1); - - // Second calls new contract code that returns 2 - let result = builder::bare_call(contract_addr).build_and_unwrap_result(); - assert_return_code!(result, 2); - }); -} - -#[test] -fn storage_deposit_limit_is_enforced() { - let (binary, _code_hash) = compile_module("store_call").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let min_balance = Contracts::min_balance(); - - // Setting insufficient storage_deposit should fail. - assert_err!( - builder::bare_instantiate(Code::Upload(binary.clone())) - // expected deposit is 2 * ed + 3 for the call - .storage_deposit_limit((2 * min_balance + 3 - 1).into()) - .build() - .result, - >::StorageDepositLimitExhausted, - ); - - // Instantiate the BOB contract. - let Contract { addr, account_id } = - builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); - - let info_deposit = test_utils::contract_base_deposit(&addr); - // Check that the BOB contract has been instantiated and has the minimum balance - assert_eq!(get_contract(&addr).total_deposit(), info_deposit); - assert_eq!( - ::Currency::total_balance(&account_id), - info_deposit + min_balance - ); - - // Create 1 byte of storage with a price of per byte, - // setting insufficient deposit limit, as it requires 3 Balance: - // 2 for the item added + 1 (value) + 48 (key) - assert_err_ignore_postinfo!( - builder::call(addr) - .storage_deposit_limit(50) - .data(1u32.to_le_bytes().to_vec()) - .build(), - >::StorageDepositLimitExhausted, - ); - - // now with enough limit - assert_ok!(builder::call(addr) - .storage_deposit_limit(51) - .data(1u32.to_le_bytes().to_vec()) - .build()); - - // Use 4 more bytes of the storage for the same item, which requires 4 Balance. - // Should fail as DefaultDepositLimit is 3 and hence isn't enough. - assert_err_ignore_postinfo!( - builder::call(addr) - .storage_deposit_limit(3) - .data(5u32.to_le_bytes().to_vec()) - .build(), - >::StorageDepositLimitExhausted, - ); - }); -} - -#[test] -fn deposit_limit_in_nested_calls() { - let (binary_caller, _code_hash_caller) = compile_module("create_storage_and_call").unwrap(); - let (binary_callee, _code_hash_callee) = compile_module("store_call").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create both contracts: Constructors do nothing. - let Contract { addr: addr_caller, .. } = - builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); - - // Create 100 bytes of storage with a price of per byte - // This is 100 Balance + 2 Balance for the item - // 48 for the key - assert_ok!(builder::call(addr_callee) - .storage_deposit_limit(102 + 48) - .data(100u32.to_le_bytes().to_vec()) - .build()); - - // We do not remove any storage but add a storage item of 12 bytes in the caller - // contract. This would cost 12 + 2 + 72 = 86 Balance. - // The nested call doesn't get a special limit, which is set by passing `u64::MAX` to it. - // This should fail as the specified parent's limit is less than the cost: 13 < - // 14. - assert_err_ignore_postinfo!( - builder::call(addr_caller) - .storage_deposit_limit(85) - .data((100u32, &addr_callee, U256::MAX).encode()) - .build(), - >::StorageDepositLimitExhausted, - ); - - // Now we specify the parent's limit high enough to cover the caller's storage - // additions. However, we use a single byte more in the callee, hence the storage - // deposit should be 87 Balance. - // The nested call doesn't get a special limit, which is set by passing `u64::MAX` to it. - // This should fail as the specified parent's limit is less than the cost: 86 < 87 - assert_err_ignore_postinfo!( - builder::call(addr_caller) - .storage_deposit_limit(86) - .data((101u32, &addr_callee, &U256::MAX).encode()) - .build(), - >::StorageDepositLimitExhausted, - ); - - // The parents storage deposit limit doesn't matter as the sub calls limit - // is enforced eagerly. However, we set a special deposit limit of 1 Balance for the - // nested call. This should fail as callee adds up 2 bytes to the storage, meaning - // that the nested call should have a deposit limit of at least 2 Balance. The - // sub-call should be rolled back, which is covered by the next test case. - let ret = builder::bare_call(addr_caller) - .storage_deposit_limit(DepositLimit::Balance(u64::MAX)) - .data((102u32, &addr_callee, U256::from(1u64)).encode()) - .build_and_unwrap_result(); - assert_return_code!(ret, RuntimeReturnCode::OutOfResources); - - // Refund in the callee contract but not enough to cover the Balance required by the - // caller. Note that if previous sub-call wouldn't roll back, this call would pass - // making the test case fail. We don't set a special limit for the nested call here. - assert_err_ignore_postinfo!( - builder::call(addr_caller) - .storage_deposit_limit(0) - .data((87u32, &addr_callee, &U256::MAX.to_little_endian()).encode()) - .build(), - >::StorageDepositLimitExhausted, - ); - - let _ = ::Currency::set_balance(&ALICE, 511); - - // Require more than the sender's balance. - // Limit the sub call to little balance so it should fail in there - let ret = builder::bare_call(addr_caller) - .data((416, &addr_callee, U256::from(1u64)).encode()) - .build_and_unwrap_result(); - assert_return_code!(ret, RuntimeReturnCode::OutOfResources); - - // Free up enough storage in the callee so that the caller can create a new item - // We set the special deposit limit of 1 Balance for the nested call, which isn't - // enforced as callee frees up storage. This should pass. - assert_ok!(builder::call(addr_caller) - .storage_deposit_limit(1) - .data((0u32, &addr_callee, U256::from(1u64)).encode()) - .build()); - }); -} - -#[test] -fn deposit_limit_in_nested_instantiate() { - let (binary_caller, _code_hash_caller) = - compile_module("create_storage_and_instantiate").unwrap(); - let (binary_callee, code_hash_callee) = compile_module("store_deploy").unwrap(); - const ED: u64 = 5; - ExtBuilder::default().existential_deposit(ED).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let _ = ::Currency::set_balance(&BOB, 1_000_000); - // Create caller contract - let Contract { addr: addr_caller, account_id: caller_id } = - builder::bare_instantiate(Code::Upload(binary_caller)) - .native_value(10_000) // this balance is later passed to the deployed contract - .build_and_unwrap_contract(); - // Deploy a contract to get its occupied storage size - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary_callee)) - .data(vec![0, 0, 0, 0]) - .build_and_unwrap_contract(); - - // This is the deposit we expect to be charged just for instantiatiting the callee. - // - // - callee_info_len + 2 for storing the new contract info - // - the deposit for depending on a code hash - // - ED for deployed contract account - // - 2 for the storage item of 0 bytes being created in the callee constructor - // - 48 for the key - let callee_min_deposit = { - let callee_info_len = - AccountInfo::::load_contract(&addr).unwrap().encoded_size() as u64; - let code_deposit = test_utils::lockup_deposit(&code_hash_callee); - callee_info_len + code_deposit + 2 + ED + 2 + 48 - }; - - // The parent just stores an item of the passed size so at least - // we need to pay for the item itself. - let caller_min_deposit = callee_min_deposit + 2 + 48; - - // Fail in callee. - // - // We still fail in the sub call because we enforce limits on return from a contract. - // Sub calls return first to they are checked first. - let ret = builder::bare_call(addr_caller) - .origin(RuntimeOrigin::signed(BOB)) - .storage_deposit_limit(DepositLimit::Balance(0)) - .data((&code_hash_callee, 100u32, &U256::MAX.to_little_endian()).encode()) - .build_and_unwrap_result(); - assert_return_code!(ret, RuntimeReturnCode::OutOfResources); - // The charges made on instantiation should be rolled back. - assert_eq!(::Currency::free_balance(&BOB), 1_000_000); - - // Fail in the caller. - // - // For that we need to supply enough storage deposit so that the sub call - // succeeds but the parent call runs out of storage. - let ret = builder::bare_call(addr_caller) - .origin(RuntimeOrigin::signed(BOB)) - .storage_deposit_limit(DepositLimit::Balance(callee_min_deposit)) - .data((&code_hash_callee, 0u32, &U256::MAX.to_little_endian()).encode()) - .build(); - assert_err!(ret.result, >::StorageDepositLimitExhausted); - // The charges made on the instantiation should be rolled back. - assert_eq!(::Currency::free_balance(&BOB), 1_000_000); - - // Fail in the callee with bytes. - // - // Same as above but stores one byte in both caller and callee. - let ret = builder::bare_call(addr_caller) - .origin(RuntimeOrigin::signed(BOB)) - .storage_deposit_limit(DepositLimit::Balance(caller_min_deposit + 1)) - .data((&code_hash_callee, 1u32, U256::from(callee_min_deposit)).encode()) - .build_and_unwrap_result(); - assert_return_code!(ret, RuntimeReturnCode::OutOfResources); - // The charges made on the instantiation should be rolled back. - assert_eq!(::Currency::free_balance(&BOB), 1_000_000); - - // Fail in the caller with bytes. - // - // Same as above but stores one byte in both caller and callee. - let ret = builder::bare_call(addr_caller) - .origin(RuntimeOrigin::signed(BOB)) - .storage_deposit_limit(DepositLimit::Balance(callee_min_deposit + 1)) - .data((&code_hash_callee, 1u32, U256::from(callee_min_deposit + 1)).encode()) - .build(); - assert_err!(ret.result, >::StorageDepositLimitExhausted); - // The charges made on the instantiation should be rolled back. - assert_eq!(::Currency::free_balance(&BOB), 1_000_000); - - // Set enough deposit limit for the child instantiate. This should succeed. - let result = builder::bare_call(addr_caller) - .origin(RuntimeOrigin::signed(BOB)) - .storage_deposit_limit((caller_min_deposit + 2).into()) - .data((&code_hash_callee, 1u32, U256::from(callee_min_deposit + 1)).encode()) - .build(); - - let returned = result.result.unwrap(); - assert!(!returned.did_revert()); - - // All balance of the caller except ED has been transferred to the callee. - // No deposit has been taken from it. - assert_eq!(::Currency::free_balance(&caller_id), ED); - // Get address of the deployed contract. - let addr_callee = H160::from_slice(&returned.data[0..20]); - let callee_account_id = ::AddressMapper::to_account_id(&addr_callee); - // 10_000 should be sent to callee from the caller contract, plus ED to be sent from the - // origin. - assert_eq!(::Currency::free_balance(&callee_account_id), 10_000 + ED); - // The origin should be charged with what the outer call consumed - assert_eq!( - ::Currency::free_balance(&BOB), - 1_000_000 - (caller_min_deposit + 2), - ); - assert_eq!(result.storage_deposit.charge_or_zero(), (caller_min_deposit + 2)) - }); -} - -#[test] -fn deposit_limit_honors_liquidity_restrictions() { - let (binary, _code_hash) = compile_module("store_call").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let bobs_balance = 1_000; - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let _ = ::Currency::set_balance(&BOB, bobs_balance); - let min_balance = Contracts::min_balance(); - - // Instantiate the BOB contract. - let Contract { addr, account_id } = - builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); - - let info_deposit = test_utils::contract_base_deposit(&addr); - // Check that the contract has been instantiated and has the minimum balance - assert_eq!(get_contract(&addr).total_deposit(), info_deposit); - assert_eq!( - ::Currency::total_balance(&account_id), - info_deposit + min_balance - ); - - // check that the hold is honored - ::Currency::hold( - &HoldReason::CodeUploadDepositReserve.into(), - &BOB, - bobs_balance - min_balance, - ) - .unwrap(); - assert_err_ignore_postinfo!( - builder::call(addr) - .origin(RuntimeOrigin::signed(BOB)) - .storage_deposit_limit(10_000) - .data(100u32.to_le_bytes().to_vec()) - .build(), - >::StorageDepositNotEnoughFunds, - ); - assert_eq!(::Currency::free_balance(&BOB), min_balance); - }); -} - -#[test] -fn deposit_limit_honors_existential_deposit() { - let (binary, _code_hash) = compile_module("store_call").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - let _ = ::Currency::set_balance(&BOB, 300); - let min_balance = Contracts::min_balance(); - - // Instantiate the BOB contract. - let Contract { addr, account_id } = - builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); - - let info_deposit = test_utils::contract_base_deposit(&addr); - - // Check that the contract has been instantiated and has the minimum balance - assert_eq!(get_contract(&addr).total_deposit(), info_deposit); - assert_eq!( - ::Currency::total_balance(&account_id), - min_balance + info_deposit - ); - - // check that the deposit can't bring the account below the existential deposit - assert_err_ignore_postinfo!( - builder::call(addr) - .origin(RuntimeOrigin::signed(BOB)) - .storage_deposit_limit(10_000) - .data(100u32.to_le_bytes().to_vec()) - .build(), - >::StorageDepositNotEnoughFunds, - ); - assert_eq!(::Currency::free_balance(&BOB), 300); - }); -} - -#[test] -fn native_dependency_deposit_works() { - let (binary, code_hash) = compile_module("set_code_hash").unwrap(); - let (dummy_binary, dummy_code_hash) = compile_module("dummy").unwrap(); - - // Test with both existing and uploaded code - for code in [Code::Upload(binary.clone()), Code::Existing(code_hash)] { - ExtBuilder::default().build().execute_with(|| { - let _ = Balances::set_balance(&ALICE, 1_000_000); - let lockup_deposit_percent = CodeHashLockupDepositPercent::get(); - - // Upload the dummy contract, - Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - dummy_binary.clone(), - deposit_limit::(), - ) - .unwrap(); - - // Upload `set_code_hash` contracts if using Code::Existing. - let add_upload_deposit = match code { - Code::Existing(_) => { - Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - binary.clone(), - deposit_limit::(), - ) - .unwrap(); - false - }, - Code::Upload(_) => true, - }; - - // Instantiate the set_code_hash contract. - let res = builder::bare_instantiate(code).build(); - - let addr = res.result.unwrap().addr; - let account_id = ::AddressMapper::to_account_id(&addr); - let base_deposit = test_utils::contract_base_deposit(&addr); - let upload_deposit = test_utils::get_code_deposit(&code_hash); - let extra_deposit = add_upload_deposit.then(|| upload_deposit).unwrap_or_default(); - - assert_eq!( - res.storage_deposit.charge_or_zero(), - extra_deposit + base_deposit + Contracts::min_balance() - ); - - // call set_code_hash - builder::bare_call(addr) - .data(dummy_code_hash.encode()) - .build_and_unwrap_result(); - - // Check updated storage_deposit due to code size changes - let deposit_diff = lockup_deposit_percent - .mul_ceil(test_utils::get_code_deposit(&code_hash)) - - lockup_deposit_percent.mul_ceil(test_utils::get_code_deposit(&dummy_code_hash)); - let new_base_deposit = test_utils::contract_base_deposit(&addr); - assert_ne!(deposit_diff, 0); - assert_eq!(base_deposit - new_base_deposit, deposit_diff); - - assert_eq!( - test_utils::get_balance_on_hold( - &HoldReason::StorageDepositReserve.into(), - &account_id - ), - new_base_deposit - ); - }); - } -} - -#[test] -fn block_hash_works() { - let (code, _) = compile_module("block_hash").unwrap(); - - ExtBuilder::default().existential_deposit(1).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // The genesis config sets to the block number to 1 - let block_hash = [1; 32]; - frame_system::BlockHash::::insert( - &crate::BlockNumberFor::::from(0u32), - ::Hash::from(&block_hash), - ); - assert_ok!(builder::call(addr) - .data((U256::zero(), H256::from(block_hash)).encode()) - .build()); - - // A block number out of range returns the zero value - assert_ok!(builder::call(addr).data((U256::from(1), H256::zero()).encode()).build()); - }); -} - -#[test] -fn block_author_works() { - let (code, _) = compile_module("block_author").unwrap(); - - ExtBuilder::default().existential_deposit(1).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // The fixture asserts the input to match the find_author API method output. - assert_ok!(builder::call(addr).data(EVE_ADDR.encode()).build()); - }); -} - -#[test] -fn root_cannot_upload_code() { - let (binary, _) = compile_module("dummy").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - assert_noop!( - Contracts::upload_code(RuntimeOrigin::root(), binary, deposit_limit::()), - DispatchError::BadOrigin, - ); - }); -} - -#[test] -fn root_cannot_remove_code() { - let (_, code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - assert_noop!( - Contracts::remove_code(RuntimeOrigin::root(), code_hash), - DispatchError::BadOrigin, - ); - }); -} - -#[test] -fn signed_cannot_set_code() { - let (_, code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - assert_noop!( - Contracts::set_code(RuntimeOrigin::signed(ALICE), BOB_ADDR, code_hash), - DispatchError::BadOrigin, - ); - }); -} - -#[test] -fn none_cannot_call_code() { - ExtBuilder::default().build().execute_with(|| { - assert_err_ignore_postinfo!( - builder::call(BOB_ADDR).origin(RuntimeOrigin::none()).build(), - DispatchError::BadOrigin, - ); - }); -} - -#[test] -fn root_can_call() { - let (binary, _) = compile_module("dummy").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); - - // Call the contract. - assert_ok!(builder::call(addr).origin(RuntimeOrigin::root()).build()); - }); -} - -#[test] -fn root_cannot_instantiate_with_code() { - let (binary, _) = compile_module("dummy").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - assert_err_ignore_postinfo!( - builder::instantiate_with_code(binary).origin(RuntimeOrigin::root()).build(), - DispatchError::BadOrigin - ); - }); -} - -#[test] -fn root_cannot_instantiate() { - let (_, code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - assert_err_ignore_postinfo!( - builder::instantiate(code_hash).origin(RuntimeOrigin::root()).build(), - DispatchError::BadOrigin - ); - }); -} - -#[test] -fn only_upload_origin_can_upload() { - let (binary, _) = compile_module("dummy").unwrap(); - UploadAccount::set(Some(ALICE)); - ExtBuilder::default().build().execute_with(|| { - let _ = Balances::set_balance(&ALICE, 1_000_000); - let _ = Balances::set_balance(&BOB, 1_000_000); - - assert_err!( - Contracts::upload_code(RuntimeOrigin::root(), binary.clone(), deposit_limit::(),), - DispatchError::BadOrigin - ); - - assert_err!( - Contracts::upload_code( - RuntimeOrigin::signed(BOB), - binary.clone(), - deposit_limit::(), - ), - DispatchError::BadOrigin - ); - - // Only alice is allowed to upload contract code. - assert_ok!(Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - binary.clone(), - deposit_limit::(), - )); - }); -} - -#[test] -fn only_instantiation_origin_can_instantiate() { - let (code, code_hash) = compile_module("dummy").unwrap(); - InstantiateAccount::set(Some(ALICE)); - ExtBuilder::default().build().execute_with(|| { - let _ = Balances::set_balance(&ALICE, 1_000_000); - let _ = Balances::set_balance(&BOB, 1_000_000); - - assert_err_ignore_postinfo!( - builder::instantiate_with_code(code.clone()) - .origin(RuntimeOrigin::root()) - .build(), - DispatchError::BadOrigin - ); - - assert_err_ignore_postinfo!( - builder::instantiate_with_code(code.clone()) - .origin(RuntimeOrigin::signed(BOB)) - .build(), - DispatchError::BadOrigin - ); - - // Only Alice can instantiate - assert_ok!(builder::instantiate_with_code(code).build()); - - // Bob cannot instantiate with either `instantiate_with_code` or `instantiate`. - assert_err_ignore_postinfo!( - builder::instantiate(code_hash).origin(RuntimeOrigin::signed(BOB)).build(), - DispatchError::BadOrigin - ); - }); -} - -#[test] -fn balance_of_api() { - let (binary, _code_hash) = compile_module("balance_of").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = Balances::set_balance(&ALICE, 1_000_000); - let _ = Balances::set_balance(&ALICE_FALLBACK, 1_000_000); - - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(binary.to_vec())).build_and_unwrap_contract(); - - // The fixture asserts a non-zero returned free balance of the account; - // The ALICE_FALLBACK account is endowed; - // Hence we should not revert - assert_ok!(builder::call(addr).data(ALICE_ADDR.0.to_vec()).build()); - - // The fixture asserts a non-zero returned free balance of the account; - // The ETH_BOB account is not endowed; - // Hence we should revert - assert_err_ignore_postinfo!( - builder::call(addr).data(BOB_ADDR.0.to_vec()).build(), - >::ContractTrapped - ); - }); -} - -#[test] -fn balance_api_returns_free_balance() { - let (binary, _code_hash) = compile_module("balance").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Instantiate the BOB contract without any extra balance. - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(binary.to_vec())).build_and_unwrap_contract(); - - let value = 0; - // Call BOB which makes it call the balance runtime API. - // The contract code asserts that the returned balance is 0. - assert_ok!(builder::call(addr).value(value).build()); - - let value = 1; - // Calling with value will trap the contract. - assert_err_ignore_postinfo!( - builder::call(addr).value(value).build(), - >::ContractTrapped - ); - }); -} - -#[test] -fn call_depth_is_enforced() { - let (binary, _code_hash) = compile_module("recurse").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let extra_recursions = 1024; - - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(binary.to_vec())).build_and_unwrap_contract(); - - // takes the number of recursions - // returns the number of left over recursions - assert_eq!( - u32::from_le_bytes( - builder::bare_call(addr) - .data((limits::CALL_STACK_DEPTH + extra_recursions).encode()) - .build_and_unwrap_result() - .data - .try_into() - .unwrap() - ), - // + 1 because when the call depth is reached the caller contract is trapped without - // the ability to return any data. hence the last call frame is untracked. - extra_recursions + 1, - ); - }); -} - -#[test] -fn gas_consumed_is_linear_for_nested_calls() { - let (code, _code_hash) = compile_module("recurse").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - let [gas_0, gas_1, gas_2, gas_max] = { - [0u32, 1u32, 2u32, limits::CALL_STACK_DEPTH] - .iter() - .map(|i| { - let result = builder::bare_call(addr).data(i.encode()).build(); - assert_eq!( - u32::from_le_bytes(result.result.unwrap().data.try_into().unwrap()), - 0 - ); - result.gas_consumed - }) - .collect::>() - .try_into() - .unwrap() - }; - - let gas_per_recursion = gas_2.checked_sub(&gas_1).unwrap(); - assert_eq!(gas_max, gas_0 + gas_per_recursion * limits::CALL_STACK_DEPTH as u64); - }); -} - -#[test] -fn read_only_call_cannot_store() { - let (binary_caller, _code_hash_caller) = compile_module("read_only_call").unwrap(); - let (binary_callee, _code_hash_callee) = compile_module("store_call").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create both contracts: Constructors do nothing. - let Contract { addr: addr_caller, .. } = - builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); - - // Read-only call fails when modifying storage. - assert_err_ignore_postinfo!( - builder::call(addr_caller).data((&addr_callee, 100u32).encode()).build(), - >::ContractTrapped - ); - }); -} - -#[test] -fn read_only_call_cannot_transfer() { - let (binary_caller, _code_hash_caller) = compile_module("call_with_flags_and_value").unwrap(); - let (binary_callee, _code_hash_callee) = compile_module("dummy").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create both contracts: Constructors do nothing. - let Contract { addr: addr_caller, .. } = - builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); - - // Read-only call fails when a non-zero value is set. - assert_err_ignore_postinfo!( - builder::call(addr_caller) - .data( - (addr_callee, pallet_revive_uapi::CallFlags::READ_ONLY.bits(), 100u64).encode() - ) - .build(), - >::StateChangeDenied - ); - }); -} - -#[test] -fn read_only_subsequent_call_cannot_store() { - let (binary_read_only_caller, _code_hash_caller) = compile_module("read_only_call").unwrap(); - let (binary_caller, _code_hash_caller) = compile_module("call_with_flags_and_value").unwrap(); - let (binary_callee, _code_hash_callee) = compile_module("store_call").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create contracts: Constructors do nothing. - let Contract { addr: addr_caller, .. } = - builder::bare_instantiate(Code::Upload(binary_read_only_caller)) - .build_and_unwrap_contract(); - let Contract { addr: addr_subsequent_caller, .. } = - builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); - - // Subsequent call input. - let input = (&addr_callee, pallet_revive_uapi::CallFlags::empty().bits(), 0u64, 100u32); - - // Read-only call fails when modifying storage. - assert_err_ignore_postinfo!( - builder::call(addr_caller) - .data((&addr_subsequent_caller, input).encode()) - .build(), - >::ContractTrapped - ); - }); -} - -#[test] -fn read_only_call_works() { - let (binary_caller, _code_hash_caller) = compile_module("read_only_call").unwrap(); - let (binary_callee, _code_hash_callee) = compile_module("dummy").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create both contracts: Constructors do nothing. - let Contract { addr: addr_caller, .. } = - builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); - - assert_ok!(builder::call(addr_caller).data(addr_callee.encode()).build()); - }); -} - -#[test] -fn create1_with_value_works() { - let (code, code_hash) = compile_module("create1_with_value").unwrap(); - let value = 42; - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create the contract: Constructor does nothing. - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // Call the contract: Deploys itself using create1 and the expected value - assert_ok!(builder::call(addr).value(value).data(code_hash.encode()).build()); - - // We should see the expected balance at the expected account - let address = crate::address::create1(&addr, 1); - let account_id = ::AddressMapper::to_account_id(&address); - let usable_balance = ::Currency::usable_balance(&account_id); - assert_eq!(usable_balance, value); - }); -} - -#[test] -fn gas_price_api_works() { - let (code, _) = compile_module("gas_price").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create fixture: Constructor does nothing - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // Call the contract: It echoes back the value returned by the gas price API. - let received = builder::bare_call(addr).build_and_unwrap_result(); - assert_eq!(received.flags, ReturnFlags::empty()); - assert_eq!(u64::from_le_bytes(received.data[..].try_into().unwrap()), u64::from(GAS_PRICE)); - }); -} - -#[test] -fn base_fee_api_works() { - let (code, _) = compile_module("base_fee").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create fixture: Constructor does nothing - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // Call the contract: It echoes back the value returned by the base fee API. - let received = builder::bare_call(addr).build_and_unwrap_result(); - assert_eq!(received.flags, ReturnFlags::empty()); - assert_eq!(U256::from_little_endian(received.data[..].try_into().unwrap()), U256::zero()); - }); -} - -#[test] -fn call_data_size_api_works() { - let (code, _) = compile_module("call_data_size").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create fixture: Constructor does nothing - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // Call the contract: It echoes back the value returned by the call data size API. - let received = builder::bare_call(addr).build_and_unwrap_result(); - assert_eq!(received.flags, ReturnFlags::empty()); - assert_eq!(u64::from_le_bytes(received.data.try_into().unwrap()), 0); - - let received = builder::bare_call(addr).data(vec![1; 256]).build_and_unwrap_result(); - assert_eq!(received.flags, ReturnFlags::empty()); - assert_eq!(u64::from_le_bytes(received.data.try_into().unwrap()), 256); - }); -} - -#[test] -fn call_data_copy_api_works() { - let (code, _) = compile_module("call_data_copy").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create fixture: Constructor does nothing - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // Call fixture: Expects an input of [255; 32] and executes tests. - assert_ok!(builder::call(addr).data(vec![255; 32]).build()); - }); -} - -#[test] -fn static_data_limit_is_enforced() { - let (oom_rw_trailing, _) = compile_module("oom_rw_trailing").unwrap(); - let (oom_rw_included, _) = compile_module("oom_rw_included").unwrap(); - let (oom_ro, _) = compile_module("oom_ro").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - let _ = Balances::set_balance(&ALICE, 1_000_000); - - assert_err!( - Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - oom_rw_trailing, - deposit_limit::(), - ), - >::StaticMemoryTooLarge - ); - - assert_err!( - Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - oom_rw_included, - deposit_limit::(), - ), - >::BlobTooLarge - ); - - assert_err!( - Contracts::upload_code(RuntimeOrigin::signed(ALICE), oom_ro, deposit_limit::(),), - >::BlobTooLarge - ); - }); -} - -#[test] -fn call_diverging_out_len_works() { - let (code, _) = compile_module("call_diverging_out_len").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create the contract: Constructor does nothing - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // Call the contract: It will issue calls and deploys, asserting on - // correct output if the supplied output length was smaller than - // than what the callee returned. - assert_ok!(builder::call(addr).build()); - }); -} - -#[test] -fn chain_id_works() { - let (code, _) = compile_module("chain_id").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let chain_id = U256::from(::ChainId::get()); - let received = builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_result(); - assert_eq!(received.result.data, chain_id.encode()); - }); -} - -#[test] -fn call_data_load_api_works() { - let (code, _) = compile_module("call_data_load").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create fixture: Constructor does nothing - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // Call the contract: It reads a byte for the offset and then returns - // what call data load returned using this byte as the offset. - let input = (3u8, U256::max_value(), U256::max_value()).encode(); - let received = builder::bare_call(addr).data(input).build().result.unwrap(); - assert_eq!(received.flags, ReturnFlags::empty()); - assert_eq!(U256::from_little_endian(&received.data), U256::max_value()); - - // Edge case - let input = (2u8, U256::from(255).to_big_endian()).encode(); - let received = builder::bare_call(addr).data(input).build().result.unwrap(); - assert_eq!(received.flags, ReturnFlags::empty()); - assert_eq!(U256::from_little_endian(&received.data), U256::from(65280)); - - // Edge case - let received = builder::bare_call(addr).data(vec![1]).build().result.unwrap(); - assert_eq!(received.flags, ReturnFlags::empty()); - assert_eq!(U256::from_little_endian(&received.data), U256::zero()); - - // OOB case - let input = (42u8).encode(); - let received = builder::bare_call(addr).data(input).build().result.unwrap(); - assert_eq!(received.flags, ReturnFlags::empty()); - assert_eq!(U256::from_little_endian(&received.data), U256::zero()); - - // No calldata should return the zero value - let received = builder::bare_call(addr).build().result.unwrap(); - assert_eq!(received.flags, ReturnFlags::empty()); - assert_eq!(U256::from_little_endian(&received.data), U256::zero()); - }); -} - -#[test] -fn return_data_api_works() { - let (code_return_data_api, _) = compile_module("return_data_api").unwrap(); - let (code_return_with_data, hash_return_with_data) = - compile_module("return_with_data").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Upload the io echoing fixture for later use - assert_ok!(Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - code_return_with_data, - deposit_limit::(), - )); - - // Create fixture: Constructor does nothing - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code_return_data_api)) - .build_and_unwrap_contract(); - - // Call the contract: It will issue calls and deploys, asserting on - assert_ok!(builder::call(addr) - .value(10 * 1024) - .data(hash_return_with_data.encode()) - .build()); - }); -} - -#[test] -fn immutable_data_works() { - let (code, _) = compile_module("immutable_data").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let data = [0xfe; 8]; - - // Create fixture: Constructor sets the immtuable data - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .data(data.to_vec()) - .build_and_unwrap_contract(); - - let contract = test_utils::get_contract(&addr); - let account = ::AddressMapper::to_account_id(&addr); - let actual_deposit = - test_utils::get_balance_on_hold(&HoldReason::StorageDepositReserve.into(), &account); - - assert_eq!(contract.immutable_data_len(), data.len() as u32); - - // Storing immmutable data charges storage deposit; verify it explicitly. - assert_eq!(actual_deposit, test_utils::contract_base_deposit(&addr)); - - // make sure it is also recorded in the base deposit - assert_eq!( - test_utils::get_balance_on_hold(&HoldReason::StorageDepositReserve.into(), &account), - contract.storage_base_deposit(), - ); - - // Call the contract: Asserts the input to equal the immutable data - assert_ok!(builder::call(addr).data(data.to_vec()).build()); - }); -} - -#[test] -fn sbrk_cannot_be_deployed() { - let (code, _) = compile_module("sbrk").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - let _ = Balances::set_balance(&ALICE, 1_000_000); - - assert_err!( - Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - code.clone(), - deposit_limit::(), - ), - >::InvalidInstruction - ); - - assert_err!( - builder::bare_instantiate(Code::Upload(code)).build().result, - >::InvalidInstruction - ); - }); -} - -#[test] -fn overweight_basic_block_cannot_be_deployed() { - let (code, _) = compile_module("basic_block").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - let _ = Balances::set_balance(&ALICE, 1_000_000); - - assert_err!( - Contracts::upload_code( - RuntimeOrigin::signed(ALICE), - code.clone(), - deposit_limit::(), - ), - >::BasicBlockTooLarge - ); - - assert_err!( - builder::bare_instantiate(Code::Upload(code)).build().result, - >::BasicBlockTooLarge - ); - }); -} - -#[test] -fn origin_api_works() { - let (code, _) = compile_module("origin").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create fixture: Constructor does nothing - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // Call the contract: Asserts the origin API to work as expected - assert_ok!(builder::call(addr).build()); - }); -} - -#[test] -fn code_hash_works() { - use crate::precompiles::{Precompile, EVM_REVERT}; - use precompiles::NoInfo; - - let builtin_precompile = H160(NoInfo::::MATCHER.base_address()); - let primitive_precompile = H160::from_low_u64_be(1); - - let (code_hash_code, self_code_hash) = compile_module("code_hash").unwrap(); - let (dummy_code, code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().existential_deposit(1).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code_hash_code)).build_and_unwrap_contract(); - let Contract { addr: dummy_addr, .. } = - builder::bare_instantiate(Code::Upload(dummy_code)).build_and_unwrap_contract(); - - // code hash of dummy contract - assert_ok!(builder::call(addr).data((dummy_addr, code_hash).encode()).build()); - // code hash of itself - assert_ok!(builder::call(addr).data((addr, self_code_hash).encode()).build()); - // code hash of primitive pre-compile (exist but have no bytecode) - assert_ok!(builder::call(addr) - .data((primitive_precompile, crate::exec::EMPTY_CODE_HASH).encode()) - .build()); - // code hash of normal pre-compile (do have a bytecode) - assert_ok!(builder::call(addr) - .data((builtin_precompile, sp_io::hashing::keccak_256(&EVM_REVERT)).encode()) - .build()); - - // EOA doesn't exists - assert_err!( - builder::bare_call(addr) - .data((BOB_ADDR, crate::exec::EMPTY_CODE_HASH).encode()) - .build() - .result, - Error::::ContractTrapped - ); - // non-existing will return zero - assert_ok!(builder::call(addr).data((BOB_ADDR, H256::zero()).encode()).build()); - - // create EOA - let _ = ::Currency::set_balance( - &::AddressMapper::to_account_id(&BOB_ADDR), - 1_000_000, - ); - - // EOA returns empty code hash - assert_ok!(builder::call(addr) - .data((BOB_ADDR, crate::exec::EMPTY_CODE_HASH).encode()) - .build()); - }); -} - -#[test] -fn code_size_works() { - let (tester_code, _) = compile_module("extcodesize").unwrap(); - let tester_code_len = tester_code.len() as u64; - - let (dummy_code, _) = compile_module("dummy").unwrap(); - let dummy_code_len = dummy_code.len() as u64; - - ExtBuilder::default().existential_deposit(1).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - let Contract { addr: tester_addr, .. } = - builder::bare_instantiate(Code::Upload(tester_code)).build_and_unwrap_contract(); - let Contract { addr: dummy_addr, .. } = - builder::bare_instantiate(Code::Upload(dummy_code)).build_and_unwrap_contract(); - - // code size of another contract address - assert_ok!(builder::call(tester_addr).data((dummy_addr, dummy_code_len).encode()).build()); - - // code size of own contract address - assert_ok!(builder::call(tester_addr) - .data((tester_addr, tester_code_len).encode()) - .build()); - - // code size of non contract accounts - assert_ok!(builder::call(tester_addr).data(([8u8; 20], 0u64).encode()).build()); - }); -} - -#[test] -fn origin_must_be_mapped() { - let (code, hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - ::Currency::set_balance(&ALICE, 1_000_000); - ::Currency::set_balance(&EVE, 1_000_000); - - let eve = RuntimeOrigin::signed(EVE); - - // alice can instantiate as she doesn't need a mapping - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // without a mapping eve can neither call nor instantiate - assert_err!( - builder::bare_call(addr).origin(eve.clone()).build().result, - >::AccountUnmapped - ); - assert_err!( - builder::bare_instantiate(Code::Existing(hash)) - .origin(eve.clone()) - .build() - .result, - >::AccountUnmapped - ); - - // after mapping eve is usable as an origin - >::map_account(eve.clone()).unwrap(); - assert_ok!(builder::bare_call(addr).origin(eve.clone()).build().result); - assert_ok!(builder::bare_instantiate(Code::Existing(hash)).origin(eve).build().result); - }); -} - -#[test] -fn mapped_address_works() { - let (code, _) = compile_module("terminate_and_send_to_argument").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - ::Currency::set_balance(&ALICE, 1_000_000); - - // without a mapping everything will be send to the fallback account - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code.clone())).build_and_unwrap_contract(); - assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 0); - builder::bare_call(addr).data(EVE_ADDR.encode()).build_and_unwrap_result(); - assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 100); - - // after mapping it will be sent to the real eve account - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - // need some balance to pay for the map deposit - ::Currency::set_balance(&EVE, 1_000); - >::map_account(RuntimeOrigin::signed(EVE)).unwrap(); - builder::bare_call(addr).data(EVE_ADDR.encode()).build_and_unwrap_result(); - assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 100); - assert_eq!(::Currency::total_balance(&EVE), 1_100); - }); -} - -#[test] -fn recovery_works() { - let (code, _) = compile_module("terminate_and_send_to_argument").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - ::Currency::set_balance(&ALICE, 1_000_000); - - // eve puts her AccountId20 as argument to terminate but forgot to register - // her AccountId32 first so now the funds are trapped in her fallback account - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code.clone())).build_and_unwrap_contract(); - assert_eq!(::Currency::total_balance(&EVE), 0); - assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 0); - builder::bare_call(addr).data(EVE_ADDR.encode()).build_and_unwrap_result(); - assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 100); - assert_eq!(::Currency::total_balance(&EVE), 0); - - let call = RuntimeCall::Balances(pallet_balances::Call::transfer_all { - dest: EVE, - keep_alive: false, - }); - - // she now uses the recovery function to move all funds from the fallback - // account to her real account - >::dispatch_as_fallback_account(RuntimeOrigin::signed(EVE), Box::new(call)) - .unwrap(); - assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 0); - assert_eq!(::Currency::total_balance(&EVE), 100); - }); -} - -#[test] -fn skip_transfer_works() { - let (code_caller, _) = compile_module("call").unwrap(); - let (code, _) = compile_module("store_call").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - ::Currency::set_balance(&ALICE, 1_000_000); - ::Currency::set_balance(&BOB, 0); - - // when gas is some (transfers enabled): bob has no money: fail - assert_err!( - Pallet::::dry_run_eth_transact( - GenericTransaction { - from: Some(BOB_ADDR), - input: code.clone().into(), - gas: Some(1u32.into()), - ..Default::default() - }, - Weight::MAX, - |_, _| 0u64, - ), - EthTransactError::Message(format!( - "insufficient funds for gas * price + value: address {BOB_ADDR:?} have 0 (supplied gas 1)" - )) - ); - - // no gas specified (all transfers are skipped): even without money bob can deploy - assert_ok!(Pallet::::dry_run_eth_transact( - GenericTransaction { - from: Some(BOB_ADDR), - input: code.clone().into(), - ..Default::default() - }, - Weight::MAX, - |_, _| 0u64, - )); - - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - let Contract { addr: caller_addr, .. } = - builder::bare_instantiate(Code::Upload(code_caller)).build_and_unwrap_contract(); - - // call directly: fails with enabled transfers - assert_err!( - Pallet::::dry_run_eth_transact( - GenericTransaction { - from: Some(BOB_ADDR), - to: Some(addr), - input: 0u32.encode().into(), - gas: Some(1u32.into()), - ..Default::default() - }, - Weight::MAX, - |_, _| 0u64, - ), - EthTransactError::Message(format!( - "insufficient funds for gas * price + value: address {BOB_ADDR:?} have 0 (supplied gas 1)" - )) - ); - - // fails to call through other contract - // we didn't roll back the storage changes done by the previous - // call. So the item already exists. We simply increase the size of - // the storage item to incur some deposits (which bob can't pay). - assert!(Pallet::::dry_run_eth_transact( - GenericTransaction { - from: Some(BOB_ADDR), - to: Some(caller_addr), - input: (1u32, &addr).encode().into(), - gas: Some(1u32.into()), - ..Default::default() - }, - Weight::MAX, - |_, _| 0u64, - ) - .is_err(),); - - // works when no gas is specified (skip transfer) - assert_ok!(Pallet::::dry_run_eth_transact( - GenericTransaction { - from: Some(BOB_ADDR), - to: Some(addr), - input: 2u32.encode().into(), - ..Default::default() - }, - Weight::MAX, - |_, _| 0u64, - )); - - // call through contract works when transfers are skipped - assert_ok!(Pallet::::dry_run_eth_transact( - GenericTransaction { - from: Some(BOB_ADDR), - to: Some(caller_addr), - input: (3u32, &addr).encode().into(), - ..Default::default() - }, - Weight::MAX, - |_, _| 0u64, - )); - - // works with transfers enabled if we don't incur a storage cost - // we shrink the item so its actually a refund - assert_ok!(Pallet::::dry_run_eth_transact( - GenericTransaction { - from: Some(BOB_ADDR), - to: Some(caller_addr), - input: (2u32, &addr).encode().into(), - gas: Some(1u32.into()), - ..Default::default() - }, - Weight::MAX, - |_, _| 0u64, - )); - - // fails when trying to increase the storage item size - assert!(Pallet::::dry_run_eth_transact( - GenericTransaction { - from: Some(BOB_ADDR), - to: Some(caller_addr), - input: (3u32, &addr).encode().into(), - gas: Some(1u32.into()), - ..Default::default() - }, - Weight::MAX, - |_, _| 0u64, - ) - .is_err()); - }); -} - -#[test] -fn gas_limit_api_works() { - let (code, _) = compile_module("gas_limit").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - - // Create fixture: Constructor does nothing - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - // Call the contract: It echoes back the value returned by the gas limit API. - let received = builder::bare_call(addr).build_and_unwrap_result(); - assert_eq!(received.flags, ReturnFlags::empty()); - assert_eq!( - u64::from_le_bytes(received.data[..].try_into().unwrap()), - ::BlockWeights::get().max_block.ref_time() - ); - }); -} - -#[test] -fn unknown_syscall_rejected() { - let (code, _) = compile_module("unknown_syscall").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - ::Currency::set_balance(&ALICE, 1_000_000); - - assert_err!( - builder::bare_instantiate(Code::Upload(code)).build().result, - >::CodeRejected, - ) - }); -} - -#[test] -fn unstable_interface_rejected() { - let (code, _) = compile_module("unstable_interface").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - ::Currency::set_balance(&ALICE, 1_000_000); - - Test::set_unstable_interface(false); - assert_err!( - builder::bare_instantiate(Code::Upload(code.clone())).build().result, - >::CodeRejected, - ); - - Test::set_unstable_interface(true); - assert_ok!(builder::bare_instantiate(Code::Upload(code)).build().result); - }); -} - -#[test] -fn tracing_works_for_transfers() { - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000); - let mut tracer = CallTracer::new(Default::default(), |_| U256::zero()); - trace(&mut tracer, || { - builder::bare_call(BOB_ADDR).evm_value(10.into()).build_and_unwrap_result(); - }); - - let trace = tracer.collect_trace(); - assert_eq!( - trace, - Some(CallTrace { - from: ALICE_ADDR, - to: BOB_ADDR, - value: Some(U256::from(10)), - call_type: CallType::Call, - ..Default::default() - }) - ) - }); -} - -#[test] -fn call_tracing_works() { - use crate::evm::*; - use CallType::*; - let (code, _code_hash) = compile_module("tracing").unwrap(); - let (binary_callee, _) = compile_module("tracing_callee").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000); - - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); - - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).evm_value(10_000_000.into()).build_and_unwrap_contract(); - - - let tracer_configs = vec![ - CallTracerConfig{ with_logs: false, only_top_call: false}, - CallTracerConfig{ with_logs: false, only_top_call: false}, - CallTracerConfig{ with_logs: false, only_top_call: true}, - ]; - - // Verify that the first trace report the same weight reported by bare_call - // TODO: fix tracing ( https://github.com/paritytech/polkadot-sdk/issues/8362 ) - /* - let mut tracer = CallTracer::new(false, |w| w); - let gas_used = trace(&mut tracer, || { - builder::bare_call(addr).data((3u32, addr_callee).encode()).build().gas_consumed - }); - let trace = tracer.collect_trace().unwrap(); - assert_eq!(&trace.gas_used, &gas_used); - */ - - // Discarding gas usage, check that traces reported are correct - for config in tracer_configs { - let logs = if config.with_logs { - vec![ - CallLog { - address: addr, - topics: Default::default(), - data: b"before".to_vec().into(), - position: 0, - }, - CallLog { - address: addr, - topics: Default::default(), - data: b"after".to_vec().into(), - position: 1, - }, - ] - } else { - vec![] - }; - - let calls = if config.only_top_call { - vec![] - } else { - vec![ - CallTrace { - from: addr, - to: addr_callee, - input: 2u32.encode().into(), - output: hex_literal::hex!( - "08c379a00000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000001a546869732066756e6374696f6e20616c77617973206661696c73000000000000" - ).to_vec().into(), - revert_reason: Some("revert: This function always fails".to_string()), - error: Some("execution reverted".to_string()), - call_type: Call, - value: Some(U256::from(0)), - ..Default::default() - }, - CallTrace { - from: addr, - to: addr, - input: (2u32, addr_callee).encode().into(), - call_type: Call, - logs: logs.clone(), - value: Some(U256::from(0)), - calls: vec![ - CallTrace { - from: addr, - to: addr_callee, - input: 1u32.encode().into(), - output: Default::default(), - error: Some("ContractTrapped".to_string()), - call_type: Call, - value: Some(U256::from(0)), - ..Default::default() - }, - CallTrace { - from: addr, - to: addr, - input: (1u32, addr_callee).encode().into(), - call_type: Call, - logs: logs.clone(), - value: Some(U256::from(0)), - calls: vec![ - CallTrace { - from: addr, - to: addr_callee, - input: 0u32.encode().into(), - output: 0u32.to_le_bytes().to_vec().into(), - call_type: Call, - value: Some(U256::from(0)), - ..Default::default() - }, - CallTrace { - from: addr, - to: addr, - input: (0u32, addr_callee).encode().into(), - call_type: Call, - value: Some(U256::from(0)), - calls: vec![ - CallTrace { - from: addr, - to: BOB_ADDR, - value: Some(U256::from(100)), - call_type: CallType::Call, - ..Default::default() - } - ], - ..Default::default() - }, - ], - ..Default::default() - }, - ], - ..Default::default() - }, - ] - }; - - let mut tracer = CallTracer::new(config, |_| U256::zero()); - trace(&mut tracer, || { - builder::bare_call(addr).data((3u32, addr_callee).encode()).build() - }); - - let trace = tracer.collect_trace(); - let expected_trace = CallTrace { - from: ALICE_ADDR, - to: addr, - input: (3u32, addr_callee).encode().into(), - call_type: Call, - logs: logs.clone(), - value: Some(U256::from(0)), - calls: calls, - ..Default::default() - }; - - assert_eq!( - trace, - expected_trace.into(), - ); - } - }); -} - -#[test] -fn create_call_tracing_works() { - use crate::evm::*; - let (code, code_hash) = compile_module("create2_with_value").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000); - - let mut tracer = CallTracer::new(Default::default(), |_| U256::zero()); - - let Contract { addr, .. } = trace(&mut tracer, || { - builder::bare_instantiate(Code::Upload(code.clone())) - .evm_value(100.into()) - .salt(None) - .build_and_unwrap_contract() - }); - - let call_trace = tracer.collect_trace().unwrap(); - assert_eq!( - call_trace, - CallTrace { - from: ALICE_ADDR, - to: addr, - value: Some(100.into()), - input: Bytes(code.clone()), - call_type: CallType::Create, - ..Default::default() - } - ); - - let mut tracer = CallTracer::new(Default::default(), |_| U256::zero()); - let data = b"garbage"; - let input = (code_hash, data).encode(); - trace(&mut tracer, || { - assert_ok!(builder::call(addr).data(input.clone()).build()); - }); - - let call_trace = tracer.collect_trace().unwrap(); - let child_addr = crate::address::create2(&addr, &code, data, &[1u8; 32]); - - assert_eq!( - call_trace, - CallTrace { - from: ALICE_ADDR, - to: addr, - value: Some(0.into()), - input: input.clone().into(), - calls: vec![CallTrace { - from: addr, - input: input.clone().into(), - to: child_addr, - value: Some(0.into()), - call_type: CallType::Create2, - ..Default::default() - },], - ..Default::default() - } - ); - }); -} - -#[test] -fn prestate_tracing_works() { - use crate::evm::*; - use alloc::collections::BTreeMap; - - let (dummy_code, _) = compile_module("dummy").unwrap(); - let (code, _) = compile_module("tracing").unwrap(); - let (callee_code, _) = compile_module("tracing_callee").unwrap(); - ExtBuilder::default().existential_deposit(200).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000); - - let Contract { addr: addr_callee, .. } = - builder::bare_instantiate(Code::Upload(callee_code.clone())) - .build_and_unwrap_contract(); - - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code.clone())) - .native_value(10) - .build_and_unwrap_contract(); - - // redact balance so that tests are resilient to weight changes - let alice_redacted_balance = Some(U256::from(1)); - - let test_cases: Vec<(Box, _, _)> = vec![ - ( - Box::new(|| { - builder::bare_call(addr) - .data((3u32, addr_callee).encode()) - .build_and_unwrap_result(); - }), - PrestateTracerConfig { - diff_mode: false, - disable_storage: false, - disable_code: false, - }, - PrestateTrace::Prestate(BTreeMap::from([ - ( - ALICE_ADDR, - PrestateTraceInfo { - balance: alice_redacted_balance, - nonce: Some(2), - ..Default::default() - }, - ), - ( - BOB_ADDR, - PrestateTraceInfo { balance: Some(U256::from(0u64)), ..Default::default() }, - ), - ( - addr_callee, - PrestateTraceInfo { - balance: Some(U256::from(0u64)), - code: Some(Bytes(callee_code.clone())), - nonce: Some(1), - ..Default::default() - }, - ), - ( - addr, - PrestateTraceInfo { - balance: Some(U256::from(10_000_000u64)), - code: Some(Bytes(code.clone())), - nonce: Some(1), - ..Default::default() - }, - ), - ])), - ), - ( - Box::new(|| { - builder::bare_call(addr) - .data((3u32, addr_callee).encode()) - .build_and_unwrap_result(); - }), - PrestateTracerConfig { - diff_mode: true, - disable_storage: false, - disable_code: false, - }, - PrestateTrace::DiffMode { - pre: BTreeMap::from([ - ( - BOB_ADDR, - PrestateTraceInfo { - balance: Some(U256::from(100u64)), - ..Default::default() - }, - ), - ( - addr, - PrestateTraceInfo { - balance: Some(U256::from(9_999_900u64)), - code: Some(Bytes(code.clone())), - nonce: Some(1), - ..Default::default() - }, - ), - ]), - post: BTreeMap::from([ - ( - BOB_ADDR, - PrestateTraceInfo { - balance: Some(U256::from(200u64)), - ..Default::default() - }, - ), - ( - addr, - PrestateTraceInfo { - balance: Some(U256::from(9_999_800u64)), - ..Default::default() - }, - ), - ]), - }, - ), - ( - Box::new(|| { - builder::bare_instantiate(Code::Upload(dummy_code.clone())) - .salt(None) - .build_and_unwrap_result(); - }), - PrestateTracerConfig { - diff_mode: true, - disable_storage: false, - disable_code: false, - }, - PrestateTrace::DiffMode { - pre: BTreeMap::from([( - ALICE_ADDR, - PrestateTraceInfo { - balance: alice_redacted_balance, - nonce: Some(2), - ..Default::default() - }, - )]), - post: BTreeMap::from([ - ( - ALICE_ADDR, - PrestateTraceInfo { - balance: alice_redacted_balance, - nonce: Some(3), - ..Default::default() - }, - ), - ( - create1(&ALICE_ADDR, 1), - PrestateTraceInfo { - code: Some(dummy_code.clone().into()), - balance: Some(U256::from(0)), - nonce: Some(1), - ..Default::default() - }, - ), - ]), - }, - ), - ]; - - for (exec_call, config, expected_trace) in test_cases.into_iter() { - let mut tracer = PrestateTracer::::new(config); - trace(&mut tracer, || { - exec_call(); - }); - - let mut trace = tracer.collect_trace(); - - // redact alice balance - match trace { - PrestateTrace::DiffMode { ref mut pre, ref mut post } => { - pre.get_mut(&ALICE_ADDR).map(|info| { - info.balance = alice_redacted_balance; - }); - post.get_mut(&ALICE_ADDR).map(|info| { - info.balance = alice_redacted_balance; - }); - }, - PrestateTrace::Prestate(ref mut pre) => { - pre.get_mut(&ALICE_ADDR).map(|info| { - info.balance = alice_redacted_balance; - }); - }, - } - - assert_eq!(trace, expected_trace); - } - }); -} - -#[test] -fn unknown_precompiles_revert() { - let (code, _code_hash) = compile_module("read_only_call").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - let cases: Vec<(H160, Box)> = vec![( - H160::from_low_u64_be(0x0a), - Box::new(|result| { - assert_err!(result, >::UnsupportedPrecompileAddress); - }), - )]; - - for (callee_addr, assert_result) in cases { - let result = - builder::bare_call(addr).data((callee_addr, [0u8; 0]).encode()).build().result; - assert_result(result); - } - }); -} - -#[test] -fn pure_precompile_works() { - use hex_literal::hex; - - let cases = vec![ - ( - "ECRecover", - H160::from_low_u64_be(1), - hex!("18c547e4f7b0f325ad1e56f57e26c745b09a3e503d86e00e5255ff7f715d3d1c000000000000000000000000000000000000000000000000000000000000001c73b1693892219d736caba55bdb67216e485557ea6b6af75f37096c9aa6a5a75feeb940b1d03b21e36b0e47e79769f095fe2ab855bd91e3a38756b7d75a9c4549").to_vec(), - hex!("000000000000000000000000a94f5374fce5edbc8e2a8697c15331677e6ebf0b").to_vec(), - ), - ( - "Sha256", - H160::from_low_u64_be(2), - hex!("ec07171c4f0f0e2b").to_vec(), - hex!("d0591ea667763c69a5f5a3bae657368ea63318b2c9c8349cccaf507e3cbd7c7a").to_vec(), - ), - ( - "Ripemd160", - H160::from_low_u64_be(3), - hex!("ec07171c4f0f0e2b").to_vec(), - hex!("000000000000000000000000a9c5ebaf7589fd8acfd542c3a008956de84fbeb7").to_vec(), - ), - ( - "Identity", - H160::from_low_u64_be(4), - [42u8; 128].to_vec(), - [42u8; 128].to_vec(), - ), - ( - "Modexp", - H160::from_low_u64_be(5), - hex!("00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000002003fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2efffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f").to_vec(), - hex!("0000000000000000000000000000000000000000000000000000000000000001").to_vec(), - ), - ( - "Bn128Add", - H160::from_low_u64_be(6), - hex!("18b18acfb4c2c30276db5411368e7185b311dd124691610c5d3b74034e093dc9063c909c4720840cb5134cb9f59fa749755796819658d32efc0d288198f3726607c2b7f58a84bd6145f00c9c2bc0bb1a187f20ff2c92963a88019e7c6a014eed06614e20c147e940f2d70da3f74c9a17df361706a4485c742bd6788478fa17d7").to_vec(), - hex!("2243525c5efd4b9c3d3c45ac0ca3fe4dd85e830a4ce6b65fa1eeaee202839703301d1d33be6da8e509df21cc35964723180eed7532537db9ae5e7d48f195c915").to_vec(), - ), - ( - "Bn128Mul", - H160::from_low_u64_be(7), - hex!("2bd3e6d0f3b142924f5ca7b49ce5b9d54c4703d7ae5648e61d02268b1a0a9fb721611ce0a6af85915e2f1d70300909ce2e49dfad4a4619c8390cae66cefdb20400000000000000000000000000000000000000000000000011138ce750fa15c2").to_vec(), - hex!("070a8d6a982153cae4be29d434e8faef8a47b274a053f5a4ee2a6c9c13c31e5c031b8ce914eba3a9ffb989f9cdd5b0f01943074bf4f0f315690ec3cec6981afc").to_vec(), - ), - ( - "Bn128Pairing", - H160::from_low_u64_be(8), - hex!("1c76476f4def4bb94541d57ebba1193381ffa7aa76ada664dd31c16024c43f593034dd2920f673e204fee2811c678745fc819b55d3e9d294e45c9b03a76aef41209dd15ebff5d46c4bd888e51a93cf99a7329636c63514396b4a452003a35bf704bf11ca01483bfa8b34b43561848d28905960114c8ac04049af4b6315a416782bb8324af6cfc93537a2ad1a445cfd0ca2a71acd7ac41fadbf933c2a51be344d120a2a4cf30c1bf9845f20c6fe39e07ea2cce61f0c9bb048165fe5e4de877550111e129f1cf1097710d41c4ac70fcdfa5ba2023c6ff1cbeac322de49d1b6df7c2032c61a830e3c17286de9462bf242fca2883585b93870a73853face6a6bf411198e9393920d483a7260bfb731fb5d25f1aa493335a9e71297e485b7aef312c21800deef121f1e76426a00665e5c4479674322d4f75edadd46debd5cd992f6ed090689d0585ff075ec9e99ad690c3395bc4b313370b38ef355acdadcd122975b12c85ea5db8c6deb4aab71808dcb408fe3d1e7690c43d37b4ce6cc0166fa7daa").to_vec(), - hex!("0000000000000000000000000000000000000000000000000000000000000001").to_vec(), - ), - ( - "Blake2F", - H160::from_low_u64_be(9), - hex!("0000000048c9bdf267e6096a3ba7ca8485ae67bb2bf894fe72f36e3cf1361d5f3af54fa5d182e6ad7f520e511f6c3e2b8c68059b6bbd41fbabd9831f79217e1319cde05b61626300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000300000000000000000000000000000001").to_vec(), - hex!("08c9bcf367e6096a3ba7ca8485ae67bb2bf894fe72f36e3cf1361d5f3af54fa5d282e6ad7f520e511f6c3e2b8c68059b9442be0454267ce079217e1319cde05b").to_vec(), - ), - ]; - - for (description, precompile_addr, input, output) in cases { - let (code, _code_hash) = compile_module("call_and_return").unwrap(); - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .native_value(1_000) - .build_and_unwrap_contract(); - - let result = builder::bare_call(addr) - .data( - (&precompile_addr, 100u64) - .encode() - .into_iter() - .chain(input) - .collect::>(), - ) - .build_and_unwrap_result(); - - assert_eq!( - Pallet::::evm_balance(&precompile_addr), - U256::from(100), - "{description}: unexpected balance" - ); - assert_eq!( - alloy_core::hex::encode(result.data), - alloy_core::hex::encode(output), - "{description} Unexpected output for precompile: {precompile_addr:?}", - ); - assert_eq!(result.flags, ReturnFlags::empty()); - }); - } -} - -#[test] -fn precompiles_work() { - use crate::precompiles::Precompile; - use alloy_core::sol_types::{Panic, PanicKind, Revert, SolError, SolInterface, SolValue}; - use precompiles::{INoInfo, NoInfo}; - - let precompile_addr = H160(NoInfo::::MATCHER.base_address()); - - let cases = vec![ - ( - INoInfo::INoInfoCalls::identity(INoInfo::identityCall { number: 42u64.into() }) - .abi_encode(), - 42u64.abi_encode(), - RuntimeReturnCode::Success, - ), - ( - INoInfo::INoInfoCalls::reverts(INoInfo::revertsCall { error: "panic".to_string() }) - .abi_encode(), - Revert::from("panic").abi_encode(), - RuntimeReturnCode::CalleeReverted, - ), - ( - INoInfo::INoInfoCalls::panics(INoInfo::panicsCall {}).abi_encode(), - Panic::from(PanicKind::Assert).abi_encode(), - RuntimeReturnCode::CalleeReverted, - ), - ( - INoInfo::INoInfoCalls::errors(INoInfo::errorsCall {}).abi_encode(), - Vec::new(), - RuntimeReturnCode::CalleeTrapped, - ), - // passing non decodeable input reverts with solidity panic - ( - b"invalid".to_vec(), - Panic::from(PanicKind::ResourceError).abi_encode(), - RuntimeReturnCode::CalleeReverted, - ), - ( - INoInfo::INoInfoCalls::passData(INoInfo::passDataCall { - inputLen: limits::CALLDATA_BYTES, - }) - .abi_encode(), - Vec::new(), - RuntimeReturnCode::Success, - ), - ( - INoInfo::INoInfoCalls::passData(INoInfo::passDataCall { - inputLen: limits::CALLDATA_BYTES + 1, - }) - .abi_encode(), - Vec::new(), - RuntimeReturnCode::CalleeTrapped, - ), - ( - INoInfo::INoInfoCalls::returnData(INoInfo::returnDataCall { - returnLen: limits::CALLDATA_BYTES - 4, - }) - .abi_encode(), - vec![42u8; limits::CALLDATA_BYTES as usize - 4], - RuntimeReturnCode::Success, - ), - ( - INoInfo::INoInfoCalls::returnData(INoInfo::returnDataCall { - returnLen: limits::CALLDATA_BYTES + 1, - }) - .abi_encode(), - vec![], - RuntimeReturnCode::CalleeTrapped, - ), - ]; - - for (input, output, error_code) in cases { - let (code, _code_hash) = compile_module("call_and_returncode").unwrap(); - ExtBuilder::default().build().execute_with(|| { - let id = ::AddressMapper::to_account_id(&precompile_addr); - let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .native_value(1000) - .build_and_unwrap_contract(); - - let result = builder::bare_call(addr) - .data( - (&precompile_addr, 0u64).encode().into_iter().chain(input).collect::>(), - ) - .build_and_unwrap_result(); - - // no account or contract info should be created for a NoInfo pre-compile - assert!(test_utils::get_contract_checked(&precompile_addr).is_none()); - assert!(!System::account_exists(&id)); - assert_eq!(Pallet::::evm_balance(&precompile_addr), U256::zero()); - - assert_eq!(result.flags, ReturnFlags::empty()); - assert_eq!(u32::from_le_bytes(result.data[..4].try_into().unwrap()), error_code as u32); - assert_eq!( - &result.data[4..], - &output, - "Unexpected output for precompile: {precompile_addr:?}", - ); - }); - } -} - -#[test] -fn precompiles_with_info_creates_contract() { - use crate::precompiles::Precompile; - use alloy_core::sol_types::SolInterface; - use precompiles::{IWithInfo, WithInfo}; - - let precompile_addr = H160(WithInfo::::MATCHER.base_address()); - - let cases = vec![( - IWithInfo::IWithInfoCalls::dummy(IWithInfo::dummyCall {}).abi_encode(), - Vec::::new(), - RuntimeReturnCode::Success, - )]; - - for (input, output, error_code) in cases { - let (code, _code_hash) = compile_module("call_and_returncode").unwrap(); - ExtBuilder::default().build().execute_with(|| { - let id = ::AddressMapper::to_account_id(&precompile_addr); - let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .native_value(1000) - .build_and_unwrap_contract(); - - let result = builder::bare_call(addr) - .data( - (&precompile_addr, 0u64).encode().into_iter().chain(input).collect::>(), - ) - .build_and_unwrap_result(); - - // a pre-compile with contract info should create an account on first call - assert!(test_utils::get_contract_checked(&precompile_addr).is_some()); - assert!(System::account_exists(&id)); - assert_eq!(Pallet::::evm_balance(&precompile_addr), U256::from(0)); - - assert_eq!(result.flags, ReturnFlags::empty()); - assert_eq!(u32::from_le_bytes(result.data[..4].try_into().unwrap()), error_code as u32); - assert_eq!( - &result.data[4..], - &output, - "Unexpected output for precompile: {precompile_addr:?}", - ); - }); - } -} - -#[test] -fn bump_nonce_once_works() { - let (code, hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().existential_deposit(100).build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 1_000_000); - frame_system::Account::::mutate(&ALICE, |account| account.nonce = 1); - - let _ = ::Currency::set_balance(&BOB, 1_000_000); - frame_system::Account::::mutate(&BOB, |account| account.nonce = 1); - - builder::bare_instantiate(Code::Upload(code.clone())) - .origin(RuntimeOrigin::signed(ALICE)) - .bump_nonce(BumpNonce::Yes) - .salt(None) - .build_and_unwrap_result(); - assert_eq!(System::account_nonce(&ALICE), 2); - - // instantiate again is ok - let result = builder::bare_instantiate(Code::Existing(hash)) - .origin(RuntimeOrigin::signed(ALICE)) - .bump_nonce(BumpNonce::Yes) - .salt(None) - .build() - .result; - assert!(result.is_ok()); - - builder::bare_instantiate(Code::Upload(code.clone())) - .origin(RuntimeOrigin::signed(BOB)) - .bump_nonce(BumpNonce::No) - .salt(None) - .build_and_unwrap_result(); - assert_eq!(System::account_nonce(&BOB), 1); - - // instantiate again should fail - let err = builder::bare_instantiate(Code::Upload(code)) - .origin(RuntimeOrigin::signed(BOB)) - .bump_nonce(BumpNonce::No) - .salt(None) - .build() - .result - .unwrap_err(); - - assert_eq!(err, >::DuplicateContract.into()); - }); -} - -#[test] -fn code_size_for_precompiles_works() { - use crate::precompiles::Precompile; - use precompiles::NoInfo; - - let builtin_precompile = H160(NoInfo::::MATCHER.base_address()); - let primitive_precompile = H160::from_low_u64_be(1); - - let (code, _code_hash) = compile_module("extcodesize").unwrap(); - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); - let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) - .native_value(1000) - .build_and_unwrap_contract(); - - // the primitive pre-compiles return 0 code size on eth - builder::bare_call(addr) - .data((&primitive_precompile, 0u64).encode()) - .build_and_unwrap_result(); - - // other precompiles should return the minimal evm revert code - builder::bare_call(addr) - .data((&builtin_precompile, 5u64).encode()) - .build_and_unwrap_result(); - }); -} - -#[test] -fn call_data_limit_is_enforced_subcalls() { - let (code, _code_hash) = compile_module("call_with_input_size").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - let cases: Vec<(u32, Box)> = vec![ - ( - 0_u32, - Box::new(|result| { - assert_ok!(result); - }), - ), - ( - 1_u32, - Box::new(|result| { - assert_ok!(result); - }), - ), - ( - limits::CALLDATA_BYTES, - Box::new(|result| { - assert_ok!(result); - }), - ), - ( - limits::CALLDATA_BYTES + 1, - Box::new(|result| { - assert_err!(result, >::CallDataTooLarge); - }), - ), - ]; - - for (callee_input_size, assert_result) in cases { - let result = builder::bare_call(addr).data(callee_input_size.encode()).build().result; - assert_result(result); - } - }); -} - -#[test] -fn call_data_limit_is_enforced_root_call() { - let (code, _code_hash) = compile_module("dummy").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - let cases: Vec<(H160, u32, Box)> = vec![ - ( - addr, - 0_u32, - Box::new(|result| { - assert_ok!(result); - }), - ), - ( - addr, - 1_u32, - Box::new(|result| { - assert_ok!(result); - }), - ), - ( - addr, - limits::CALLDATA_BYTES, - Box::new(|result| { - assert_ok!(result); - }), - ), - ( - addr, - limits::CALLDATA_BYTES + 1, - Box::new(|result| { - assert_err!(result, >::CallDataTooLarge); - }), - ), - ( - // limit is not enforced when tx calls EOA - BOB_ADDR, - limits::CALLDATA_BYTES + 1, - Box::new(|result| { - assert_ok!(result); - }), - ), - ]; - - for (addr, callee_input_size, assert_result) in cases { - let result = builder::bare_call(addr) - .data(vec![42; callee_input_size as usize]) - .build() - .result; - assert_result(result); - } - }); -} - -#[test] -fn return_data_limit_is_enforced() { - let (code, _code_hash) = compile_module("return_sized").unwrap(); - - ExtBuilder::default().build().execute_with(|| { - let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); - let Contract { addr, .. } = - builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); - - let cases: Vec<(u32, Box)> = vec![ - ( - 1_u32, - Box::new(|result| { - assert_ok!(result); - }), - ), - ( - limits::CALLDATA_BYTES, - Box::new(|result| { - assert_ok!(result); - }), - ), - ( - limits::CALLDATA_BYTES + 1, - Box::new(|result| { - assert_err!(result, >::ReturnDataTooLarge); - }), - ), - ]; - - for (return_size, assert_result) in cases { - let result = builder::bare_call(addr).data(return_size.encode()).build().result; - assert_result(result); - } - }); -} diff --git a/substrate/frame/revive/src/tests/pvm.rs b/substrate/frame/revive/src/tests/pvm.rs new file mode 100644 index 0000000000000..81aab74f72f2f --- /dev/null +++ b/substrate/frame/revive/src/tests/pvm.rs @@ -0,0 +1,4892 @@ +// This file is part of Substrate. + +// Copyright (C) Parity Technologies (UK) Ltd. +// SPDX-License-Identifier: Apache-2.0 + +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +//! The pallet-revive PVM specific integration test suite. + +use super::{ + precompiles, + precompiles::{INoInfo, NoInfo}, +}; +use crate::{ + address::{create1, create2, AddressMapper}, + assert_refcount, assert_return_code, + evm::{runtime::GAS_PRICE, CallTrace, CallTracer, CallType, GenericTransaction}, + exec::Key, + limits, + storage::DeletionQueueManager, + test_utils::builder::Contract, + tests::{ + builder, initialize_block, test_utils::*, Balances, CodeHashLockupDepositPercent, + Contracts, DepositPerByte, DepositPerItem, ExtBuilder, InstantiateAccount, RuntimeCall, + RuntimeEvent, RuntimeOrigin, System, Test, UploadAccount, DEPOSIT_PER_BYTE, *, + }, + tracing::trace, + weights::WeightInfo, + AccountInfo, AccountInfoOf, BalanceWithDust, BumpNonce, Code, Config, ContractInfo, + DeletionQueueCounter, DepositLimit, Error, EthTransactError, HoldReason, Pallet, PristineCode, + StorageDeposit, H160, +}; +use assert_matches::assert_matches; +use codec::Encode; +use frame_support::{ + assert_err, assert_err_ignore_postinfo, assert_noop, assert_ok, + storage::child, + traits::{ + fungible::{BalancedHold, Inspect, Mutate, MutateHold}, + tokens::Preservation, + OnIdle, OnInitialize, + }, + weights::{Weight, WeightMeter}, +}; +use frame_system::{EventRecord, Phase}; +use pallet_revive_fixtures::compile_module; +use pallet_revive_uapi::{ReturnErrorCode as RuntimeReturnCode, ReturnFlags}; +use pretty_assertions::{assert_eq, assert_ne}; +use sp_core::{Get, U256}; +use sp_io::hashing::blake2_256; +use sp_runtime::{testing::H256, traits::Zero, AccountId32, DispatchError, TokenError}; + +#[test] +fn transfer_with_dust_works() { + struct TestCase { + description: &'static str, + from_balance: BalanceWithDust, + to_balance: BalanceWithDust, + amount: BalanceWithDust, + expected_from_balance: BalanceWithDust, + expected_to_balance: BalanceWithDust, + total_issuance_diff: i64, + } + + let plank: u32 = ::NativeToEthRatio::get(); + + let test_cases = vec![ + TestCase { + description: "without dust", + from_balance: BalanceWithDust::new_unchecked::(100, 0), + to_balance: BalanceWithDust::new_unchecked::(0, 0), + amount: BalanceWithDust::new_unchecked::(1, 0), + expected_from_balance: BalanceWithDust::new_unchecked::(99, 0), + expected_to_balance: BalanceWithDust::new_unchecked::(1, 0), + total_issuance_diff: 0, + }, + TestCase { + description: "with dust", + from_balance: BalanceWithDust::new_unchecked::(100, 0), + to_balance: BalanceWithDust::new_unchecked::(0, 0), + amount: BalanceWithDust::new_unchecked::(1, 10), + expected_from_balance: BalanceWithDust::new_unchecked::(98, plank - 10), + expected_to_balance: BalanceWithDust::new_unchecked::(1, 10), + total_issuance_diff: 1, + }, + TestCase { + description: "just dust", + from_balance: BalanceWithDust::new_unchecked::(100, 0), + to_balance: BalanceWithDust::new_unchecked::(0, 0), + amount: BalanceWithDust::new_unchecked::(0, 10), + expected_from_balance: BalanceWithDust::new_unchecked::(99, plank - 10), + expected_to_balance: BalanceWithDust::new_unchecked::(0, 10), + total_issuance_diff: 1, + }, + TestCase { + description: "with existing dust", + from_balance: BalanceWithDust::new_unchecked::(100, 5), + to_balance: BalanceWithDust::new_unchecked::(0, plank - 5), + amount: BalanceWithDust::new_unchecked::(1, 10), + expected_from_balance: BalanceWithDust::new_unchecked::(98, plank - 5), + expected_to_balance: BalanceWithDust::new_unchecked::(2, 5), + total_issuance_diff: 0, + }, + TestCase { + description: "with enough existing dust", + from_balance: BalanceWithDust::new_unchecked::(100, 10), + to_balance: BalanceWithDust::new_unchecked::(0, plank - 10), + amount: BalanceWithDust::new_unchecked::(1, 10), + expected_from_balance: BalanceWithDust::new_unchecked::(99, 0), + expected_to_balance: BalanceWithDust::new_unchecked::(2, 0), + total_issuance_diff: -1, + }, + TestCase { + description: "receiver dust less than 1 plank", + from_balance: BalanceWithDust::new_unchecked::(100, plank / 10), + to_balance: BalanceWithDust::new_unchecked::(0, plank / 2), + amount: BalanceWithDust::new_unchecked::(1, plank / 10 * 3), + expected_from_balance: BalanceWithDust::new_unchecked::(98, plank / 10 * 8), + expected_to_balance: BalanceWithDust::new_unchecked::(1, plank / 10 * 8), + total_issuance_diff: 1, + }, + ]; + + for TestCase { + description, + from_balance, + to_balance, + amount, + expected_from_balance, + expected_to_balance, + total_issuance_diff, + } in test_cases.into_iter() + { + ExtBuilder::default().build().execute_with(|| { + set_balance_with_dust(&ALICE_ADDR, from_balance); + set_balance_with_dust(&BOB_ADDR, to_balance); + + let total_issuance = ::Currency::total_issuance(); + let evm_value = Pallet::::convert_native_to_evm(amount); + + let (value, dust) = amount.deconstruct(); + assert_eq!(Pallet::::has_dust(evm_value), !dust.is_zero()); + assert_eq!(Pallet::::has_balance(evm_value), !value.is_zero()); + + let result = + builder::bare_call(BOB_ADDR).evm_value(evm_value).build_and_unwrap_result(); + assert_eq!(result, Default::default(), "{description} tx failed"); + + assert_eq!( + Pallet::::evm_balance(&ALICE_ADDR), + Pallet::::convert_native_to_evm(expected_from_balance), + "{description}: invalid from balance" + ); + + assert_eq!( + Pallet::::evm_balance(&BOB_ADDR), + Pallet::::convert_native_to_evm(expected_to_balance), + "{description}: invalid to balance" + ); + + assert_eq!( + total_issuance as i64 - total_issuance_diff, + ::Currency::total_issuance() as i64, + "{description}: total issuance should match" + ); + }); + } +} + +#[test] +fn eth_call_transfer_with_dust_works() { + let (binary, _) = compile_module("dummy").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); + + let balance = + Pallet::::convert_native_to_evm(BalanceWithDust::new_unchecked::(100, 10)); + assert_ok!(builder::eth_call(addr).value(balance).build()); + + assert_eq!(Pallet::::evm_balance(&addr), balance); + }); +} + +#[test] +fn contract_call_transfer_with_dust_works() { + let (binary_caller, _code_hash_caller) = compile_module("call_with_value").unwrap(); + let (binary_callee, _code_hash_callee) = compile_module("dummy").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let Contract { addr: addr_caller, .. } = + builder::bare_instantiate(Code::Upload(binary_caller)) + .native_value(200) + .build_and_unwrap_contract(); + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); + + let balance = + Pallet::::convert_native_to_evm(BalanceWithDust::new_unchecked::(100, 10)); + assert_ok!(builder::call(addr_caller).data((balance, addr_callee).encode()).build()); + + assert_eq!(Pallet::::evm_balance(&addr_callee), balance); + }); +} + +#[test] +fn deposit_limit_enforced_on_plain_transfer() { + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let _ = ::Currency::set_balance(&BOB, 1_000_000); + + // sending balance to a new account should fail when the limit is lower than the ed + let result = builder::bare_call(CHARLIE_ADDR) + .native_value(1) + .storage_deposit_limit(190.into()) + .build(); + assert_err!(result.result, >::StorageDepositLimitExhausted); + assert_eq!(result.storage_deposit, StorageDeposit::Charge(0)); + assert_eq!(get_balance(&CHARLIE), 0); + + // works when the account is prefunded + let result = builder::bare_call(BOB_ADDR) + .native_value(1) + .storage_deposit_limit(0.into()) + .build(); + assert_ok!(result.result); + assert_eq!(result.storage_deposit, StorageDeposit::Charge(0)); + assert_eq!(get_balance(&BOB), 1_000_001); + + // also works allowing enough deposit + let result = builder::bare_call(CHARLIE_ADDR) + .native_value(1) + .storage_deposit_limit(200.into()) + .build(); + assert_ok!(result.result); + assert_eq!(result.storage_deposit, StorageDeposit::Charge(200)); + assert_eq!(get_balance(&CHARLIE), 201); + }); +} + +#[test] +fn instantiate_and_call_and_deposit_event() { + let (binary, code_hash) = compile_module("event_and_return_on_deploy").unwrap(); + + ExtBuilder::default().existential_deposit(1).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let min_balance = Contracts::min_balance(); + let value = 100; + + // We determine the storage deposit limit after uploading because it depends on ALICEs + // free balance which is changed by uploading a module. + assert_ok!(Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + binary, + deposit_limit::(), + )); + + // Drop previous events + initialize_block(2); + + // Check at the end to get hash on error easily + let Contract { addr, account_id } = builder::bare_instantiate(Code::Existing(code_hash)) + .native_value(value) + .build_and_unwrap_contract(); + assert!(AccountInfoOf::::contains_key(&addr)); + + let hold_balance = contract_base_deposit(&addr); + + assert_eq!( + System::events(), + vec![ + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::System(frame_system::Event::NewAccount { + account: account_id.clone() + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Endowed { + account: account_id.clone(), + free_balance: min_balance, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { + from: ALICE, + to: account_id.clone(), + amount: min_balance, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { + from: ALICE, + to: account_id.clone(), + amount: value, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Contracts(crate::Event::ContractEmitted { + contract: addr, + data: vec![1, 2, 3, 4], + topics: vec![H256::repeat_byte(42)], + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Contracts(crate::Event::Instantiated { + deployer: ALICE_ADDR, + contract: addr + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { + reason: ::RuntimeHoldReason::Contracts( + HoldReason::StorageDepositReserve, + ), + source: ALICE, + dest: account_id.clone(), + transferred: hold_balance, + }), + topics: vec![], + }, + ] + ); + }); +} + +#[test] +fn create1_address_from_extrinsic() { + let (binary, code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().existential_deposit(1).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + assert_ok!(Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + binary.clone(), + deposit_limit::(), + )); + + assert_eq!(System::account_nonce(&ALICE), 0); + System::inc_account_nonce(&ALICE); + + for nonce in 1..3 { + let Contract { addr, .. } = builder::bare_instantiate(Code::Existing(code_hash)) + .salt(None) + .build_and_unwrap_contract(); + assert!(AccountInfoOf::::contains_key(&addr)); + assert_eq!( + addr, + create1(&::AddressMapper::to_address(&ALICE), nonce - 1) + ); + } + assert_eq!(System::account_nonce(&ALICE), 3); + + for nonce in 3..6 { + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary.clone())) + .salt(None) + .build_and_unwrap_contract(); + assert!(AccountInfoOf::::contains_key(&addr)); + assert_eq!( + addr, + create1(&::AddressMapper::to_address(&ALICE), nonce - 1) + ); + } + assert_eq!(System::account_nonce(&ALICE), 6); + }); +} + +#[test] +fn deposit_event_max_value_limit() { + let (binary, _code_hash) = compile_module("event_size").unwrap(); + + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + // Create + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(30_000) + .build_and_unwrap_contract(); + + // Call contract with allowed storage value. + assert_ok!(builder::call(addr) + .gas_limit(GAS_LIMIT.set_ref_time(GAS_LIMIT.ref_time() * 2)) // we are copying a huge buffer, + .data(limits::PAYLOAD_BYTES.encode()) + .build()); + + // Call contract with too large a storage value. + assert_err_ignore_postinfo!( + builder::call(addr).data((limits::PAYLOAD_BYTES + 1).encode()).build(), + Error::::ValueTooLarge, + ); + }); +} + +// Fail out of fuel (ref_time weight) in the engine. +#[test] +fn run_out_of_fuel_engine() { + let (binary, _code_hash) = compile_module("run_out_of_gas").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(100 * min_balance) + .build_and_unwrap_contract(); + + // Call the contract with a fixed gas limit. It must run out of gas because it just + // loops forever. + assert_err_ignore_postinfo!( + builder::call(addr) + .gas_limit(Weight::from_parts(10_000_000_000, u64::MAX)) + .build(), + Error::::OutOfGas, + ); + }); +} + +// Fail out of fuel (ref_time weight) in the host. +#[test] +fn run_out_of_fuel_host() { + use crate::precompiles::Precompile; + use alloy_core::sol_types::SolInterface; + + let precompile_addr = H160(NoInfo::::MATCHER.base_address()); + let input = INoInfo::INoInfoCalls::consumeMaxGas(INoInfo::consumeMaxGasCall {}).abi_encode(); + + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); + let result = builder::bare_call(precompile_addr).data(input).build().result; + assert_err!(result, >::OutOfGas); + }); +} + +#[test] +fn gas_syncs_work() { + let (code, _code_hash) = compile_module("caller_is_origin_n").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let contract = builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + let result = builder::bare_call(contract.addr).data(0u32.encode()).build(); + assert_ok!(result.result); + let engine_consumed_noop = result.gas_consumed.ref_time(); + + let result = builder::bare_call(contract.addr).data(1u32.encode()).build(); + assert_ok!(result.result); + let gas_consumed_once = result.gas_consumed.ref_time(); + let host_consumed_once = ::WeightInfo::seal_caller_is_origin().ref_time(); + let engine_consumed_once = gas_consumed_once - host_consumed_once - engine_consumed_noop; + + let result = builder::bare_call(contract.addr).data(2u32.encode()).build(); + assert_ok!(result.result); + let gas_consumed_twice = result.gas_consumed.ref_time(); + let host_consumed_twice = host_consumed_once * 2; + let engine_consumed_twice = gas_consumed_twice - host_consumed_twice - engine_consumed_noop; + + // Second contract just repeats first contract's instructions twice. + // If runtime syncs gas with the engine properly, this should pass. + assert_eq!(engine_consumed_twice, engine_consumed_once * 2); + }); +} + +/// Check that contracts with the same account id have different trie ids. +/// Check the `Nonce` storage item for more information. +#[test] +fn instantiate_unique_trie_id() { + let (binary, code_hash) = compile_module("self_destruct").unwrap(); + + ExtBuilder::default().existential_deposit(500).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, deposit_limit::()) + .unwrap(); + + // Instantiate the contract and store its trie id for later comparison. + let Contract { addr, .. } = + builder::bare_instantiate(Code::Existing(code_hash)).build_and_unwrap_contract(); + let trie_id = get_contract(&addr).trie_id; + + // Try to instantiate it again without termination should yield an error. + assert_err_ignore_postinfo!( + builder::instantiate(code_hash).build(), + >::DuplicateContract, + ); + + // Terminate the contract. + assert_ok!(builder::call(addr).build()); + + // Re-Instantiate after termination. + assert_ok!(builder::instantiate(code_hash).build()); + + // Trie ids shouldn't match or we might have a collision + assert_ne!(trie_id, get_contract(&addr).trie_id); + }); +} + +#[test] +fn storage_work() { + let (code, _code_hash) = compile_module("storage").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let min_balance = Contracts::min_balance(); + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + builder::bare_call(addr).build_and_unwrap_result(); + }); +} + +#[test] +fn storage_max_value_limit() { + let (binary, _code_hash) = compile_module("storage_size").unwrap(); + + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + // Create + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(30_000) + .build_and_unwrap_contract(); + get_contract(&addr); + + // Call contract with allowed storage value. + assert_ok!(builder::call(addr) + .gas_limit(GAS_LIMIT.set_ref_time(GAS_LIMIT.ref_time() * 2)) // we are copying a huge buffer + .data(limits::PAYLOAD_BYTES.encode()) + .build()); + + // Call contract with too large a storage value. + assert_err_ignore_postinfo!( + builder::call(addr).data((limits::PAYLOAD_BYTES + 1).encode()).build(), + Error::::ValueTooLarge, + ); + }); +} + +#[test] +fn clear_storage_on_zero_value() { + let (code, _code_hash) = compile_module("clear_storage_on_zero_value").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let min_balance = Contracts::min_balance(); + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + builder::bare_call(addr).build_and_unwrap_result(); + }); +} + +#[test] +fn transient_storage_work() { + let (code, _code_hash) = compile_module("transient_storage").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let min_balance = Contracts::min_balance(); + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + builder::bare_call(addr).build_and_unwrap_result(); + }); +} + +#[test] +fn transient_storage_limit_in_call() { + let (binary_caller, _code_hash_caller) = + compile_module("create_transient_storage_and_call").unwrap(); + let (binary_callee, _code_hash_callee) = compile_module("set_transient_storage").unwrap(); + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create both contracts: Constructors do nothing. + let Contract { addr: addr_caller, .. } = + builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); + + // Call contracts with storage values within the limit. + // Caller and Callee contracts each set a transient storage value of size 100. + assert_ok!(builder::call(addr_caller) + .data((100u32, 100u32, &addr_callee).encode()) + .build(),); + + // Call a contract with a storage value that is too large. + // Limit exceeded in the caller contract. + assert_err_ignore_postinfo!( + builder::call(addr_caller) + .data((4u32 * 1024u32, 200u32, &addr_callee).encode()) + .build(), + >::OutOfTransientStorage, + ); + + // Call a contract with a storage value that is too large. + // Limit exceeded in the callee contract. + assert_err_ignore_postinfo!( + builder::call(addr_caller) + .data((50u32, 4 * 1024u32, &addr_callee).encode()) + .build(), + >::ContractTrapped + ); + }); +} + +#[test] +fn deploy_and_call_other_contract() { + let (caller_binary, _caller_code_hash) = compile_module("caller_contract").unwrap(); + let (callee_binary, callee_code_hash) = compile_module("return_with_data").unwrap(); + let code_load_weight = crate::vm::code_load_weight(callee_binary.len() as u32); + + ExtBuilder::default().existential_deposit(1).build().execute_with(|| { + let min_balance = Contracts::min_balance(); + + // Create + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let Contract { addr: caller_addr, account_id: caller_account } = + builder::bare_instantiate(Code::Upload(caller_binary)) + .native_value(100_000) + .build_and_unwrap_contract(); + + let callee_addr = create2( + &caller_addr, + &callee_binary, + &[0, 1, 34, 51, 68, 85, 102, 119], // hard coded in binary + &[0u8; 32], + ); + let callee_account = ::AddressMapper::to_account_id(&callee_addr); + + Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + callee_binary, + deposit_limit::(), + ) + .unwrap(); + + // Drop previous events + initialize_block(2); + + // Call BOB contract, which attempts to instantiate and call the callee contract and + // makes various assertions on the results from those calls. + assert_ok!(builder::call(caller_addr) + .data( + (callee_code_hash, code_load_weight.ref_time(), code_load_weight.proof_size()) + .encode() + ) + .build()); + + assert_eq!( + System::events(), + vec![ + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::System(frame_system::Event::NewAccount { + account: callee_account.clone() + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Endowed { + account: callee_account.clone(), + free_balance: min_balance, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { + from: ALICE, + to: callee_account.clone(), + amount: min_balance, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { + from: caller_account.clone(), + to: callee_account.clone(), + amount: 32768 // hardcoded in binary + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { + from: caller_account.clone(), + to: callee_account.clone(), + amount: 32768, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { + reason: ::RuntimeHoldReason::Contracts( + HoldReason::StorageDepositReserve, + ), + source: ALICE, + dest: callee_account.clone(), + transferred: 555, + }), + topics: vec![], + }, + ] + ); + }); +} + +#[test] +fn delegate_call() { + let (caller_binary, _caller_code_hash) = compile_module("delegate_call").unwrap(); + let (callee_binary, _callee_code_hash) = compile_module("delegate_call_lib").unwrap(); + + ExtBuilder::default().existential_deposit(500).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Instantiate the 'caller' + let Contract { addr: caller_addr, .. } = + builder::bare_instantiate(Code::Upload(caller_binary)) + .native_value(300_000) + .build_and_unwrap_contract(); + + // Instantiate the 'callee' + let Contract { addr: callee_addr, .. } = + builder::bare_instantiate(Code::Upload(callee_binary)) + .native_value(100_000) + .build_and_unwrap_contract(); + + assert_ok!(builder::call(caller_addr) + .value(1337) + .data((callee_addr, u64::MAX, u64::MAX).encode()) + .build()); + }); +} + +#[test] +fn delegate_call_non_existant_is_noop() { + let (caller_binary, _caller_code_hash) = compile_module("delegate_call_simple").unwrap(); + + ExtBuilder::default().existential_deposit(500).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Instantiate the 'caller' + let Contract { addr: caller_addr, .. } = + builder::bare_instantiate(Code::Upload(caller_binary)) + .native_value(300_000) + .build_and_unwrap_contract(); + + assert_ok!(builder::call(caller_addr) + .value(1337) + .data((BOB_ADDR, u64::MAX, u64::MAX).encode()) + .build()); + + assert_eq!(get_balance(&BOB_FALLBACK), 0); + }); +} + +#[test] +fn delegate_call_with_weight_limit() { + let (caller_binary, _caller_code_hash) = compile_module("delegate_call").unwrap(); + let (callee_binary, _callee_code_hash) = compile_module("delegate_call_lib").unwrap(); + + ExtBuilder::default().existential_deposit(500).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Instantiate the 'caller' + let Contract { addr: caller_addr, .. } = + builder::bare_instantiate(Code::Upload(caller_binary)) + .native_value(300_000) + .build_and_unwrap_contract(); + + // Instantiate the 'callee' + let Contract { addr: callee_addr, .. } = + builder::bare_instantiate(Code::Upload(callee_binary)) + .native_value(100_000) + .build_and_unwrap_contract(); + + // fails, not enough weight + assert_err!( + builder::bare_call(caller_addr) + .native_value(1337) + .data((callee_addr, 100u64, 100u64).encode()) + .build() + .result, + Error::::ContractTrapped, + ); + + assert_ok!(builder::call(caller_addr) + .value(1337) + .data((callee_addr, 500_000_000u64, 100_000u64).encode()) + .build()); + }); +} + +#[test] +fn delegate_call_with_deposit_limit() { + let (caller_binary, _caller_code_hash) = compile_module("delegate_call_deposit_limit").unwrap(); + let (callee_binary, _callee_code_hash) = compile_module("delegate_call_lib").unwrap(); + + ExtBuilder::default().existential_deposit(500).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Instantiate the 'caller' + let Contract { addr: caller_addr, .. } = + builder::bare_instantiate(Code::Upload(caller_binary)) + .native_value(300_000) + .build_and_unwrap_contract(); + + // Instantiate the 'callee' + let Contract { addr: callee_addr, .. } = + builder::bare_instantiate(Code::Upload(callee_binary)) + .native_value(100_000) + .build_and_unwrap_contract(); + + // Delegate call will write 1 storage and deposit of 2 (1 item) + 32 (bytes) is required. + // + 32 + 16 for blake2_128concat + // Fails, not enough deposit + let ret = builder::bare_call(caller_addr) + .native_value(1337) + .data((callee_addr, 81u64).encode()) + .build_and_unwrap_result(); + assert_return_code!(ret, RuntimeReturnCode::OutOfResources); + + assert_ok!(builder::call(caller_addr) + .value(1337) + .data((callee_addr, 82u64).encode()) + .build()); + }); +} + +#[test] +fn transfer_expendable_cannot_kill_account() { + let (binary, _code_hash) = compile_module("dummy").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Instantiate the BOB contract. + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(1_000) + .build_and_unwrap_contract(); + + // Check that the BOB contract has been instantiated. + get_contract(&addr); + + let account = ::AddressMapper::to_account_id(&addr); + let total_balance = ::Currency::total_balance(&account); + + assert_eq!( + get_balance_on_hold(&HoldReason::StorageDepositReserve.into(), &account), + contract_base_deposit(&addr) + ); + + // Some or the total balance is held, so it can't be transferred. + assert_err!( + <::Currency as Mutate>::transfer( + &account, + &ALICE, + total_balance, + Preservation::Expendable, + ), + TokenError::FundsUnavailable, + ); + + assert_eq!(::Currency::total_balance(&account), total_balance); + }); +} + +#[test] +fn cannot_self_destruct_through_draining() { + let (binary, _code_hash) = compile_module("drain").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let value = 1_000; + let min_balance = Contracts::min_balance(); + + // Instantiate the BOB contract. + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(value) + .build_and_unwrap_contract(); + let account = ::AddressMapper::to_account_id(&addr); + + // Check that the BOB contract has been instantiated. + get_contract(&addr); + + // Call BOB which makes it send all funds to the zero address + // The contract code asserts that the transfer fails with the correct error code + assert_ok!(builder::call(addr).build()); + + // Make sure the account wasn't remove by sending all free balance away. + assert_eq!( + ::Currency::total_balance(&account), + value + contract_base_deposit(&addr) + min_balance, + ); + }); +} + +#[test] +fn cannot_self_destruct_through_storage_refund_after_price_change() { + let (binary, _code_hash) = compile_module("store_call").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let min_balance = Contracts::min_balance(); + + // Instantiate the BOB contract. + let contract = builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); + let info_deposit = contract_base_deposit(&contract.addr); + + // Check that the contract has been instantiated and has the minimum balance + assert_eq!(get_contract(&contract.addr).total_deposit(), info_deposit); + assert_eq!(get_contract(&contract.addr).extra_deposit(), 0); + assert_eq!( + ::Currency::total_balance(&contract.account_id), + info_deposit + min_balance + ); + + // Create 100 (16 + 32 bytes for key for blake128 concat) bytes of storage with a + // price of per byte and a single storage item of price 2 + assert_ok!(builder::call(contract.addr).data(100u32.to_le_bytes().to_vec()).build()); + assert_eq!(get_contract(&contract.addr).total_deposit(), info_deposit + 100 + 16 + 32 + 2); + + // Increase the byte price and trigger a refund. This should not have any influence + // because the removal is pro rata and exactly those 100 bytes should have been + // removed as we didn't delete the key. + DEPOSIT_PER_BYTE.with(|c| *c.borrow_mut() = 500); + assert_ok!(builder::call(contract.addr).data(0u32.to_le_bytes().to_vec()).build()); + + // Make sure the account wasn't removed by the refund + assert_eq!( + ::Currency::total_balance(&contract.account_id), + get_contract(&contract.addr).total_deposit() + min_balance, + ); + // + 1 because due to fixed point arithmetic we can sometimes refund + // one unit to little + assert_eq!(get_contract(&contract.addr).extra_deposit(), 16 + 32 + 2 + 1); + }); +} + +#[test] +fn cannot_self_destruct_while_live() { + let (binary, _code_hash) = compile_module("self_destruct").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Instantiate the BOB contract. + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(100_000) + .build_and_unwrap_contract(); + + // Check that the BOB contract has been instantiated. + get_contract(&addr); + + // Call BOB with input data, forcing it make a recursive call to itself to + // self-destruct, resulting in a trap. + assert_err_ignore_postinfo!( + builder::call(addr).data(vec![0]).build(), + Error::::ContractTrapped, + ); + + // Check that BOB is still there. + get_contract(&addr); + }); +} + +#[test] +fn self_destruct_works() { + let (binary, code_hash) = compile_module("self_destruct").unwrap(); + ExtBuilder::default().existential_deposit(1_000).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let _ = ::Currency::set_balance(&DJANGO_FALLBACK, 1_000_000); + let min_balance = Contracts::min_balance(); + + // Instantiate the BOB contract. + let contract = builder::bare_instantiate(Code::Upload(binary)) + .native_value(100_000) + .build_and_unwrap_contract(); + + let hold_balance = contract_base_deposit(&contract.addr); + + // Check that the BOB contract has been instantiated. + let _ = get_contract(&contract.addr); + + // Drop all previous events + initialize_block(2); + + // Call BOB without input data which triggers termination. + assert_matches!(builder::call(contract.addr).build(), Ok(_)); + + // Check that code is still there but refcount dropped to zero. + assert_refcount!(&code_hash, 0); + + // Check that account is gone + assert!(get_contract_checked(&contract.addr).is_none()); + assert_eq!(::Currency::total_balance(&contract.account_id), 0); + + // Check that the beneficiary (django) got remaining balance. + assert_eq!( + ::Currency::free_balance(DJANGO_FALLBACK), + 1_000_000 + 100_000 + min_balance + ); + + // Check that the Alice is missing Django's benefit. Within ALICE's total balance + // there's also the code upload deposit held. + assert_eq!( + ::Currency::total_balance(&ALICE), + 1_000_000 - (100_000 + min_balance) + ); + + pretty_assertions::assert_eq!( + System::events(), + vec![ + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::TransferOnHold { + reason: ::RuntimeHoldReason::Contracts( + HoldReason::StorageDepositReserve, + ), + source: contract.account_id.clone(), + dest: ALICE, + amount: hold_balance, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::System(frame_system::Event::KilledAccount { + account: contract.account_id.clone() + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { + from: contract.account_id.clone(), + to: DJANGO_FALLBACK, + amount: 100_000 + min_balance, + }), + topics: vec![], + }, + ], + ); + }); +} + +// This tests that one contract cannot prevent another from self-destructing by sending it +// additional funds after it has been drained. +#[test] +fn destroy_contract_and_transfer_funds() { + let (callee_binary, callee_code_hash) = compile_module("self_destruct").unwrap(); + let (caller_binary, _caller_code_hash) = compile_module("destroy_and_transfer").unwrap(); + + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + // Create code hash for bob to instantiate + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + callee_binary.clone(), + deposit_limit::(), + ) + .unwrap(); + + // This deploys the BOB contract, which in turn deploys the CHARLIE contract during + // construction. + let Contract { addr: addr_bob, .. } = + builder::bare_instantiate(Code::Upload(caller_binary)) + .native_value(200_000) + .data(callee_code_hash.as_ref().to_vec()) + .build_and_unwrap_contract(); + + // Check that the CHARLIE contract has been instantiated. + let salt = [47; 32]; // hard coded in fixture. + let addr_charlie = create2(&addr_bob, &callee_binary, &[], &salt); + get_contract(&addr_charlie); + + // Call BOB, which calls CHARLIE, forcing CHARLIE to self-destruct. + assert_ok!(builder::call(addr_bob).data(addr_charlie.encode()).build()); + + // Check that CHARLIE has moved on to the great beyond (ie. died). + assert!(get_contract_checked(&addr_charlie).is_none()); + }); +} + +#[test] +fn cannot_self_destruct_in_constructor() { + let (binary, _) = compile_module("self_destructing_constructor").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Fail to instantiate the BOB because the constructor calls seal_terminate. + assert_err_ignore_postinfo!( + builder::instantiate_with_code(binary).value(100_000).build(), + Error::::TerminatedInConstructor, + ); + }); +} + +#[test] +fn crypto_hash_keccak_256() { + let (binary, _code_hash) = compile_module("crypto_hash_keccak_256").unwrap(); + + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Instantiate the CRYPTO_HASH_KECCAK_256 contract. + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(100_000) + .build_and_unwrap_contract(); + // Perform the call. + let input = b"_DEAD_BEEF"; + use sp_io::hashing::*; + // Wraps a hash function into a more dynamic form usable for testing. + macro_rules! dyn_hash_fn { + ($name:ident) => { + Box::new(|input| $name(input).as_ref().to_vec().into_boxed_slice()) + }; + } + // The hash function and its associated output byte lengths. + let hash_fn: Box Box<[u8]>> = dyn_hash_fn!(keccak_256); + let expected_size: usize = 32; + // Test the hash function for the input: "_DEAD_BEEF" + let result = builder::bare_call(addr).data(input.to_vec()).build_and_unwrap_result(); + assert!(!result.did_revert()); + let expected = hash_fn(input.as_ref()); + assert_eq!(&result.data[..expected_size], &*expected); + }) +} + +#[test] +fn transfer_return_code() { + let (binary, _code_hash) = compile_module("transfer_return_code").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); + + let contract = builder::bare_instantiate(Code::Upload(binary)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + // Contract has only the minimal balance so any transfer will fail. + ::Currency::set_balance(&contract.account_id, min_balance); + let result = builder::bare_call(contract.addr).build_and_unwrap_result(); + assert_return_code!(result, RuntimeReturnCode::TransferFailed); + }); +} + +#[test] +fn call_return_code() { + let (caller_code, _caller_hash) = compile_module("call_return_code").unwrap(); + let (callee_code, _callee_hash) = compile_module("ok_trap_revert").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); + let _ = ::Currency::set_balance(&CHARLIE, 1000 * min_balance); + + let bob = builder::bare_instantiate(Code::Upload(caller_code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + // BOB cannot pay the ed which is needed to pull DJANGO into existence + // this does trap the caller instead of returning an error code + // reasoning is that this error state does not exist on eth where + // ed does not exist. We hide this fact from the contract. + let result = builder::bare_call(bob.addr) + .data((DJANGO_ADDR, u256_bytes(1)).encode()) + .origin(RuntimeOrigin::signed(BOB)) + .build(); + assert_err!(result.result, >::StorageDepositNotEnoughFunds); + + // Contract calls into Django which is no valid contract + // This will be a balance transfer into a new account + // with more than the contract has which will make the transfer fail + let value = Pallet::::convert_native_to_evm(min_balance * 200); + let result = builder::bare_call(bob.addr) + .data( + AsRef::<[u8]>::as_ref(&DJANGO_ADDR) + .iter() + .chain(&value.to_little_endian()) + .cloned() + .collect(), + ) + .build_and_unwrap_result(); + assert_return_code!(result, RuntimeReturnCode::TransferFailed); + + // Sending below the minimum balance should result in success. + // The ED is charged from the call origin. + let alice_before = get_balance(&ALICE_FALLBACK); + assert_eq!(get_balance(&DJANGO_FALLBACK), 0); + + let value = Pallet::::convert_native_to_evm(1u64); + let result = builder::bare_call(bob.addr) + .data( + AsRef::<[u8]>::as_ref(&DJANGO_ADDR) + .iter() + .chain(&value.to_little_endian()) + .cloned() + .collect(), + ) + .build_and_unwrap_result(); + assert_return_code!(result, RuntimeReturnCode::Success); + assert_eq!(get_balance(&DJANGO_FALLBACK), min_balance + 1); + assert_eq!(get_balance(&ALICE_FALLBACK), alice_before - min_balance); + + let django = builder::bare_instantiate(Code::Upload(callee_code)) + .origin(RuntimeOrigin::signed(CHARLIE)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + // Sending more than the contract has will make the transfer fail. + let value = Pallet::::convert_native_to_evm(min_balance * 300); + let result = builder::bare_call(bob.addr) + .data( + AsRef::<[u8]>::as_ref(&django.addr) + .iter() + .chain(&value.to_little_endian()) + .chain(&0u32.to_le_bytes()) + .cloned() + .collect(), + ) + .build_and_unwrap_result(); + assert_return_code!(result, RuntimeReturnCode::TransferFailed); + + // Contract has enough balance but callee reverts because "1" is passed. + ::Currency::set_balance(&bob.account_id, min_balance + 1000); + let value = Pallet::::convert_native_to_evm(5u64); + let result = builder::bare_call(bob.addr) + .data( + AsRef::<[u8]>::as_ref(&django.addr) + .iter() + .chain(&value.to_little_endian()) + .chain(&1u32.to_le_bytes()) + .cloned() + .collect(), + ) + .build_and_unwrap_result(); + assert_return_code!(result, RuntimeReturnCode::CalleeReverted); + + // Contract has enough balance but callee traps because "2" is passed. + let result = builder::bare_call(bob.addr) + .data( + AsRef::<[u8]>::as_ref(&django.addr) + .iter() + .chain(&value.to_little_endian()) + .chain(&2u32.to_le_bytes()) + .cloned() + .collect(), + ) + .build_and_unwrap_result(); + assert_return_code!(result, RuntimeReturnCode::CalleeTrapped); + }); +} + +#[test] +fn instantiate_return_code() { + let (caller_code, _caller_hash) = compile_module("instantiate_return_code").unwrap(); + let (callee_code, callee_hash) = compile_module("ok_trap_revert").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); + let _ = ::Currency::set_balance(&CHARLIE, 1000 * min_balance); + let callee_hash = callee_hash.as_ref().to_vec(); + + assert_ok!(builder::instantiate_with_code(callee_code).value(min_balance * 100).build()); + + let contract = builder::bare_instantiate(Code::Upload(caller_code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + // bob cannot pay the ED to create the contract as he has no money + // this traps the caller rather than returning an error + let result = builder::bare_call(contract.addr) + .data(callee_hash.iter().chain(&0u32.to_le_bytes()).cloned().collect()) + .origin(RuntimeOrigin::signed(BOB)) + .build(); + assert_err!(result.result, >::StorageDepositNotEnoughFunds); + + // Contract has only the minimal balance so any transfer will fail. + ::Currency::set_balance(&contract.account_id, min_balance); + let result = builder::bare_call(contract.addr) + .data(callee_hash.iter().chain(&0u32.to_le_bytes()).cloned().collect()) + .build_and_unwrap_result(); + assert_return_code!(result, RuntimeReturnCode::TransferFailed); + + // Contract has enough balance but the passed code hash is invalid + ::Currency::set_balance(&contract.account_id, min_balance + 10_000); + let result = builder::bare_call(contract.addr).data(vec![0; 36]).build(); + assert_err!(result.result, >::CodeNotFound); + + // Contract has enough balance but callee reverts because "1" is passed. + let result = builder::bare_call(contract.addr) + .data(callee_hash.iter().chain(&1u32.to_le_bytes()).cloned().collect()) + .build_and_unwrap_result(); + assert_return_code!(result, RuntimeReturnCode::CalleeReverted); + + // Contract has enough balance but callee traps because "2" is passed. + let result = builder::bare_call(contract.addr) + .data(callee_hash.iter().chain(&2u32.to_le_bytes()).cloned().collect()) + .build_and_unwrap_result(); + assert_return_code!(result, RuntimeReturnCode::CalleeTrapped); + + // Contract instantiation succeeds + let result = builder::bare_call(contract.addr) + .data(callee_hash.iter().chain(&0u32.to_le_bytes()).cloned().collect()) + .build_and_unwrap_result(); + assert_return_code!(result, 0); + + // Contract instantiation fails because the same salt is being used again. + let result = builder::bare_call(contract.addr) + .data(callee_hash.iter().chain(&0u32.to_le_bytes()).cloned().collect()) + .build_and_unwrap_result(); + assert_return_code!(result, RuntimeReturnCode::DuplicateContractAddress); + }); +} + +#[test] +fn lazy_removal_works() { + let (code, _hash) = compile_module("self_destruct").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); + + let contract = builder::bare_instantiate(Code::Upload(code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + let info = get_contract(&contract.addr); + let trie = &info.child_trie_info(); + + // Put value into the contracts child trie + child::put(trie, &[99], &42); + + // Terminate the contract + assert_ok!(builder::call(contract.addr).build()); + + // Contract info should be gone + assert!(!>::contains_key(&contract.addr)); + + // But value should be still there as the lazy removal did not run, yet. + assert_matches!(child::get(trie, &[99]), Some(42)); + + // Run the lazy removal + Contracts::on_idle(System::block_number(), Weight::MAX); + + // Value should be gone now + assert_matches!(child::get::(trie, &[99]), None); + }); +} + +#[test] +fn lazy_batch_removal_works() { + let (code, _hash) = compile_module("self_destruct").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); + let mut tries: Vec = vec![]; + + for i in 0..3u8 { + let contract = builder::bare_instantiate(Code::Upload(code.clone())) + .native_value(min_balance * 100) + .salt(Some([i; 32])) + .build_and_unwrap_contract(); + + let info = get_contract(&contract.addr); + let trie = &info.child_trie_info(); + + // Put value into the contracts child trie + child::put(trie, &[99], &42); + + // Terminate the contract. Contract info should be gone, but value should be still + // there as the lazy removal did not run, yet. + assert_ok!(builder::call(contract.addr).build()); + + assert!(!>::contains_key(&contract.addr)); + assert_matches!(child::get(trie, &[99]), Some(42)); + + tries.push(trie.clone()) + } + + // Run single lazy removal + Contracts::on_idle(System::block_number(), Weight::MAX); + + // The single lazy removal should have removed all queued tries + for trie in tries.iter() { + assert_matches!(child::get::(trie, &[99]), None); + } + }); +} + +#[test] +fn ref_time_left_api_works() { + let (code, _) = compile_module("ref_time_left").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create fixture: Constructor calls ref_time_left twice and asserts it to decrease + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // Call the contract: It echoes back the ref_time returned by the ref_time_left API. + let received = builder::bare_call(addr).build_and_unwrap_result(); + assert_eq!(received.flags, ReturnFlags::empty()); + + let returned_value = u64::from_le_bytes(received.data[..8].try_into().unwrap()); + assert!(returned_value > 0); + assert!(returned_value < GAS_LIMIT.ref_time()); + }); +} + +#[test] +fn lazy_removal_partial_remove_works() { + let (code, _hash) = compile_module("self_destruct").unwrap(); + + // We create a contract with some extra keys above the weight limit + let extra_keys = 7u32; + let mut meter = WeightMeter::with_limit(Weight::from_parts(5_000_000_000, 100 * 1024)); + let (weight_per_key, max_keys) = ContractInfo::::deletion_budget(&meter); + let vals: Vec<_> = (0..max_keys + extra_keys) + .map(|i| (blake2_256(&i.encode()), (i as u32), (i as u32).encode())) + .collect(); + + let mut ext = ExtBuilder::default().existential_deposit(50).build(); + + let trie = ext.execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); + + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + let info = get_contract(&addr); + + // Put value into the contracts child trie + for val in &vals { + info.write(&Key::Fix(val.0), Some(val.2.clone()), None, false).unwrap(); + } + AccountInfo::::insert_contract(&addr, info.clone()); + + // Terminate the contract + assert_ok!(builder::call(addr).build()); + + // Contract info should be gone + assert!(!>::contains_key(&addr)); + + let trie = info.child_trie_info(); + + // But value should be still there as the lazy removal did not run, yet. + for val in &vals { + assert_eq!(child::get::(&trie, &blake2_256(&val.0)), Some(val.1)); + } + + trie.clone() + }); + + // The lazy removal limit only applies to the backend but not to the overlay. + // This commits all keys from the overlay to the backend. + ext.commit_all().unwrap(); + + ext.execute_with(|| { + // Run the lazy removal + ContractInfo::::process_deletion_queue_batch(&mut meter); + + // Weight should be exhausted because we could not even delete all keys + assert!(!meter.can_consume(weight_per_key)); + + let mut num_deleted = 0u32; + let mut num_remaining = 0u32; + + for val in &vals { + match child::get::(&trie, &blake2_256(&val.0)) { + None => num_deleted += 1, + Some(x) if x == val.1 => num_remaining += 1, + Some(_) => panic!("Unexpected value in contract storage"), + } + } + + // All but one key is removed + assert_eq!(num_deleted + num_remaining, vals.len() as u32); + assert_eq!(num_deleted, max_keys); + assert_eq!(num_remaining, extra_keys); + }); +} + +#[test] +fn lazy_removal_does_no_run_on_low_remaining_weight() { + let (code, _hash) = compile_module("self_destruct").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); + + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + let info = get_contract(&addr); + let trie = &info.child_trie_info(); + + // Put value into the contracts child trie + child::put(trie, &[99], &42); + + // Terminate the contract + assert_ok!(builder::call(addr).build()); + + // Contract info should be gone + assert!(!>::contains_key(&addr)); + + // But value should be still there as the lazy removal did not run, yet. + assert_matches!(child::get(trie, &[99]), Some(42)); + + // Assign a remaining weight which is too low for a successful deletion of the contract + let low_remaining_weight = + <::WeightInfo as WeightInfo>::on_process_deletion_queue_batch(); + + // Run the lazy removal + Contracts::on_idle(System::block_number(), low_remaining_weight); + + // Value should still be there, since remaining weight was too low for removal + assert_matches!(child::get::(trie, &[99]), Some(42)); + + // Run the lazy removal while deletion_queue is not full + Contracts::on_initialize(System::block_number()); + + // Value should still be there, since deletion_queue was not full + assert_matches!(child::get::(trie, &[99]), Some(42)); + + // Run on_idle with max remaining weight, this should remove the value + Contracts::on_idle(System::block_number(), Weight::MAX); + + // Value should be gone + assert_matches!(child::get::(trie, &[99]), None); + }); +} + +#[test] +fn lazy_removal_does_not_use_all_weight() { + let (code, _hash) = compile_module("self_destruct").unwrap(); + + let mut meter = WeightMeter::with_limit(Weight::from_parts(5_000_000_000, 100 * 1024)); + let mut ext = ExtBuilder::default().existential_deposit(50).build(); + + let (trie, vals, weight_per_key) = ext.execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); + + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + let info = get_contract(&addr); + let (weight_per_key, max_keys) = ContractInfo::::deletion_budget(&meter); + assert!(max_keys > 0); + + // We create a contract with one less storage item than we can remove within the limit + let vals: Vec<_> = (0..max_keys - 1) + .map(|i| (blake2_256(&i.encode()), (i as u32), (i as u32).encode())) + .collect(); + + // Put value into the contracts child trie + for val in &vals { + info.write(&Key::Fix(val.0), Some(val.2.clone()), None, false).unwrap(); + } + AccountInfo::::insert_contract(&addr, info.clone()); + + // Terminate the contract + assert_ok!(builder::call(addr).build()); + + // Contract info should be gone + assert!(!>::contains_key(&addr)); + + let trie = info.child_trie_info(); + + // But value should be still there as the lazy removal did not run, yet. + for val in &vals { + assert_eq!(child::get::(&trie, &blake2_256(&val.0)), Some(val.1)); + } + + (trie, vals, weight_per_key) + }); + + // The lazy removal limit only applies to the backend but not to the overlay. + // This commits all keys from the overlay to the backend. + ext.commit_all().unwrap(); + + ext.execute_with(|| { + // Run the lazy removal + ContractInfo::::process_deletion_queue_batch(&mut meter); + let base_weight = + <::WeightInfo as WeightInfo>::on_process_deletion_queue_batch(); + assert_eq!(meter.consumed(), weight_per_key.mul(vals.len() as _) + base_weight); + + // All the keys are removed + for val in vals { + assert_eq!(child::get::(&trie, &blake2_256(&val.0)), None); + } + }); +} + +#[test] +fn deletion_queue_ring_buffer_overflow() { + let (code, _hash) = compile_module("self_destruct").unwrap(); + let mut ext = ExtBuilder::default().existential_deposit(50).build(); + + // setup the deletion queue with custom counters + ext.execute_with(|| { + let queue = DeletionQueueManager::from_test_values(u32::MAX - 1, u32::MAX - 1); + >::set(queue); + }); + + // commit the changes to the storage + ext.commit_all().unwrap(); + + ext.execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); + let mut tries: Vec = vec![]; + + // add 3 contracts to the deletion queue + for i in 0..3u8 { + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code.clone())) + .native_value(min_balance * 100) + .salt(Some([i; 32])) + .build_and_unwrap_contract(); + + let info = get_contract(&addr); + let trie = &info.child_trie_info(); + + // Put value into the contracts child trie + child::put(trie, &[99], &42); + + // Terminate the contract. Contract info should be gone, but value should be still + // there as the lazy removal did not run, yet. + assert_ok!(builder::call(addr).build()); + + assert!(!>::contains_key(&addr)); + assert_matches!(child::get(trie, &[99]), Some(42)); + + tries.push(trie.clone()) + } + + // Run single lazy removal + Contracts::on_idle(System::block_number(), Weight::MAX); + + // The single lazy removal should have removed all queued tries + for trie in tries.iter() { + assert_matches!(child::get::(trie, &[99]), None); + } + + // insert and delete counter values should go from u32::MAX - 1 to 1 + assert_eq!(>::get().as_test_tuple(), (1, 1)); + }) +} +#[test] +fn refcounter() { + let (binary, code_hash) = compile_module("self_destruct").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let min_balance = Contracts::min_balance(); + + // Create two contracts with the same code and check that they do in fact share it. + let Contract { addr: addr0, .. } = builder::bare_instantiate(Code::Upload(binary.clone())) + .native_value(min_balance * 100) + .salt(Some([0; 32])) + .build_and_unwrap_contract(); + let Contract { addr: addr1, .. } = builder::bare_instantiate(Code::Upload(binary.clone())) + .native_value(min_balance * 100) + .salt(Some([1; 32])) + .build_and_unwrap_contract(); + assert_refcount!(code_hash, 2); + + // Sharing should also work with the usual instantiate call + let Contract { addr: addr2, .. } = builder::bare_instantiate(Code::Existing(code_hash)) + .native_value(min_balance * 100) + .salt(Some([2; 32])) + .build_and_unwrap_contract(); + assert_refcount!(code_hash, 3); + + // Terminating one contract should decrement the refcount + assert_ok!(builder::call(addr0).build()); + assert_refcount!(code_hash, 2); + + // remove another one + assert_ok!(builder::call(addr1).build()); + assert_refcount!(code_hash, 1); + + // Pristine code should still be there + PristineCode::::get(code_hash).unwrap(); + + // remove the last contract + assert_ok!(builder::call(addr2).build()); + assert_refcount!(code_hash, 0); + + // refcount is `0` but code should still exists because it needs to be removed manually + assert!(crate::PristineCode::::contains_key(&code_hash)); + }); +} + +#[test] +fn gas_estimation_for_subcalls() { + let (caller_code, _caller_hash) = compile_module("call_with_limit").unwrap(); + let (dummy_code, _callee_hash) = compile_module("dummy").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 2_000 * min_balance); + + let Contract { addr: addr_caller, .. } = + builder::bare_instantiate(Code::Upload(caller_code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + let Contract { addr: addr_dummy, .. } = builder::bare_instantiate(Code::Upload(dummy_code)) + .native_value(min_balance * 100) + .build_and_unwrap_contract(); + + // Run the test for all of those weight limits for the subcall + let weights = [ + Weight::MAX, + GAS_LIMIT, + GAS_LIMIT * 2, + GAS_LIMIT / 5, + Weight::from_parts(u64::MAX, GAS_LIMIT.proof_size()), + Weight::from_parts(GAS_LIMIT.ref_time(), u64::MAX), + ]; + + let (sub_addr, sub_input) = (addr_dummy.as_ref(), vec![]); + + for weight in weights { + let input: Vec = sub_addr + .iter() + .cloned() + .chain(weight.ref_time().to_le_bytes()) + .chain(weight.proof_size().to_le_bytes()) + .chain(sub_input.clone()) + .collect(); + + // Call in order to determine the gas that is required for this call + let result_orig = builder::bare_call(addr_caller).data(input.clone()).build(); + assert_ok!(&result_orig.result); + assert_eq!(result_orig.gas_required, result_orig.gas_consumed); + + // Make the same call using the estimated gas. Should succeed. + let result = builder::bare_call(addr_caller) + .gas_limit(result_orig.gas_required) + .storage_deposit_limit(result_orig.storage_deposit.charge_or_zero().into()) + .data(input.clone()) + .build(); + assert_ok!(&result.result); + + // Check that it fails with too little ref_time + let result = builder::bare_call(addr_caller) + .gas_limit(result_orig.gas_required.sub_ref_time(1)) + .storage_deposit_limit(result_orig.storage_deposit.charge_or_zero().into()) + .data(input.clone()) + .build(); + assert_err!(result.result, >::OutOfGas); + + // Check that it fails with too little proof_size + let result = builder::bare_call(addr_caller) + .gas_limit(result_orig.gas_required.sub_proof_size(1)) + .storage_deposit_limit(result_orig.storage_deposit.charge_or_zero().into()) + .data(input.clone()) + .build(); + assert_err!(result.result, >::OutOfGas); + } + }); +} + +#[test] +fn call_runtime_reentrancy_guarded() { + use crate::precompiles::Precompile; + use alloy_core::sol_types::SolInterface; + use precompiles::{INoInfo, NoInfo}; + + let precompile_addr = H160(NoInfo::::MATCHER.base_address()); + + let (callee_code, _callee_hash) = compile_module("dummy").unwrap(); + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let min_balance = Contracts::min_balance(); + let _ = ::Currency::set_balance(&ALICE, 1000 * min_balance); + let _ = ::Currency::set_balance(&CHARLIE, 1000 * min_balance); + + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(callee_code)) + .native_value(min_balance * 100) + .salt(Some([1; 32])) + .build_and_unwrap_contract(); + + // Call pallet_revive call() dispatchable + let call = RuntimeCall::Contracts(crate::Call::call { + dest: addr_callee, + value: 0, + gas_limit: GAS_LIMIT / 3, + storage_deposit_limit: deposit_limit::(), + data: vec![], + }) + .encode(); + + // Call runtime to re-enter back to contracts engine by + // calling dummy contract + let result = builder::bare_call(precompile_addr) + .data( + INoInfo::INoInfoCalls::callRuntime(INoInfo::callRuntimeCall { call: call.into() }) + .abi_encode(), + ) + .build(); + // Call to runtime should fail because of the re-entrancy guard + assert_err!(result.result, >::ReenteredPallet); + }); +} + +#[test] +fn sr25519_verify() { + let (binary, _code_hash) = compile_module("sr25519_verify").unwrap(); + + ExtBuilder::default().existential_deposit(50).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Instantiate the sr25519_verify contract. + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(100_000) + .build_and_unwrap_contract(); + + let call_with = |message: &[u8; 11]| { + // Alice's signature for "hello world" + #[rustfmt::skip] + let signature: [u8; 64] = [ + 184, 49, 74, 238, 78, 165, 102, 252, 22, 92, 156, 176, 124, 118, 168, 116, 247, + 99, 0, 94, 2, 45, 9, 170, 73, 222, 182, 74, 60, 32, 75, 64, 98, 174, 69, 55, 83, + 85, 180, 98, 208, 75, 231, 57, 205, 62, 4, 105, 26, 136, 172, 17, 123, 99, 90, 255, + 228, 54, 115, 63, 30, 207, 205, 131, + ]; + + // Alice's public key + #[rustfmt::skip] + let public_key: [u8; 32] = [ + 212, 53, 147, 199, 21, 253, 211, 28, 97, 20, 26, 189, 4, 169, 159, 214, 130, 44, + 133, 88, 133, 76, 205, 227, 154, 86, 132, 231, 165, 109, 162, 125, + ]; + + let mut params = vec![]; + params.extend_from_slice(&signature); + params.extend_from_slice(&public_key); + params.extend_from_slice(message); + + builder::bare_call(addr).data(params).build_and_unwrap_result() + }; + + // verification should succeed for "hello world" + assert_return_code!(call_with(&b"hello world"), RuntimeReturnCode::Success); + + // verification should fail for other messages + assert_return_code!(call_with(&b"hello worlD"), RuntimeReturnCode::Sr25519VerifyFailed); + }); +} + +#[test] +fn upload_code_works() { + let (binary, code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Drop previous events + initialize_block(2); + + assert!(!PristineCode::::contains_key(&code_hash)); + assert_ok!(Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, 1_000,)); + // Ensure the contract was stored and get expected deposit amount to be reserved. + expected_deposit(ensure_stored(code_hash)); + }); +} + +#[test] +fn upload_code_limit_too_low() { + let (binary, _code_hash) = compile_module("dummy").unwrap(); + let deposit_expected = expected_deposit(binary.len()); + let deposit_insufficient = deposit_expected.saturating_sub(1); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Drop previous events + initialize_block(2); + + assert_noop!( + Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, deposit_insufficient,), + >::StorageDepositLimitExhausted, + ); + + assert_eq!(System::events(), vec![]); + }); +} + +#[test] +fn upload_code_not_enough_balance() { + let (binary, _code_hash) = compile_module("dummy").unwrap(); + let deposit_expected = expected_deposit(binary.len()); + let deposit_insufficient = deposit_expected.saturating_sub(1); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, deposit_insufficient); + + // Drop previous events + initialize_block(2); + + assert_noop!( + Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, 1_000,), + >::StorageDepositNotEnoughFunds, + ); + + assert_eq!(System::events(), vec![]); + }); +} + +#[test] +fn remove_code_works() { + let (binary, code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Drop previous events + initialize_block(2); + + assert_ok!(Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, 1_000,)); + // Ensure the contract was stored and get expected deposit amount to be reserved. + expected_deposit(ensure_stored(code_hash)); + assert_ok!(Contracts::remove_code(RuntimeOrigin::signed(ALICE), code_hash)); + }); +} + +#[test] +fn remove_code_wrong_origin() { + let (binary, code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Drop previous events + initialize_block(2); + + assert_ok!(Contracts::upload_code(RuntimeOrigin::signed(ALICE), binary, 1_000,)); + // Ensure the contract was stored and get expected deposit amount to be reserved. + expected_deposit(ensure_stored(code_hash)); + + assert_noop!( + Contracts::remove_code(RuntimeOrigin::signed(BOB), code_hash), + sp_runtime::traits::BadOrigin, + ); + }); +} + +#[test] +fn remove_code_in_use() { + let (binary, code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + assert_ok!(builder::instantiate_with_code(binary).build()); + + // Drop previous events + initialize_block(2); + + assert_noop!( + Contracts::remove_code(RuntimeOrigin::signed(ALICE), code_hash), + >::CodeInUse, + ); + + assert_eq!(System::events(), vec![]); + }); +} + +#[test] +fn remove_code_not_found() { + let (_binary, code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Drop previous events + initialize_block(2); + + assert_noop!( + Contracts::remove_code(RuntimeOrigin::signed(ALICE), code_hash), + >::CodeNotFound, + ); + + assert_eq!(System::events(), vec![]); + }); +} + +#[test] +fn instantiate_with_zero_balance_works() { + let (binary, code_hash) = compile_module("dummy").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let min_balance = Contracts::min_balance(); + + // Drop previous events + initialize_block(2); + + // Instantiate the BOB contract. + let Contract { addr, account_id } = + builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); + + // Ensure the contract was stored and get expected deposit amount to be reserved. + expected_deposit(ensure_stored(code_hash)); + + // Make sure the account exists even though no free balance was send + assert_eq!(::Currency::free_balance(&account_id), min_balance); + assert_eq!( + ::Currency::total_balance(&account_id), + min_balance + contract_base_deposit(&addr) + ); + + assert_eq!( + System::events(), + vec![ + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Held { + reason: ::RuntimeHoldReason::Contracts( + HoldReason::CodeUploadDepositReserve, + ), + who: ALICE, + amount: 776, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::System(frame_system::Event::NewAccount { + account: account_id.clone(), + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Endowed { + account: account_id.clone(), + free_balance: min_balance, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { + from: ALICE, + to: account_id.clone(), + amount: min_balance, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Contracts(crate::Event::Instantiated { + deployer: ALICE_ADDR, + contract: addr, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { + reason: ::RuntimeHoldReason::Contracts( + HoldReason::StorageDepositReserve, + ), + source: ALICE, + dest: account_id, + transferred: 336, + }), + topics: vec![], + }, + ] + ); + }); +} + +#[test] +fn instantiate_with_below_existential_deposit_works() { + let (binary, code_hash) = compile_module("dummy").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let min_balance = Contracts::min_balance(); + let value = 50; + + // Drop previous events + initialize_block(2); + + // Instantiate the BOB contract. + let Contract { addr, account_id } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(value) + .build_and_unwrap_contract(); + + // Ensure the contract was stored and get expected deposit amount to be reserved. + expected_deposit(ensure_stored(code_hash)); + // Make sure the account exists even though not enough free balance was send + assert_eq!(::Currency::free_balance(&account_id), min_balance + value); + assert_eq!( + ::Currency::total_balance(&account_id), + min_balance + value + contract_base_deposit(&addr) + ); + + assert_eq!( + System::events(), + vec![ + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Held { + reason: ::RuntimeHoldReason::Contracts( + HoldReason::CodeUploadDepositReserve, + ), + who: ALICE, + amount: 776, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::System(frame_system::Event::NewAccount { + account: account_id.clone() + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Endowed { + account: account_id.clone(), + free_balance: min_balance, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { + from: ALICE, + to: account_id.clone(), + amount: min_balance, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { + from: ALICE, + to: account_id.clone(), + amount: 50, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Contracts(crate::Event::Instantiated { + deployer: ALICE_ADDR, + contract: addr, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { + reason: ::RuntimeHoldReason::Contracts( + HoldReason::StorageDepositReserve, + ), + source: ALICE, + dest: account_id.clone(), + transferred: 336, + }), + topics: vec![], + }, + ] + ); + }); +} + +#[test] +fn storage_deposit_works() { + let (binary, _code_hash) = compile_module("multi_store").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let Contract { addr, account_id } = + builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); + + let mut deposit = contract_base_deposit(&addr); + + // Drop previous events + initialize_block(2); + + // Create storage + assert_ok!(builder::call(addr).value(42).data((50u32, 20u32).encode()).build()); + // 4 is for creating 2 storage items + // 48 is for each of the keys + let charged0 = 4 + 50 + 20 + 48 + 48; + deposit += charged0; + assert_eq!(get_contract(&addr).total_deposit(), deposit); + + // Add more storage (but also remove some) + assert_ok!(builder::call(addr).data((100u32, 10u32).encode()).build()); + let charged1 = 50 - 10; + deposit += charged1; + assert_eq!(get_contract(&addr).total_deposit(), deposit); + + // Remove more storage (but also add some) + assert_ok!(builder::call(addr).data((10u32, 20u32).encode()).build()); + // -1 for numeric instability + let refunded0 = 90 - 10 - 1; + deposit -= refunded0; + assert_eq!(get_contract(&addr).total_deposit(), deposit); + + assert_eq!( + System::events(), + vec![ + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::Transfer { + from: ALICE, + to: account_id.clone(), + amount: 42, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { + reason: ::RuntimeHoldReason::Contracts( + HoldReason::StorageDepositReserve, + ), + source: ALICE, + dest: account_id.clone(), + transferred: charged0, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::TransferAndHold { + reason: ::RuntimeHoldReason::Contracts( + HoldReason::StorageDepositReserve, + ), + source: ALICE, + dest: account_id.clone(), + transferred: charged1, + }), + topics: vec![], + }, + EventRecord { + phase: Phase::Initialization, + event: RuntimeEvent::Balances(pallet_balances::Event::TransferOnHold { + reason: ::RuntimeHoldReason::Contracts( + HoldReason::StorageDepositReserve, + ), + source: account_id.clone(), + dest: ALICE, + amount: refunded0, + }), + topics: vec![], + }, + ] + ); + }); +} + +#[test] +fn storage_deposit_callee_works() { + let (binary_caller, _code_hash_caller) = compile_module("call").unwrap(); + let (binary_callee, _code_hash_callee) = compile_module("store_call").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create both contracts: Constructors do nothing. + let Contract { addr: addr_caller, .. } = + builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); + + assert_ok!(builder::call(addr_caller).data((100u32, &addr_callee).encode()).build()); + + let callee = get_contract(&addr_callee); + let deposit = DepositPerByte::get() * 100 + DepositPerItem::get() * 1 + 48; + + assert_eq!(Pallet::::evm_balance(&addr_caller), U256::zero()); + assert_eq!(callee.total_deposit(), deposit + contract_base_deposit(&addr_callee)); + }); +} + +#[test] +fn set_code_extrinsic() { + let (binary, code_hash) = compile_module("dummy").unwrap(); + let (new_binary, new_code_hash) = compile_module("crypto_hash_keccak_256").unwrap(); + + assert_ne!(code_hash, new_code_hash); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); + + assert_ok!(Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + new_binary, + deposit_limit::(), + )); + + // Drop previous events + initialize_block(2); + + assert_eq!(get_contract(&addr).code_hash, code_hash); + assert_refcount!(&code_hash, 1); + assert_refcount!(&new_code_hash, 0); + + // only root can execute this extrinsic + assert_noop!( + Contracts::set_code(RuntimeOrigin::signed(ALICE), addr, new_code_hash), + sp_runtime::traits::BadOrigin, + ); + assert_eq!(get_contract(&addr).code_hash, code_hash); + assert_refcount!(&code_hash, 1); + assert_refcount!(&new_code_hash, 0); + assert_eq!(System::events(), vec![]); + + // contract must exist + assert_noop!( + Contracts::set_code(RuntimeOrigin::root(), BOB_ADDR, new_code_hash), + >::ContractNotFound, + ); + assert_eq!(get_contract(&addr).code_hash, code_hash); + assert_refcount!(&code_hash, 1); + assert_refcount!(&new_code_hash, 0); + assert_eq!(System::events(), vec![]); + + // new code hash must exist + assert_noop!( + Contracts::set_code(RuntimeOrigin::root(), addr, Default::default()), + >::CodeNotFound, + ); + assert_eq!(get_contract(&addr).code_hash, code_hash); + assert_refcount!(&code_hash, 1); + assert_refcount!(&new_code_hash, 0); + assert_eq!(System::events(), vec![]); + + // successful call + assert_ok!(Contracts::set_code(RuntimeOrigin::root(), addr, new_code_hash)); + assert_eq!(get_contract(&addr).code_hash, new_code_hash); + assert_refcount!(&code_hash, 0); + assert_refcount!(&new_code_hash, 1); + }); +} + +#[test] +fn slash_cannot_kill_account() { + let (binary, _code_hash) = compile_module("dummy").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let value = 700; + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let min_balance = Contracts::min_balance(); + + let Contract { addr, account_id } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(value) + .build_and_unwrap_contract(); + + // Drop previous events + initialize_block(2); + + let info_deposit = contract_base_deposit(&addr); + + assert_eq!( + get_balance_on_hold(&HoldReason::StorageDepositReserve.into(), &account_id), + info_deposit + ); + + assert_eq!( + ::Currency::total_balance(&account_id), + info_deposit + value + min_balance + ); + + // Try to destroy the account of the contract by slashing the total balance. + // The account does not get destroyed because slashing only affects the balance held + // under certain `reason`. Slashing can for example happen if the contract takes part + // in staking. + let _ = ::Currency::slash( + &HoldReason::StorageDepositReserve.into(), + &account_id, + ::Currency::total_balance(&account_id), + ); + + // Slashing only removed the balance held. + assert_eq!(::Currency::total_balance(&account_id), value + min_balance); + }); +} + +#[test] +fn contract_reverted() { + let (binary, code_hash) = compile_module("return_with_data").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let flags = ReturnFlags::REVERT; + let buffer = [4u8, 8, 15, 16, 23, 42]; + let input = (flags.bits(), buffer).encode(); + + // We just upload the code for later use + assert_ok!(Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + binary.clone(), + deposit_limit::(), + )); + + // Calling extrinsic: revert leads to an error + assert_err_ignore_postinfo!( + builder::instantiate(code_hash).data(input.clone()).build(), + >::ContractReverted, + ); + + // Calling extrinsic: revert leads to an error + assert_err_ignore_postinfo!( + builder::instantiate_with_code(binary).data(input.clone()).build(), + >::ContractReverted, + ); + + // Calling directly: revert leads to success but the flags indicate the error + // This is just a different way of transporting the error that allows the read out + // the `data` which is only there on success. Obviously, the contract isn't + // instantiated. + let result = builder::bare_instantiate(Code::Existing(code_hash)) + .data(input.clone()) + .build_and_unwrap_result(); + assert_eq!(result.result.flags, flags); + assert_eq!(result.result.data, buffer); + assert!(!>::contains_key(result.addr)); + + // Pass empty flags and therefore successfully instantiate the contract for later use. + let Contract { addr, .. } = builder::bare_instantiate(Code::Existing(code_hash)) + .data(ReturnFlags::empty().bits().encode()) + .build_and_unwrap_contract(); + + // Calling extrinsic: revert leads to an error + assert_err_ignore_postinfo!( + builder::call(addr).data(input.clone()).build(), + >::ContractReverted, + ); + + // Calling directly: revert leads to success but the flags indicate the error + let result = builder::bare_call(addr).data(input).build_and_unwrap_result(); + assert_eq!(result.flags, flags); + assert_eq!(result.data, buffer); + }); +} + +#[test] +fn set_code_hash() { + let (binary, _) = compile_module("set_code_hash").unwrap(); + let (new_binary, new_code_hash) = compile_module("new_set_code_hash_contract").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Instantiate the 'caller' + let Contract { addr: contract_addr, .. } = builder::bare_instantiate(Code::Upload(binary)) + .native_value(300_000) + .build_and_unwrap_contract(); + // upload new code + assert_ok!(Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + new_binary.clone(), + deposit_limit::(), + )); + + System::reset_events(); + + // First call sets new code_hash and returns 1 + let result = builder::bare_call(contract_addr) + .data(new_code_hash.as_ref().to_vec()) + .build_and_unwrap_result(); + assert_return_code!(result, 1); + + // Second calls new contract code that returns 2 + let result = builder::bare_call(contract_addr).build_and_unwrap_result(); + assert_return_code!(result, 2); + }); +} + +#[test] +fn storage_deposit_limit_is_enforced() { + let (binary, _code_hash) = compile_module("store_call").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let min_balance = Contracts::min_balance(); + + // Setting insufficient storage_deposit should fail. + assert_err!( + builder::bare_instantiate(Code::Upload(binary.clone())) + // expected deposit is 2 * ed + 3 for the call + .storage_deposit_limit((2 * min_balance + 3 - 1).into()) + .build() + .result, + >::StorageDepositLimitExhausted, + ); + + // Instantiate the BOB contract. + let Contract { addr, account_id } = + builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); + + let info_deposit = contract_base_deposit(&addr); + // Check that the BOB contract has been instantiated and has the minimum balance + assert_eq!(get_contract(&addr).total_deposit(), info_deposit); + assert_eq!( + ::Currency::total_balance(&account_id), + info_deposit + min_balance + ); + + // Create 1 byte of storage with a price of per byte, + // setting insufficient deposit limit, as it requires 3 Balance: + // 2 for the item added + 1 (value) + 48 (key) + assert_err_ignore_postinfo!( + builder::call(addr) + .storage_deposit_limit(50) + .data(1u32.to_le_bytes().to_vec()) + .build(), + >::StorageDepositLimitExhausted, + ); + + // now with enough limit + assert_ok!(builder::call(addr) + .storage_deposit_limit(51) + .data(1u32.to_le_bytes().to_vec()) + .build()); + + // Use 4 more bytes of the storage for the same item, which requires 4 Balance. + // Should fail as DefaultDepositLimit is 3 and hence isn't enough. + assert_err_ignore_postinfo!( + builder::call(addr) + .storage_deposit_limit(3) + .data(5u32.to_le_bytes().to_vec()) + .build(), + >::StorageDepositLimitExhausted, + ); + }); +} + +#[test] +fn deposit_limit_in_nested_calls() { + let (binary_caller, _code_hash_caller) = compile_module("create_storage_and_call").unwrap(); + let (binary_callee, _code_hash_callee) = compile_module("store_call").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create both contracts: Constructors do nothing. + let Contract { addr: addr_caller, .. } = + builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); + + // Create 100 bytes of storage with a price of per byte + // This is 100 Balance + 2 Balance for the item + // 48 for the key + assert_ok!(builder::call(addr_callee) + .storage_deposit_limit(102 + 48) + .data(100u32.to_le_bytes().to_vec()) + .build()); + + // We do not remove any storage but add a storage item of 12 bytes in the caller + // contract. This would cost 12 + 2 + 72 = 86 Balance. + // The nested call doesn't get a special limit, which is set by passing `u64::MAX` to it. + // This should fail as the specified parent's limit is less than the cost: 13 < + // 14. + assert_err_ignore_postinfo!( + builder::call(addr_caller) + .storage_deposit_limit(85) + .data((100u32, &addr_callee, U256::MAX).encode()) + .build(), + >::StorageDepositLimitExhausted, + ); + + // Now we specify the parent's limit high enough to cover the caller's storage + // additions. However, we use a single byte more in the callee, hence the storage + // deposit should be 87 Balance. + // The nested call doesn't get a special limit, which is set by passing `u64::MAX` to it. + // This should fail as the specified parent's limit is less than the cost: 86 < 87 + assert_err_ignore_postinfo!( + builder::call(addr_caller) + .storage_deposit_limit(86) + .data((101u32, &addr_callee, &U256::MAX).encode()) + .build(), + >::StorageDepositLimitExhausted, + ); + + // The parents storage deposit limit doesn't matter as the sub calls limit + // is enforced eagerly. However, we set a special deposit limit of 1 Balance for the + // nested call. This should fail as callee adds up 2 bytes to the storage, meaning + // that the nested call should have a deposit limit of at least 2 Balance. The + // sub-call should be rolled back, which is covered by the next test case. + let ret = builder::bare_call(addr_caller) + .storage_deposit_limit(DepositLimit::Balance(u64::MAX)) + .data((102u32, &addr_callee, U256::from(1u64)).encode()) + .build_and_unwrap_result(); + assert_return_code!(ret, RuntimeReturnCode::OutOfResources); + + // Refund in the callee contract but not enough to cover the Balance required by the + // caller. Note that if previous sub-call wouldn't roll back, this call would pass + // making the test case fail. We don't set a special limit for the nested call here. + assert_err_ignore_postinfo!( + builder::call(addr_caller) + .storage_deposit_limit(0) + .data((87u32, &addr_callee, &U256::MAX.to_little_endian()).encode()) + .build(), + >::StorageDepositLimitExhausted, + ); + + let _ = ::Currency::set_balance(&ALICE, 511); + + // Require more than the sender's balance. + // Limit the sub call to little balance so it should fail in there + let ret = builder::bare_call(addr_caller) + .data((416, &addr_callee, U256::from(1u64)).encode()) + .build_and_unwrap_result(); + assert_return_code!(ret, RuntimeReturnCode::OutOfResources); + + // Free up enough storage in the callee so that the caller can create a new item + // We set the special deposit limit of 1 Balance for the nested call, which isn't + // enforced as callee frees up storage. This should pass. + assert_ok!(builder::call(addr_caller) + .storage_deposit_limit(1) + .data((0u32, &addr_callee, U256::from(1u64)).encode()) + .build()); + }); +} + +#[test] +fn deposit_limit_in_nested_instantiate() { + let (binary_caller, _code_hash_caller) = + compile_module("create_storage_and_instantiate").unwrap(); + let (binary_callee, code_hash_callee) = compile_module("store_deploy").unwrap(); + const ED: u64 = 5; + ExtBuilder::default().existential_deposit(ED).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let _ = ::Currency::set_balance(&BOB, 1_000_000); + // Create caller contract + let Contract { addr: addr_caller, account_id: caller_id } = + builder::bare_instantiate(Code::Upload(binary_caller)) + .native_value(10_000) // this balance is later passed to the deployed contract + .build_and_unwrap_contract(); + // Deploy a contract to get its occupied storage size + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(binary_callee)) + .data(vec![0, 0, 0, 0]) + .build_and_unwrap_contract(); + + // This is the deposit we expect to be charged just for instantiatiting the callee. + // + // - callee_info_len + 2 for storing the new contract info + // - the deposit for depending on a code hash + // - ED for deployed contract account + // - 2 for the storage item of 0 bytes being created in the callee constructor + // - 48 for the key + let callee_min_deposit = { + let callee_info_len = + AccountInfo::::load_contract(&addr).unwrap().encoded_size() as u64; + let code_deposit = lockup_deposit(&code_hash_callee); + callee_info_len + code_deposit + 2 + ED + 2 + 48 + }; + + // The parent just stores an item of the passed size so at least + // we need to pay for the item itself. + let caller_min_deposit = callee_min_deposit + 2 + 48; + + // Fail in callee. + // + // We still fail in the sub call because we enforce limits on return from a contract. + // Sub calls return first to they are checked first. + let ret = builder::bare_call(addr_caller) + .origin(RuntimeOrigin::signed(BOB)) + .storage_deposit_limit(DepositLimit::Balance(0)) + .data((&code_hash_callee, 100u32, &U256::MAX.to_little_endian()).encode()) + .build_and_unwrap_result(); + assert_return_code!(ret, RuntimeReturnCode::OutOfResources); + // The charges made on instantiation should be rolled back. + assert_eq!(::Currency::free_balance(&BOB), 1_000_000); + + // Fail in the caller. + // + // For that we need to supply enough storage deposit so that the sub call + // succeeds but the parent call runs out of storage. + let ret = builder::bare_call(addr_caller) + .origin(RuntimeOrigin::signed(BOB)) + .storage_deposit_limit(DepositLimit::Balance(callee_min_deposit)) + .data((&code_hash_callee, 0u32, &U256::MAX.to_little_endian()).encode()) + .build(); + assert_err!(ret.result, >::StorageDepositLimitExhausted); + // The charges made on the instantiation should be rolled back. + assert_eq!(::Currency::free_balance(&BOB), 1_000_000); + + // Fail in the callee with bytes. + // + // Same as above but stores one byte in both caller and callee. + let ret = builder::bare_call(addr_caller) + .origin(RuntimeOrigin::signed(BOB)) + .storage_deposit_limit(DepositLimit::Balance(caller_min_deposit + 1)) + .data((&code_hash_callee, 1u32, U256::from(callee_min_deposit)).encode()) + .build_and_unwrap_result(); + assert_return_code!(ret, RuntimeReturnCode::OutOfResources); + // The charges made on the instantiation should be rolled back. + assert_eq!(::Currency::free_balance(&BOB), 1_000_000); + + // Fail in the caller with bytes. + // + // Same as above but stores one byte in both caller and callee. + let ret = builder::bare_call(addr_caller) + .origin(RuntimeOrigin::signed(BOB)) + .storage_deposit_limit(DepositLimit::Balance(callee_min_deposit + 1)) + .data((&code_hash_callee, 1u32, U256::from(callee_min_deposit + 1)).encode()) + .build(); + assert_err!(ret.result, >::StorageDepositLimitExhausted); + // The charges made on the instantiation should be rolled back. + assert_eq!(::Currency::free_balance(&BOB), 1_000_000); + + // Set enough deposit limit for the child instantiate. This should succeed. + let result = builder::bare_call(addr_caller) + .origin(RuntimeOrigin::signed(BOB)) + .storage_deposit_limit((caller_min_deposit + 2).into()) + .data((&code_hash_callee, 1u32, U256::from(callee_min_deposit + 1)).encode()) + .build(); + + let returned = result.result.unwrap(); + assert!(!returned.did_revert()); + + // All balance of the caller except ED has been transferred to the callee. + // No deposit has been taken from it. + assert_eq!(::Currency::free_balance(&caller_id), ED); + // Get address of the deployed contract. + let addr_callee = H160::from_slice(&returned.data[0..20]); + let callee_account_id = ::AddressMapper::to_account_id(&addr_callee); + // 10_000 should be sent to callee from the caller contract, plus ED to be sent from the + // origin. + assert_eq!(::Currency::free_balance(&callee_account_id), 10_000 + ED); + // The origin should be charged with what the outer call consumed + assert_eq!( + ::Currency::free_balance(&BOB), + 1_000_000 - (caller_min_deposit + 2), + ); + assert_eq!(result.storage_deposit.charge_or_zero(), (caller_min_deposit + 2)) + }); +} + +#[test] +fn deposit_limit_honors_liquidity_restrictions() { + let (binary, _code_hash) = compile_module("store_call").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let bobs_balance = 1_000; + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let _ = ::Currency::set_balance(&BOB, bobs_balance); + let min_balance = Contracts::min_balance(); + + // Instantiate the BOB contract. + let Contract { addr, account_id } = + builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); + + let info_deposit = contract_base_deposit(&addr); + // Check that the contract has been instantiated and has the minimum balance + assert_eq!(get_contract(&addr).total_deposit(), info_deposit); + assert_eq!( + ::Currency::total_balance(&account_id), + info_deposit + min_balance + ); + + // check that the hold is honored + ::Currency::hold( + &HoldReason::CodeUploadDepositReserve.into(), + &BOB, + bobs_balance - min_balance, + ) + .unwrap(); + assert_err_ignore_postinfo!( + builder::call(addr) + .origin(RuntimeOrigin::signed(BOB)) + .storage_deposit_limit(10_000) + .data(100u32.to_le_bytes().to_vec()) + .build(), + >::StorageDepositNotEnoughFunds, + ); + assert_eq!(::Currency::free_balance(&BOB), min_balance); + }); +} + +#[test] +fn deposit_limit_honors_existential_deposit() { + let (binary, _code_hash) = compile_module("store_call").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + let _ = ::Currency::set_balance(&BOB, 300); + let min_balance = Contracts::min_balance(); + + // Instantiate the BOB contract. + let Contract { addr, account_id } = + builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); + + let info_deposit = contract_base_deposit(&addr); + + // Check that the contract has been instantiated and has the minimum balance + assert_eq!(get_contract(&addr).total_deposit(), info_deposit); + assert_eq!( + ::Currency::total_balance(&account_id), + min_balance + info_deposit + ); + + // check that the deposit can't bring the account below the existential deposit + assert_err_ignore_postinfo!( + builder::call(addr) + .origin(RuntimeOrigin::signed(BOB)) + .storage_deposit_limit(10_000) + .data(100u32.to_le_bytes().to_vec()) + .build(), + >::StorageDepositNotEnoughFunds, + ); + assert_eq!(::Currency::free_balance(&BOB), 300); + }); +} + +#[test] +fn native_dependency_deposit_works() { + let (binary, code_hash) = compile_module("set_code_hash").unwrap(); + let (dummy_binary, dummy_code_hash) = compile_module("dummy").unwrap(); + + // Test with both existing and uploaded code + for code in [Code::Upload(binary.clone()), Code::Existing(code_hash)] { + ExtBuilder::default().build().execute_with(|| { + let _ = Balances::set_balance(&ALICE, 1_000_000); + let lockup_deposit_percent = CodeHashLockupDepositPercent::get(); + + // Upload the dummy contract, + Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + dummy_binary.clone(), + deposit_limit::(), + ) + .unwrap(); + + // Upload `set_code_hash` contracts if using Code::Existing. + let add_upload_deposit = match code { + Code::Existing(_) => { + Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + binary.clone(), + deposit_limit::(), + ) + .unwrap(); + false + }, + Code::Upload(_) => true, + }; + + // Instantiate the set_code_hash contract. + let res = builder::bare_instantiate(code).build(); + + let addr = res.result.unwrap().addr; + let account_id = ::AddressMapper::to_account_id(&addr); + let base_deposit = contract_base_deposit(&addr); + let upload_deposit = get_code_deposit(&code_hash); + let extra_deposit = add_upload_deposit.then(|| upload_deposit).unwrap_or_default(); + + assert_eq!( + res.storage_deposit.charge_or_zero(), + extra_deposit + base_deposit + Contracts::min_balance() + ); + + // call set_code_hash + builder::bare_call(addr) + .data(dummy_code_hash.encode()) + .build_and_unwrap_result(); + + // Check updated storage_deposit due to code size changes + let deposit_diff = lockup_deposit_percent.mul_ceil(get_code_deposit(&code_hash)) - + lockup_deposit_percent.mul_ceil(get_code_deposit(&dummy_code_hash)); + let new_base_deposit = contract_base_deposit(&addr); + assert_ne!(deposit_diff, 0); + assert_eq!(base_deposit - new_base_deposit, deposit_diff); + + assert_eq!( + get_balance_on_hold(&HoldReason::StorageDepositReserve.into(), &account_id), + new_base_deposit + ); + }); + } +} + +#[test] +fn block_hash_works() { + let (code, _) = compile_module("block_hash").unwrap(); + + ExtBuilder::default().existential_deposit(1).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // The genesis config sets to the block number to 1 + let block_hash = [1; 32]; + frame_system::BlockHash::::insert( + &crate::BlockNumberFor::::from(0u32), + ::Hash::from(&block_hash), + ); + assert_ok!(builder::call(addr) + .data((U256::zero(), H256::from(block_hash)).encode()) + .build()); + + // A block number out of range returns the zero value + assert_ok!(builder::call(addr).data((U256::from(1), H256::zero()).encode()).build()); + }); +} + +#[test] +fn block_author_works() { + let (code, _) = compile_module("block_author").unwrap(); + + ExtBuilder::default().existential_deposit(1).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // The fixture asserts the input to match the find_author API method output. + assert_ok!(builder::call(addr).data(EVE_ADDR.encode()).build()); + }); +} + +#[test] +fn root_cannot_upload_code() { + let (binary, _) = compile_module("dummy").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + assert_noop!( + Contracts::upload_code(RuntimeOrigin::root(), binary, deposit_limit::()), + DispatchError::BadOrigin, + ); + }); +} + +#[test] +fn root_cannot_remove_code() { + let (_, code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + assert_noop!( + Contracts::remove_code(RuntimeOrigin::root(), code_hash), + DispatchError::BadOrigin, + ); + }); +} + +#[test] +fn signed_cannot_set_code() { + let (_, code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + assert_noop!( + Contracts::set_code(RuntimeOrigin::signed(ALICE), BOB_ADDR, code_hash), + DispatchError::BadOrigin, + ); + }); +} + +#[test] +fn none_cannot_call_code() { + ExtBuilder::default().build().execute_with(|| { + assert_err_ignore_postinfo!( + builder::call(BOB_ADDR).origin(RuntimeOrigin::none()).build(), + DispatchError::BadOrigin, + ); + }); +} + +#[test] +fn root_can_call() { + let (binary, _) = compile_module("dummy").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(binary)).build_and_unwrap_contract(); + + // Call the contract. + assert_ok!(builder::call(addr).origin(RuntimeOrigin::root()).build()); + }); +} + +#[test] +fn root_cannot_instantiate_with_code() { + let (binary, _) = compile_module("dummy").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + assert_err_ignore_postinfo!( + builder::instantiate_with_code(binary).origin(RuntimeOrigin::root()).build(), + DispatchError::BadOrigin + ); + }); +} + +#[test] +fn root_cannot_instantiate() { + let (_, code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + assert_err_ignore_postinfo!( + builder::instantiate(code_hash).origin(RuntimeOrigin::root()).build(), + DispatchError::BadOrigin + ); + }); +} + +#[test] +fn only_upload_origin_can_upload() { + let (binary, _) = compile_module("dummy").unwrap(); + UploadAccount::set(Some(ALICE)); + ExtBuilder::default().build().execute_with(|| { + let _ = Balances::set_balance(&ALICE, 1_000_000); + let _ = Balances::set_balance(&BOB, 1_000_000); + + assert_err!( + Contracts::upload_code(RuntimeOrigin::root(), binary.clone(), deposit_limit::(),), + DispatchError::BadOrigin + ); + + assert_err!( + Contracts::upload_code( + RuntimeOrigin::signed(BOB), + binary.clone(), + deposit_limit::(), + ), + DispatchError::BadOrigin + ); + + // Only alice is allowed to upload contract code. + assert_ok!(Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + binary.clone(), + deposit_limit::(), + )); + }); +} + +#[test] +fn only_instantiation_origin_can_instantiate() { + let (code, code_hash) = compile_module("dummy").unwrap(); + InstantiateAccount::set(Some(ALICE)); + ExtBuilder::default().build().execute_with(|| { + let _ = Balances::set_balance(&ALICE, 1_000_000); + let _ = Balances::set_balance(&BOB, 1_000_000); + + assert_err_ignore_postinfo!( + builder::instantiate_with_code(code.clone()) + .origin(RuntimeOrigin::root()) + .build(), + DispatchError::BadOrigin + ); + + assert_err_ignore_postinfo!( + builder::instantiate_with_code(code.clone()) + .origin(RuntimeOrigin::signed(BOB)) + .build(), + DispatchError::BadOrigin + ); + + // Only Alice can instantiate + assert_ok!(builder::instantiate_with_code(code).build()); + + // Bob cannot instantiate with either `instantiate_with_code` or `instantiate`. + assert_err_ignore_postinfo!( + builder::instantiate(code_hash).origin(RuntimeOrigin::signed(BOB)).build(), + DispatchError::BadOrigin + ); + }); +} + +#[test] +fn balance_of_api() { + let (binary, _code_hash) = compile_module("balance_of").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = Balances::set_balance(&ALICE, 1_000_000); + let _ = Balances::set_balance(&ALICE_FALLBACK, 1_000_000); + + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(binary.to_vec())).build_and_unwrap_contract(); + + // The fixture asserts a non-zero returned free balance of the account; + // The ALICE_FALLBACK account is endowed; + // Hence we should not revert + assert_ok!(builder::call(addr).data(ALICE_ADDR.0.to_vec()).build()); + + // The fixture asserts a non-zero returned free balance of the account; + // The ETH_BOB account is not endowed; + // Hence we should revert + assert_err_ignore_postinfo!( + builder::call(addr).data(BOB_ADDR.0.to_vec()).build(), + >::ContractTrapped + ); + }); +} + +#[test] +fn balance_api_returns_free_balance() { + let (binary, _code_hash) = compile_module("balance").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Instantiate the BOB contract without any extra balance. + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(binary.to_vec())).build_and_unwrap_contract(); + + let value = 0; + // Call BOB which makes it call the balance runtime API. + // The contract code asserts that the returned balance is 0. + assert_ok!(builder::call(addr).value(value).build()); + + let value = 1; + // Calling with value will trap the contract. + assert_err_ignore_postinfo!( + builder::call(addr).value(value).build(), + >::ContractTrapped + ); + }); +} + +#[test] +fn call_depth_is_enforced() { + let (binary, _code_hash) = compile_module("recurse").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let extra_recursions = 1024; + + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(binary.to_vec())).build_and_unwrap_contract(); + + // takes the number of recursions + // returns the number of left over recursions + assert_eq!( + u32::from_le_bytes( + builder::bare_call(addr) + .data((limits::CALL_STACK_DEPTH + extra_recursions).encode()) + .build_and_unwrap_result() + .data + .try_into() + .unwrap() + ), + // + 1 because when the call depth is reached the caller contract is trapped without + // the ability to return any data. hence the last call frame is untracked. + extra_recursions + 1, + ); + }); +} + +#[test] +fn gas_consumed_is_linear_for_nested_calls() { + let (code, _code_hash) = compile_module("recurse").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + let [gas_0, gas_1, gas_2, gas_max] = { + [0u32, 1u32, 2u32, limits::CALL_STACK_DEPTH] + .iter() + .map(|i| { + let result = builder::bare_call(addr).data(i.encode()).build(); + assert_eq!( + u32::from_le_bytes(result.result.unwrap().data.try_into().unwrap()), + 0 + ); + result.gas_consumed + }) + .collect::>() + .try_into() + .unwrap() + }; + + let gas_per_recursion = gas_2.checked_sub(&gas_1).unwrap(); + assert_eq!(gas_max, gas_0 + gas_per_recursion * limits::CALL_STACK_DEPTH as u64); + }); +} + +#[test] +fn read_only_call_cannot_store() { + let (binary_caller, _code_hash_caller) = compile_module("read_only_call").unwrap(); + let (binary_callee, _code_hash_callee) = compile_module("store_call").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create both contracts: Constructors do nothing. + let Contract { addr: addr_caller, .. } = + builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); + + // Read-only call fails when modifying storage. + assert_err_ignore_postinfo!( + builder::call(addr_caller).data((&addr_callee, 100u32).encode()).build(), + >::ContractTrapped + ); + }); +} + +#[test] +fn read_only_call_cannot_transfer() { + let (binary_caller, _code_hash_caller) = compile_module("call_with_flags_and_value").unwrap(); + let (binary_callee, _code_hash_callee) = compile_module("dummy").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create both contracts: Constructors do nothing. + let Contract { addr: addr_caller, .. } = + builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); + + // Read-only call fails when a non-zero value is set. + assert_err_ignore_postinfo!( + builder::call(addr_caller) + .data( + (addr_callee, pallet_revive_uapi::CallFlags::READ_ONLY.bits(), 100u64).encode() + ) + .build(), + >::StateChangeDenied + ); + }); +} + +#[test] +fn read_only_subsequent_call_cannot_store() { + let (binary_read_only_caller, _code_hash_caller) = compile_module("read_only_call").unwrap(); + let (binary_caller, _code_hash_caller) = compile_module("call_with_flags_and_value").unwrap(); + let (binary_callee, _code_hash_callee) = compile_module("store_call").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create contracts: Constructors do nothing. + let Contract { addr: addr_caller, .. } = + builder::bare_instantiate(Code::Upload(binary_read_only_caller)) + .build_and_unwrap_contract(); + let Contract { addr: addr_subsequent_caller, .. } = + builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); + + // Subsequent call input. + let input = (&addr_callee, pallet_revive_uapi::CallFlags::empty().bits(), 0u64, 100u32); + + // Read-only call fails when modifying storage. + assert_err_ignore_postinfo!( + builder::call(addr_caller) + .data((&addr_subsequent_caller, input).encode()) + .build(), + >::ContractTrapped + ); + }); +} + +#[test] +fn read_only_call_works() { + let (binary_caller, _code_hash_caller) = compile_module("read_only_call").unwrap(); + let (binary_callee, _code_hash_callee) = compile_module("dummy").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create both contracts: Constructors do nothing. + let Contract { addr: addr_caller, .. } = + builder::bare_instantiate(Code::Upload(binary_caller)).build_and_unwrap_contract(); + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); + + assert_ok!(builder::call(addr_caller).data(addr_callee.encode()).build()); + }); +} + +#[test] +fn create1_with_value_works() { + let (code, code_hash) = compile_module("create1_with_value").unwrap(); + let value = 42; + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create the contract: Constructor does nothing. + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // Call the contract: Deploys itself using create1 and the expected value + assert_ok!(builder::call(addr).value(value).data(code_hash.encode()).build()); + + // We should see the expected balance at the expected account + let address = crate::address::create1(&addr, 1); + let account_id = ::AddressMapper::to_account_id(&address); + let usable_balance = ::Currency::usable_balance(&account_id); + assert_eq!(usable_balance, value); + }); +} + +#[test] +fn gas_price_api_works() { + let (code, _) = compile_module("gas_price").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create fixture: Constructor does nothing + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // Call the contract: It echoes back the value returned by the gas price API. + let received = builder::bare_call(addr).build_and_unwrap_result(); + assert_eq!(received.flags, ReturnFlags::empty()); + assert_eq!(u64::from_le_bytes(received.data[..].try_into().unwrap()), u64::from(GAS_PRICE)); + }); +} + +#[test] +fn base_fee_api_works() { + let (code, _) = compile_module("base_fee").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create fixture: Constructor does nothing + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // Call the contract: It echoes back the value returned by the base fee API. + let received = builder::bare_call(addr).build_and_unwrap_result(); + assert_eq!(received.flags, ReturnFlags::empty()); + assert_eq!(U256::from_little_endian(received.data[..].try_into().unwrap()), U256::zero()); + }); +} + +#[test] +fn call_data_size_api_works() { + let (code, _) = compile_module("call_data_size").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create fixture: Constructor does nothing + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // Call the contract: It echoes back the value returned by the call data size API. + let received = builder::bare_call(addr).build_and_unwrap_result(); + assert_eq!(received.flags, ReturnFlags::empty()); + assert_eq!(u64::from_le_bytes(received.data.try_into().unwrap()), 0); + + let received = builder::bare_call(addr).data(vec![1; 256]).build_and_unwrap_result(); + assert_eq!(received.flags, ReturnFlags::empty()); + assert_eq!(u64::from_le_bytes(received.data.try_into().unwrap()), 256); + }); +} + +#[test] +fn call_data_copy_api_works() { + let (code, _) = compile_module("call_data_copy").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create fixture: Constructor does nothing + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // Call fixture: Expects an input of [255; 32] and executes tests. + assert_ok!(builder::call(addr).data(vec![255; 32]).build()); + }); +} + +#[test] +fn static_data_limit_is_enforced() { + let (oom_rw_trailing, _) = compile_module("oom_rw_trailing").unwrap(); + let (oom_rw_included, _) = compile_module("oom_rw_included").unwrap(); + let (oom_ro, _) = compile_module("oom_ro").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + let _ = Balances::set_balance(&ALICE, 1_000_000); + + assert_err!( + Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + oom_rw_trailing, + deposit_limit::(), + ), + >::StaticMemoryTooLarge + ); + + assert_err!( + Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + oom_rw_included, + deposit_limit::(), + ), + >::BlobTooLarge + ); + + assert_err!( + Contracts::upload_code(RuntimeOrigin::signed(ALICE), oom_ro, deposit_limit::(),), + >::BlobTooLarge + ); + }); +} + +#[test] +fn call_diverging_out_len_works() { + let (code, _) = compile_module("call_diverging_out_len").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create the contract: Constructor does nothing + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // Call the contract: It will issue calls and deploys, asserting on + // correct output if the supplied output length was smaller than + // than what the callee returned. + assert_ok!(builder::call(addr).build()); + }); +} + +#[test] +fn chain_id_works() { + let (code, _) = compile_module("chain_id").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let chain_id = U256::from(::ChainId::get()); + let received = builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_result(); + assert_eq!(received.result.data, chain_id.encode()); + }); +} + +#[test] +fn call_data_load_api_works() { + let (code, _) = compile_module("call_data_load").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create fixture: Constructor does nothing + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // Call the contract: It reads a byte for the offset and then returns + // what call data load returned using this byte as the offset. + let input = (3u8, U256::max_value(), U256::max_value()).encode(); + let received = builder::bare_call(addr).data(input).build().result.unwrap(); + assert_eq!(received.flags, ReturnFlags::empty()); + assert_eq!(U256::from_little_endian(&received.data), U256::max_value()); + + // Edge case + let input = (2u8, U256::from(255).to_big_endian()).encode(); + let received = builder::bare_call(addr).data(input).build().result.unwrap(); + assert_eq!(received.flags, ReturnFlags::empty()); + assert_eq!(U256::from_little_endian(&received.data), U256::from(65280)); + + // Edge case + let received = builder::bare_call(addr).data(vec![1]).build().result.unwrap(); + assert_eq!(received.flags, ReturnFlags::empty()); + assert_eq!(U256::from_little_endian(&received.data), U256::zero()); + + // OOB case + let input = (42u8).encode(); + let received = builder::bare_call(addr).data(input).build().result.unwrap(); + assert_eq!(received.flags, ReturnFlags::empty()); + assert_eq!(U256::from_little_endian(&received.data), U256::zero()); + + // No calldata should return the zero value + let received = builder::bare_call(addr).build().result.unwrap(); + assert_eq!(received.flags, ReturnFlags::empty()); + assert_eq!(U256::from_little_endian(&received.data), U256::zero()); + }); +} + +#[test] +fn return_data_api_works() { + let (code_return_data_api, _) = compile_module("return_data_api").unwrap(); + let (code_return_with_data, hash_return_with_data) = + compile_module("return_with_data").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Upload the io echoing fixture for later use + assert_ok!(Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + code_return_with_data, + deposit_limit::(), + )); + + // Create fixture: Constructor does nothing + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code_return_data_api)) + .build_and_unwrap_contract(); + + // Call the contract: It will issue calls and deploys, asserting on + assert_ok!(builder::call(addr) + .value(10 * 1024) + .data(hash_return_with_data.encode()) + .build()); + }); +} + +#[test] +fn immutable_data_works() { + let (code, _) = compile_module("immutable_data").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let data = [0xfe; 8]; + + // Create fixture: Constructor sets the immtuable data + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .data(data.to_vec()) + .build_and_unwrap_contract(); + + let contract = get_contract(&addr); + let account = ::AddressMapper::to_account_id(&addr); + let actual_deposit = + get_balance_on_hold(&HoldReason::StorageDepositReserve.into(), &account); + + assert_eq!(contract.immutable_data_len(), data.len() as u32); + + // Storing immmutable data charges storage deposit; verify it explicitly. + assert_eq!(actual_deposit, contract_base_deposit(&addr)); + + // make sure it is also recorded in the base deposit + assert_eq!( + get_balance_on_hold(&HoldReason::StorageDepositReserve.into(), &account), + contract.storage_base_deposit(), + ); + + // Call the contract: Asserts the input to equal the immutable data + assert_ok!(builder::call(addr).data(data.to_vec()).build()); + }); +} + +#[test] +fn sbrk_cannot_be_deployed() { + let (code, _) = compile_module("sbrk").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + let _ = Balances::set_balance(&ALICE, 1_000_000); + + assert_err!( + Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + code.clone(), + deposit_limit::(), + ), + >::InvalidInstruction + ); + + assert_err!( + builder::bare_instantiate(Code::Upload(code)).build().result, + >::InvalidInstruction + ); + }); +} + +#[test] +fn overweight_basic_block_cannot_be_deployed() { + let (code, _) = compile_module("basic_block").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + let _ = Balances::set_balance(&ALICE, 1_000_000); + + assert_err!( + Contracts::upload_code( + RuntimeOrigin::signed(ALICE), + code.clone(), + deposit_limit::(), + ), + >::BasicBlockTooLarge + ); + + assert_err!( + builder::bare_instantiate(Code::Upload(code)).build().result, + >::BasicBlockTooLarge + ); + }); +} + +#[test] +fn origin_api_works() { + let (code, _) = compile_module("origin").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create fixture: Constructor does nothing + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // Call the contract: Asserts the origin API to work as expected + assert_ok!(builder::call(addr).build()); + }); +} + +#[test] +fn code_hash_works() { + use crate::precompiles::{Precompile, EVM_REVERT}; + use precompiles::NoInfo; + + let builtin_precompile = H160(NoInfo::::MATCHER.base_address()); + let primitive_precompile = H160::from_low_u64_be(1); + + let (code_hash_code, self_code_hash) = compile_module("code_hash").unwrap(); + let (dummy_code, code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().existential_deposit(1).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code_hash_code)).build_and_unwrap_contract(); + let Contract { addr: dummy_addr, .. } = + builder::bare_instantiate(Code::Upload(dummy_code)).build_and_unwrap_contract(); + + // code hash of dummy contract + assert_ok!(builder::call(addr).data((dummy_addr, code_hash).encode()).build()); + // code hash of itself + assert_ok!(builder::call(addr).data((addr, self_code_hash).encode()).build()); + // code hash of primitive pre-compile (exist but have no bytecode) + assert_ok!(builder::call(addr) + .data((primitive_precompile, crate::exec::EMPTY_CODE_HASH).encode()) + .build()); + // code hash of normal pre-compile (do have a bytecode) + assert_ok!(builder::call(addr) + .data((builtin_precompile, sp_io::hashing::keccak_256(&EVM_REVERT)).encode()) + .build()); + + // EOA doesn't exists + assert_err!( + builder::bare_call(addr) + .data((BOB_ADDR, crate::exec::EMPTY_CODE_HASH).encode()) + .build() + .result, + Error::::ContractTrapped + ); + // non-existing will return zero + assert_ok!(builder::call(addr).data((BOB_ADDR, H256::zero()).encode()).build()); + + // create EOA + let _ = ::Currency::set_balance( + &::AddressMapper::to_account_id(&BOB_ADDR), + 1_000_000, + ); + + // EOA returns empty code hash + assert_ok!(builder::call(addr) + .data((BOB_ADDR, crate::exec::EMPTY_CODE_HASH).encode()) + .build()); + }); +} + +#[test] +fn code_size_works() { + let (tester_code, _) = compile_module("extcodesize").unwrap(); + let tester_code_len = tester_code.len() as u64; + + let (dummy_code, _) = compile_module("dummy").unwrap(); + let dummy_code_len = dummy_code.len() as u64; + + ExtBuilder::default().existential_deposit(1).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + let Contract { addr: tester_addr, .. } = + builder::bare_instantiate(Code::Upload(tester_code)).build_and_unwrap_contract(); + let Contract { addr: dummy_addr, .. } = + builder::bare_instantiate(Code::Upload(dummy_code)).build_and_unwrap_contract(); + + // code size of another contract address + assert_ok!(builder::call(tester_addr).data((dummy_addr, dummy_code_len).encode()).build()); + + // code size of own contract address + assert_ok!(builder::call(tester_addr) + .data((tester_addr, tester_code_len).encode()) + .build()); + + // code size of non contract accounts + assert_ok!(builder::call(tester_addr).data(([8u8; 20], 0u64).encode()).build()); + }); +} + +#[test] +fn origin_must_be_mapped() { + let (code, hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + ::Currency::set_balance(&ALICE, 1_000_000); + ::Currency::set_balance(&EVE, 1_000_000); + + let eve = RuntimeOrigin::signed(EVE); + + // alice can instantiate as she doesn't need a mapping + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // without a mapping eve can neither call nor instantiate + assert_err!( + builder::bare_call(addr).origin(eve.clone()).build().result, + >::AccountUnmapped + ); + assert_err!( + builder::bare_instantiate(Code::Existing(hash)) + .origin(eve.clone()) + .build() + .result, + >::AccountUnmapped + ); + + // after mapping eve is usable as an origin + >::map_account(eve.clone()).unwrap(); + assert_ok!(builder::bare_call(addr).origin(eve.clone()).build().result); + assert_ok!(builder::bare_instantiate(Code::Existing(hash)).origin(eve).build().result); + }); +} + +#[test] +fn mapped_address_works() { + let (code, _) = compile_module("terminate_and_send_to_argument").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + ::Currency::set_balance(&ALICE, 1_000_000); + + // without a mapping everything will be send to the fallback account + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code.clone())).build_and_unwrap_contract(); + assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 0); + builder::bare_call(addr).data(EVE_ADDR.encode()).build_and_unwrap_result(); + assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 100); + + // after mapping it will be sent to the real eve account + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + // need some balance to pay for the map deposit + ::Currency::set_balance(&EVE, 1_000); + >::map_account(RuntimeOrigin::signed(EVE)).unwrap(); + builder::bare_call(addr).data(EVE_ADDR.encode()).build_and_unwrap_result(); + assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 100); + assert_eq!(::Currency::total_balance(&EVE), 1_100); + }); +} + +#[test] +fn recovery_works() { + let (code, _) = compile_module("terminate_and_send_to_argument").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + ::Currency::set_balance(&ALICE, 1_000_000); + + // eve puts her AccountId20 as argument to terminate but forgot to register + // her AccountId32 first so now the funds are trapped in her fallback account + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code.clone())).build_and_unwrap_contract(); + assert_eq!(::Currency::total_balance(&EVE), 0); + assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 0); + builder::bare_call(addr).data(EVE_ADDR.encode()).build_and_unwrap_result(); + assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 100); + assert_eq!(::Currency::total_balance(&EVE), 0); + + let call = RuntimeCall::Balances(pallet_balances::Call::transfer_all { + dest: EVE, + keep_alive: false, + }); + + // she now uses the recovery function to move all funds from the fallback + // account to her real account + >::dispatch_as_fallback_account(RuntimeOrigin::signed(EVE), Box::new(call)) + .unwrap(); + assert_eq!(::Currency::total_balance(&EVE_FALLBACK), 0); + assert_eq!(::Currency::total_balance(&EVE), 100); + }); +} + +#[test] +fn skip_transfer_works() { + let (code_caller, _) = compile_module("call").unwrap(); + let (code, _) = compile_module("store_call").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + ::Currency::set_balance(&ALICE, 1_000_000); + ::Currency::set_balance(&BOB, 0); + + // when gas is some (transfers enabled): bob has no money: fail + assert_err!( + Pallet::::dry_run_eth_transact( + GenericTransaction { + from: Some(BOB_ADDR), + input: code.clone().into(), + gas: Some(1u32.into()), + ..Default::default() + }, + Weight::MAX, + |_, _| 0u64, + ), + EthTransactError::Message(format!( + "insufficient funds for gas * price + value: address {BOB_ADDR:?} have 0 (supplied gas 1)" + )) + ); + + // no gas specified (all transfers are skipped): even without money bob can deploy + assert_ok!(Pallet::::dry_run_eth_transact( + GenericTransaction { + from: Some(BOB_ADDR), + input: code.clone().into(), + ..Default::default() + }, + Weight::MAX, + |_, _| 0u64, + )); + + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + let Contract { addr: caller_addr, .. } = + builder::bare_instantiate(Code::Upload(code_caller)).build_and_unwrap_contract(); + + // call directly: fails with enabled transfers + assert_err!( + Pallet::::dry_run_eth_transact( + GenericTransaction { + from: Some(BOB_ADDR), + to: Some(addr), + input: 0u32.encode().into(), + gas: Some(1u32.into()), + ..Default::default() + }, + Weight::MAX, + |_, _| 0u64, + ), + EthTransactError::Message(format!( + "insufficient funds for gas * price + value: address {BOB_ADDR:?} have 0 (supplied gas 1)" + )) + ); + + // fails to call through other contract + // we didn't roll back the storage changes done by the previous + // call. So the item already exists. We simply increase the size of + // the storage item to incur some deposits (which bob can't pay). + assert!(Pallet::::dry_run_eth_transact( + GenericTransaction { + from: Some(BOB_ADDR), + to: Some(caller_addr), + input: (1u32, &addr).encode().into(), + gas: Some(1u32.into()), + ..Default::default() + }, + Weight::MAX, + |_, _| 0u64, + ) + .is_err(),); + + // works when no gas is specified (skip transfer) + assert_ok!(Pallet::::dry_run_eth_transact( + GenericTransaction { + from: Some(BOB_ADDR), + to: Some(addr), + input: 2u32.encode().into(), + ..Default::default() + }, + Weight::MAX, + |_, _| 0u64, + )); + + // call through contract works when transfers are skipped + assert_ok!(Pallet::::dry_run_eth_transact( + GenericTransaction { + from: Some(BOB_ADDR), + to: Some(caller_addr), + input: (3u32, &addr).encode().into(), + ..Default::default() + }, + Weight::MAX, + |_, _| 0u64, + )); + + // works with transfers enabled if we don't incur a storage cost + // we shrink the item so its actually a refund + assert_ok!(Pallet::::dry_run_eth_transact( + GenericTransaction { + from: Some(BOB_ADDR), + to: Some(caller_addr), + input: (2u32, &addr).encode().into(), + gas: Some(1u32.into()), + ..Default::default() + }, + Weight::MAX, + |_, _| 0u64, + )); + + // fails when trying to increase the storage item size + assert!(Pallet::::dry_run_eth_transact( + GenericTransaction { + from: Some(BOB_ADDR), + to: Some(caller_addr), + input: (3u32, &addr).encode().into(), + gas: Some(1u32.into()), + ..Default::default() + }, + Weight::MAX, + |_, _| 0u64, + ) + .is_err()); + }); +} + +#[test] +fn gas_limit_api_works() { + let (code, _) = compile_module("gas_limit").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + + // Create fixture: Constructor does nothing + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + // Call the contract: It echoes back the value returned by the gas limit API. + let received = builder::bare_call(addr).build_and_unwrap_result(); + assert_eq!(received.flags, ReturnFlags::empty()); + assert_eq!( + u64::from_le_bytes(received.data[..].try_into().unwrap()), + ::BlockWeights::get().max_block.ref_time() + ); + }); +} + +#[test] +fn unknown_syscall_rejected() { + let (code, _) = compile_module("unknown_syscall").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + ::Currency::set_balance(&ALICE, 1_000_000); + + assert_err!( + builder::bare_instantiate(Code::Upload(code)).build().result, + >::CodeRejected, + ) + }); +} + +#[test] +fn unstable_interface_rejected() { + let (code, _) = compile_module("unstable_interface").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + ::Currency::set_balance(&ALICE, 1_000_000); + + Test::set_unstable_interface(false); + assert_err!( + builder::bare_instantiate(Code::Upload(code.clone())).build().result, + >::CodeRejected, + ); + + Test::set_unstable_interface(true); + assert_ok!(builder::bare_instantiate(Code::Upload(code)).build().result); + }); +} + +#[test] +fn tracing_works_for_transfers() { + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000); + let mut tracer = CallTracer::new(Default::default(), |_| U256::zero()); + trace(&mut tracer, || { + builder::bare_call(BOB_ADDR).evm_value(10.into()).build_and_unwrap_result(); + }); + + let trace = tracer.collect_trace(); + assert_eq!( + trace, + Some(CallTrace { + from: ALICE_ADDR, + to: BOB_ADDR, + value: Some(U256::from(10)), + call_type: CallType::Call, + ..Default::default() + }) + ) + }); +} + +#[test] +fn call_tracing_works() { + use crate::evm::*; + use CallType::*; + let (code, _code_hash) = compile_module("tracing").unwrap(); + let (binary_callee, _) = compile_module("tracing_callee").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000); + + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(binary_callee)).build_and_unwrap_contract(); + + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).evm_value(10_000_000.into()).build_and_unwrap_contract(); + + + let tracer_configs = vec![ + CallTracerConfig{ with_logs: false, only_top_call: false}, + CallTracerConfig{ with_logs: false, only_top_call: false}, + CallTracerConfig{ with_logs: false, only_top_call: true}, + ]; + + // Verify that the first trace report the same weight reported by bare_call + // TODO: fix tracing ( https://github.com/paritytech/polkadot-sdk/issues/8362 ) + /* + let mut tracer = CallTracer::new(false, |w| w); + let gas_used = trace(&mut tracer, || { + builder::bare_call(addr).data((3u32, addr_callee).encode()).build().gas_consumed + }); + let trace = tracer.collect_trace().unwrap(); + assert_eq!(&trace.gas_used, &gas_used); + */ + + // Discarding gas usage, check that traces reported are correct + for config in tracer_configs { + let logs = if config.with_logs { + vec![ + CallLog { + address: addr, + topics: Default::default(), + data: b"before".to_vec().into(), + position: 0, + }, + CallLog { + address: addr, + topics: Default::default(), + data: b"after".to_vec().into(), + position: 1, + }, + ] + } else { + vec![] + }; + + let calls = if config.only_top_call { + vec![] + } else { + vec![ + CallTrace { + from: addr, + to: addr_callee, + input: 2u32.encode().into(), + output: hex_literal::hex!( + "08c379a00000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000001a546869732066756e6374696f6e20616c77617973206661696c73000000000000" + ).to_vec().into(), + revert_reason: Some("revert: This function always fails".to_string()), + error: Some("execution reverted".to_string()), + call_type: Call, + value: Some(U256::from(0)), + ..Default::default() + }, + CallTrace { + from: addr, + to: addr, + input: (2u32, addr_callee).encode().into(), + call_type: Call, + logs: logs.clone(), + value: Some(U256::from(0)), + calls: vec![ + CallTrace { + from: addr, + to: addr_callee, + input: 1u32.encode().into(), + output: Default::default(), + error: Some("ContractTrapped".to_string()), + call_type: Call, + value: Some(U256::from(0)), + ..Default::default() + }, + CallTrace { + from: addr, + to: addr, + input: (1u32, addr_callee).encode().into(), + call_type: Call, + logs: logs.clone(), + value: Some(U256::from(0)), + calls: vec![ + CallTrace { + from: addr, + to: addr_callee, + input: 0u32.encode().into(), + output: 0u32.to_le_bytes().to_vec().into(), + call_type: Call, + value: Some(U256::from(0)), + ..Default::default() + }, + CallTrace { + from: addr, + to: addr, + input: (0u32, addr_callee).encode().into(), + call_type: Call, + value: Some(U256::from(0)), + calls: vec![ + CallTrace { + from: addr, + to: BOB_ADDR, + value: Some(U256::from(100)), + call_type: CallType::Call, + ..Default::default() + } + ], + ..Default::default() + }, + ], + ..Default::default() + }, + ], + ..Default::default() + }, + ] + }; + + let mut tracer = CallTracer::new(config, |_| U256::zero()); + trace(&mut tracer, || { + builder::bare_call(addr).data((3u32, addr_callee).encode()).build() + }); + + let trace = tracer.collect_trace(); + let expected_trace = CallTrace { + from: ALICE_ADDR, + to: addr, + input: (3u32, addr_callee).encode().into(), + call_type: Call, + logs: logs.clone(), + value: Some(U256::from(0)), + calls: calls, + ..Default::default() + }; + + assert_eq!( + trace, + expected_trace.into(), + ); + } + }); +} + +#[test] +fn create_call_tracing_works() { + use crate::evm::*; + let (code, code_hash) = compile_module("create2_with_value").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000); + + let mut tracer = CallTracer::new(Default::default(), |_| U256::zero()); + + let Contract { addr, .. } = trace(&mut tracer, || { + builder::bare_instantiate(Code::Upload(code.clone())) + .evm_value(100.into()) + .salt(None) + .build_and_unwrap_contract() + }); + + let call_trace = tracer.collect_trace().unwrap(); + assert_eq!( + call_trace, + CallTrace { + from: ALICE_ADDR, + to: addr, + value: Some(100.into()), + input: Bytes(code.clone()), + call_type: CallType::Create, + ..Default::default() + } + ); + + let mut tracer = CallTracer::new(Default::default(), |_| U256::zero()); + let data = b"garbage"; + let input = (code_hash, data).encode(); + trace(&mut tracer, || { + assert_ok!(builder::call(addr).data(input.clone()).build()); + }); + + let call_trace = tracer.collect_trace().unwrap(); + let child_addr = crate::address::create2(&addr, &code, data, &[1u8; 32]); + + assert_eq!( + call_trace, + CallTrace { + from: ALICE_ADDR, + to: addr, + value: Some(0.into()), + input: input.clone().into(), + calls: vec![CallTrace { + from: addr, + input: input.clone().into(), + to: child_addr, + value: Some(0.into()), + call_type: CallType::Create2, + ..Default::default() + },], + ..Default::default() + } + ); + }); +} + +#[test] +fn prestate_tracing_works() { + use crate::evm::*; + use alloc::collections::BTreeMap; + + let (dummy_code, _) = compile_module("dummy").unwrap(); + let (code, _) = compile_module("tracing").unwrap(); + let (callee_code, _) = compile_module("tracing_callee").unwrap(); + ExtBuilder::default().existential_deposit(200).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000); + + let Contract { addr: addr_callee, .. } = + builder::bare_instantiate(Code::Upload(callee_code.clone())) + .build_and_unwrap_contract(); + + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code.clone())) + .native_value(10) + .build_and_unwrap_contract(); + + // redact balance so that tests are resilient to weight changes + let alice_redacted_balance = Some(U256::from(1)); + + let test_cases: Vec<(Box, _, _)> = vec![ + ( + Box::new(|| { + builder::bare_call(addr) + .data((3u32, addr_callee).encode()) + .build_and_unwrap_result(); + }), + PrestateTracerConfig { + diff_mode: false, + disable_storage: false, + disable_code: false, + }, + PrestateTrace::Prestate(BTreeMap::from([ + ( + ALICE_ADDR, + PrestateTraceInfo { + balance: alice_redacted_balance, + nonce: Some(2), + ..Default::default() + }, + ), + ( + BOB_ADDR, + PrestateTraceInfo { balance: Some(U256::from(0u64)), ..Default::default() }, + ), + ( + addr_callee, + PrestateTraceInfo { + balance: Some(U256::from(0u64)), + code: Some(Bytes(callee_code.clone())), + nonce: Some(1), + ..Default::default() + }, + ), + ( + addr, + PrestateTraceInfo { + balance: Some(U256::from(10_000_000u64)), + code: Some(Bytes(code.clone())), + nonce: Some(1), + ..Default::default() + }, + ), + ])), + ), + ( + Box::new(|| { + builder::bare_call(addr) + .data((3u32, addr_callee).encode()) + .build_and_unwrap_result(); + }), + PrestateTracerConfig { + diff_mode: true, + disable_storage: false, + disable_code: false, + }, + PrestateTrace::DiffMode { + pre: BTreeMap::from([ + ( + BOB_ADDR, + PrestateTraceInfo { + balance: Some(U256::from(100u64)), + ..Default::default() + }, + ), + ( + addr, + PrestateTraceInfo { + balance: Some(U256::from(9_999_900u64)), + code: Some(Bytes(code.clone())), + nonce: Some(1), + ..Default::default() + }, + ), + ]), + post: BTreeMap::from([ + ( + BOB_ADDR, + PrestateTraceInfo { + balance: Some(U256::from(200u64)), + ..Default::default() + }, + ), + ( + addr, + PrestateTraceInfo { + balance: Some(U256::from(9_999_800u64)), + ..Default::default() + }, + ), + ]), + }, + ), + ( + Box::new(|| { + builder::bare_instantiate(Code::Upload(dummy_code.clone())) + .salt(None) + .build_and_unwrap_result(); + }), + PrestateTracerConfig { + diff_mode: true, + disable_storage: false, + disable_code: false, + }, + PrestateTrace::DiffMode { + pre: BTreeMap::from([( + ALICE_ADDR, + PrestateTraceInfo { + balance: alice_redacted_balance, + nonce: Some(2), + ..Default::default() + }, + )]), + post: BTreeMap::from([ + ( + ALICE_ADDR, + PrestateTraceInfo { + balance: alice_redacted_balance, + nonce: Some(3), + ..Default::default() + }, + ), + ( + create1(&ALICE_ADDR, 1), + PrestateTraceInfo { + code: Some(dummy_code.clone().into()), + balance: Some(U256::from(0)), + nonce: Some(1), + ..Default::default() + }, + ), + ]), + }, + ), + ]; + + for (exec_call, config, expected_trace) in test_cases.into_iter() { + let mut tracer = PrestateTracer::::new(config); + trace(&mut tracer, || { + exec_call(); + }); + + let mut trace = tracer.collect_trace(); + + // redact alice balance + match trace { + PrestateTrace::DiffMode { ref mut pre, ref mut post } => { + pre.get_mut(&ALICE_ADDR).map(|info| { + info.balance = alice_redacted_balance; + }); + post.get_mut(&ALICE_ADDR).map(|info| { + info.balance = alice_redacted_balance; + }); + }, + PrestateTrace::Prestate(ref mut pre) => { + pre.get_mut(&ALICE_ADDR).map(|info| { + info.balance = alice_redacted_balance; + }); + }, + } + + assert_eq!(trace, expected_trace); + } + }); +} + +#[test] +fn unknown_precompiles_revert() { + let (code, _code_hash) = compile_module("read_only_call").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + let cases: Vec<(H160, Box)> = vec![( + H160::from_low_u64_be(0x0a), + Box::new(|result| { + assert_err!(result, >::UnsupportedPrecompileAddress); + }), + )]; + + for (callee_addr, assert_result) in cases { + let result = + builder::bare_call(addr).data((callee_addr, [0u8; 0]).encode()).build().result; + assert_result(result); + } + }); +} + +#[test] +fn pure_precompile_works() { + use hex_literal::hex; + + let cases = vec![ + ( + "ECRecover", + H160::from_low_u64_be(1), + hex!("18c547e4f7b0f325ad1e56f57e26c745b09a3e503d86e00e5255ff7f715d3d1c000000000000000000000000000000000000000000000000000000000000001c73b1693892219d736caba55bdb67216e485557ea6b6af75f37096c9aa6a5a75feeb940b1d03b21e36b0e47e79769f095fe2ab855bd91e3a38756b7d75a9c4549").to_vec(), + hex!("000000000000000000000000a94f5374fce5edbc8e2a8697c15331677e6ebf0b").to_vec(), + ), + ( + "Sha256", + H160::from_low_u64_be(2), + hex!("ec07171c4f0f0e2b").to_vec(), + hex!("d0591ea667763c69a5f5a3bae657368ea63318b2c9c8349cccaf507e3cbd7c7a").to_vec(), + ), + ( + "Ripemd160", + H160::from_low_u64_be(3), + hex!("ec07171c4f0f0e2b").to_vec(), + hex!("000000000000000000000000a9c5ebaf7589fd8acfd542c3a008956de84fbeb7").to_vec(), + ), + ( + "Identity", + H160::from_low_u64_be(4), + [42u8; 128].to_vec(), + [42u8; 128].to_vec(), + ), + ( + "Modexp", + H160::from_low_u64_be(5), + hex!("00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000002003fffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2efffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f").to_vec(), + hex!("0000000000000000000000000000000000000000000000000000000000000001").to_vec(), + ), + ( + "Bn128Add", + H160::from_low_u64_be(6), + hex!("18b18acfb4c2c30276db5411368e7185b311dd124691610c5d3b74034e093dc9063c909c4720840cb5134cb9f59fa749755796819658d32efc0d288198f3726607c2b7f58a84bd6145f00c9c2bc0bb1a187f20ff2c92963a88019e7c6a014eed06614e20c147e940f2d70da3f74c9a17df361706a4485c742bd6788478fa17d7").to_vec(), + hex!("2243525c5efd4b9c3d3c45ac0ca3fe4dd85e830a4ce6b65fa1eeaee202839703301d1d33be6da8e509df21cc35964723180eed7532537db9ae5e7d48f195c915").to_vec(), + ), + ( + "Bn128Mul", + H160::from_low_u64_be(7), + hex!("2bd3e6d0f3b142924f5ca7b49ce5b9d54c4703d7ae5648e61d02268b1a0a9fb721611ce0a6af85915e2f1d70300909ce2e49dfad4a4619c8390cae66cefdb20400000000000000000000000000000000000000000000000011138ce750fa15c2").to_vec(), + hex!("070a8d6a982153cae4be29d434e8faef8a47b274a053f5a4ee2a6c9c13c31e5c031b8ce914eba3a9ffb989f9cdd5b0f01943074bf4f0f315690ec3cec6981afc").to_vec(), + ), + ( + "Bn128Pairing", + H160::from_low_u64_be(8), + hex!("1c76476f4def4bb94541d57ebba1193381ffa7aa76ada664dd31c16024c43f593034dd2920f673e204fee2811c678745fc819b55d3e9d294e45c9b03a76aef41209dd15ebff5d46c4bd888e51a93cf99a7329636c63514396b4a452003a35bf704bf11ca01483bfa8b34b43561848d28905960114c8ac04049af4b6315a416782bb8324af6cfc93537a2ad1a445cfd0ca2a71acd7ac41fadbf933c2a51be344d120a2a4cf30c1bf9845f20c6fe39e07ea2cce61f0c9bb048165fe5e4de877550111e129f1cf1097710d41c4ac70fcdfa5ba2023c6ff1cbeac322de49d1b6df7c2032c61a830e3c17286de9462bf242fca2883585b93870a73853face6a6bf411198e9393920d483a7260bfb731fb5d25f1aa493335a9e71297e485b7aef312c21800deef121f1e76426a00665e5c4479674322d4f75edadd46debd5cd992f6ed090689d0585ff075ec9e99ad690c3395bc4b313370b38ef355acdadcd122975b12c85ea5db8c6deb4aab71808dcb408fe3d1e7690c43d37b4ce6cc0166fa7daa").to_vec(), + hex!("0000000000000000000000000000000000000000000000000000000000000001").to_vec(), + ), + ( + "Blake2F", + H160::from_low_u64_be(9), + hex!("0000000048c9bdf267e6096a3ba7ca8485ae67bb2bf894fe72f36e3cf1361d5f3af54fa5d182e6ad7f520e511f6c3e2b8c68059b6bbd41fbabd9831f79217e1319cde05b61626300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000300000000000000000000000000000001").to_vec(), + hex!("08c9bcf367e6096a3ba7ca8485ae67bb2bf894fe72f36e3cf1361d5f3af54fa5d282e6ad7f520e511f6c3e2b8c68059b9442be0454267ce079217e1319cde05b").to_vec(), + ), + ]; + + for (description, precompile_addr, input, output) in cases { + let (code, _code_hash) = compile_module("call_and_return").unwrap(); + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .native_value(1_000) + .build_and_unwrap_contract(); + + let result = builder::bare_call(addr) + .data( + (&precompile_addr, 100u64) + .encode() + .into_iter() + .chain(input) + .collect::>(), + ) + .build_and_unwrap_result(); + + assert_eq!( + Pallet::::evm_balance(&precompile_addr), + U256::from(100), + "{description}: unexpected balance" + ); + assert_eq!( + alloy_core::hex::encode(result.data), + alloy_core::hex::encode(output), + "{description} Unexpected output for precompile: {precompile_addr:?}", + ); + assert_eq!(result.flags, ReturnFlags::empty()); + }); + } +} + +#[test] +fn precompiles_work() { + use crate::precompiles::Precompile; + use alloy_core::sol_types::{Panic, PanicKind, Revert, SolError, SolInterface, SolValue}; + use precompiles::{INoInfo, NoInfo}; + + let precompile_addr = H160(NoInfo::::MATCHER.base_address()); + + let cases = vec![ + ( + INoInfo::INoInfoCalls::identity(INoInfo::identityCall { number: 42u64.into() }) + .abi_encode(), + 42u64.abi_encode(), + RuntimeReturnCode::Success, + ), + ( + INoInfo::INoInfoCalls::reverts(INoInfo::revertsCall { error: "panic".to_string() }) + .abi_encode(), + Revert::from("panic").abi_encode(), + RuntimeReturnCode::CalleeReverted, + ), + ( + INoInfo::INoInfoCalls::panics(INoInfo::panicsCall {}).abi_encode(), + Panic::from(PanicKind::Assert).abi_encode(), + RuntimeReturnCode::CalleeReverted, + ), + ( + INoInfo::INoInfoCalls::errors(INoInfo::errorsCall {}).abi_encode(), + Vec::new(), + RuntimeReturnCode::CalleeTrapped, + ), + // passing non decodeable input reverts with solidity panic + ( + b"invalid".to_vec(), + Panic::from(PanicKind::ResourceError).abi_encode(), + RuntimeReturnCode::CalleeReverted, + ), + ( + INoInfo::INoInfoCalls::passData(INoInfo::passDataCall { + inputLen: limits::CALLDATA_BYTES, + }) + .abi_encode(), + Vec::new(), + RuntimeReturnCode::Success, + ), + ( + INoInfo::INoInfoCalls::passData(INoInfo::passDataCall { + inputLen: limits::CALLDATA_BYTES + 1, + }) + .abi_encode(), + Vec::new(), + RuntimeReturnCode::CalleeTrapped, + ), + ( + INoInfo::INoInfoCalls::returnData(INoInfo::returnDataCall { + returnLen: limits::CALLDATA_BYTES - 4, + }) + .abi_encode(), + vec![42u8; limits::CALLDATA_BYTES as usize - 4], + RuntimeReturnCode::Success, + ), + ( + INoInfo::INoInfoCalls::returnData(INoInfo::returnDataCall { + returnLen: limits::CALLDATA_BYTES + 1, + }) + .abi_encode(), + vec![], + RuntimeReturnCode::CalleeTrapped, + ), + ]; + + for (input, output, error_code) in cases { + let (code, _code_hash) = compile_module("call_and_returncode").unwrap(); + ExtBuilder::default().build().execute_with(|| { + let id = ::AddressMapper::to_account_id(&precompile_addr); + let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .native_value(1000) + .build_and_unwrap_contract(); + + let result = builder::bare_call(addr) + .data( + (&precompile_addr, 0u64).encode().into_iter().chain(input).collect::>(), + ) + .build_and_unwrap_result(); + + // no account or contract info should be created for a NoInfo pre-compile + assert!(get_contract_checked(&precompile_addr).is_none()); + assert!(!System::account_exists(&id)); + assert_eq!(Pallet::::evm_balance(&precompile_addr), U256::zero()); + + assert_eq!(result.flags, ReturnFlags::empty()); + assert_eq!(u32::from_le_bytes(result.data[..4].try_into().unwrap()), error_code as u32); + assert_eq!( + &result.data[4..], + &output, + "Unexpected output for precompile: {precompile_addr:?}", + ); + }); + } +} + +#[test] +fn precompiles_with_info_creates_contract() { + use crate::precompiles::Precompile; + use alloy_core::sol_types::SolInterface; + use precompiles::{IWithInfo, WithInfo}; + + let precompile_addr = H160(WithInfo::::MATCHER.base_address()); + + let cases = vec![( + IWithInfo::IWithInfoCalls::dummy(IWithInfo::dummyCall {}).abi_encode(), + Vec::::new(), + RuntimeReturnCode::Success, + )]; + + for (input, output, error_code) in cases { + let (code, _code_hash) = compile_module("call_and_returncode").unwrap(); + ExtBuilder::default().build().execute_with(|| { + let id = ::AddressMapper::to_account_id(&precompile_addr); + let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .native_value(1000) + .build_and_unwrap_contract(); + + let result = builder::bare_call(addr) + .data( + (&precompile_addr, 0u64).encode().into_iter().chain(input).collect::>(), + ) + .build_and_unwrap_result(); + + // a pre-compile with contract info should create an account on first call + assert!(get_contract_checked(&precompile_addr).is_some()); + assert!(System::account_exists(&id)); + assert_eq!(Pallet::::evm_balance(&precompile_addr), U256::from(0)); + + assert_eq!(result.flags, ReturnFlags::empty()); + assert_eq!(u32::from_le_bytes(result.data[..4].try_into().unwrap()), error_code as u32); + assert_eq!( + &result.data[4..], + &output, + "Unexpected output for precompile: {precompile_addr:?}", + ); + }); + } +} + +#[test] +fn bump_nonce_once_works() { + let (code, hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().existential_deposit(100).build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 1_000_000); + frame_system::Account::::mutate(&ALICE, |account| account.nonce = 1); + + let _ = ::Currency::set_balance(&BOB, 1_000_000); + frame_system::Account::::mutate(&BOB, |account| account.nonce = 1); + + builder::bare_instantiate(Code::Upload(code.clone())) + .origin(RuntimeOrigin::signed(ALICE)) + .bump_nonce(BumpNonce::Yes) + .salt(None) + .build_and_unwrap_result(); + assert_eq!(System::account_nonce(&ALICE), 2); + + // instantiate again is ok + let result = builder::bare_instantiate(Code::Existing(hash)) + .origin(RuntimeOrigin::signed(ALICE)) + .bump_nonce(BumpNonce::Yes) + .salt(None) + .build() + .result; + assert!(result.is_ok()); + + builder::bare_instantiate(Code::Upload(code.clone())) + .origin(RuntimeOrigin::signed(BOB)) + .bump_nonce(BumpNonce::No) + .salt(None) + .build_and_unwrap_result(); + assert_eq!(System::account_nonce(&BOB), 1); + + // instantiate again should fail + let err = builder::bare_instantiate(Code::Upload(code)) + .origin(RuntimeOrigin::signed(BOB)) + .bump_nonce(BumpNonce::No) + .salt(None) + .build() + .result + .unwrap_err(); + + assert_eq!(err, >::DuplicateContract.into()); + }); +} + +#[test] +fn code_size_for_precompiles_works() { + use crate::precompiles::Precompile; + use precompiles::NoInfo; + + let builtin_precompile = H160(NoInfo::::MATCHER.base_address()); + let primitive_precompile = H160::from_low_u64_be(1); + + let (code, _code_hash) = compile_module("extcodesize").unwrap(); + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); + let Contract { addr, .. } = builder::bare_instantiate(Code::Upload(code)) + .native_value(1000) + .build_and_unwrap_contract(); + + // the primitive pre-compiles return 0 code size on eth + builder::bare_call(addr) + .data((&primitive_precompile, 0u64).encode()) + .build_and_unwrap_result(); + + // other precompiles should return the minimal evm revert code + builder::bare_call(addr) + .data((&builtin_precompile, 5u64).encode()) + .build_and_unwrap_result(); + }); +} + +#[test] +fn call_data_limit_is_enforced_subcalls() { + let (code, _code_hash) = compile_module("call_with_input_size").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + let cases: Vec<(u32, Box)> = vec![ + ( + 0_u32, + Box::new(|result| { + assert_ok!(result); + }), + ), + ( + 1_u32, + Box::new(|result| { + assert_ok!(result); + }), + ), + ( + limits::CALLDATA_BYTES, + Box::new(|result| { + assert_ok!(result); + }), + ), + ( + limits::CALLDATA_BYTES + 1, + Box::new(|result| { + assert_err!(result, >::CallDataTooLarge); + }), + ), + ]; + + for (callee_input_size, assert_result) in cases { + let result = builder::bare_call(addr).data(callee_input_size.encode()).build().result; + assert_result(result); + } + }); +} + +#[test] +fn call_data_limit_is_enforced_root_call() { + let (code, _code_hash) = compile_module("dummy").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + let cases: Vec<(H160, u32, Box)> = vec![ + ( + addr, + 0_u32, + Box::new(|result| { + assert_ok!(result); + }), + ), + ( + addr, + 1_u32, + Box::new(|result| { + assert_ok!(result); + }), + ), + ( + addr, + limits::CALLDATA_BYTES, + Box::new(|result| { + assert_ok!(result); + }), + ), + ( + addr, + limits::CALLDATA_BYTES + 1, + Box::new(|result| { + assert_err!(result, >::CallDataTooLarge); + }), + ), + ( + // limit is not enforced when tx calls EOA + BOB_ADDR, + limits::CALLDATA_BYTES + 1, + Box::new(|result| { + assert_ok!(result); + }), + ), + ]; + + for (addr, callee_input_size, assert_result) in cases { + let result = builder::bare_call(addr) + .data(vec![42; callee_input_size as usize]) + .build() + .result; + assert_result(result); + } + }); +} + +#[test] +fn return_data_limit_is_enforced() { + let (code, _code_hash) = compile_module("return_sized").unwrap(); + + ExtBuilder::default().build().execute_with(|| { + let _ = ::Currency::set_balance(&ALICE, 100_000_000_000); + let Contract { addr, .. } = + builder::bare_instantiate(Code::Upload(code)).build_and_unwrap_contract(); + + let cases: Vec<(u32, Box)> = vec![ + ( + 1_u32, + Box::new(|result| { + assert_ok!(result); + }), + ), + ( + limits::CALLDATA_BYTES, + Box::new(|result| { + assert_ok!(result); + }), + ), + ( + limits::CALLDATA_BYTES + 1, + Box::new(|result| { + assert_err!(result, >::ReturnDataTooLarge); + }), + ), + ]; + + for (return_size, assert_result) in cases { + let result = builder::bare_call(addr).data(return_size.encode()).build().result; + assert_result(result); + } + }); +} diff --git a/substrate/frame/revive/src/vm/mod.rs b/substrate/frame/revive/src/vm/mod.rs index ced372c320ba1..3c65cbbfccab3 100644 --- a/substrate/frame/revive/src/vm/mod.rs +++ b/substrate/frame/revive/src/vm/mod.rs @@ -18,23 +18,16 @@ //! This module provides a means for executing contracts //! represented in vm bytecode. -mod runtime; +pub mod pvm; +mod runtime_costs; -#[cfg(doc)] -pub use crate::vm::runtime::SyscallDoc; - -#[cfg(feature = "runtime-benchmarks")] -pub use crate::vm::runtime::{ReturnData, TrapReason}; - -pub use crate::vm::runtime::{Runtime, RuntimeCosts}; +pub use runtime_costs::RuntimeCosts; use crate::{ exec::{ExecResult, Executable, ExportedFunction, Ext}, gas::{GasMeter, Token}, - limits, - storage::meter::Diff, weights::WeightInfo, - AccountIdOf, BadOrigin, BalanceOf, CodeInfoOf, CodeVec, Config, Error, ExecError, HoldReason, + AccountIdOf, BadOrigin, BalanceOf, CodeInfoOf, CodeVec, Config, Error, HoldReason, PristineCode, Weight, LOG_TARGET, }; use alloc::vec::Vec; @@ -44,7 +37,7 @@ use frame_support::{ ensure, traits::{fungible::MutateHold, tokens::Precision::BestEffort}, }; -use sp_core::{Get, H256, U256}; +use sp_core::{H256, U256}; use sp_runtime::DispatchError; /// Validated Vm module ready for execution. @@ -132,29 +125,6 @@ impl ContractBlob where BalanceOf: Into + TryFrom, { - /// We only check for size and nothing else when the code is uploaded. - pub fn from_code(code: Vec, owner: AccountIdOf) -> Result { - // We do validation only when new code is deployed. This allows us to increase - // the limits later without affecting already deployed code. - let available_syscalls = runtime::list_syscalls(T::UnsafeUnstableInterface::get()); - let code = limits::code::enforce::(code, available_syscalls)?; - - let code_len = code.len() as u32; - let bytes_added = code_len.saturating_add(>::max_encoded_len() as u32); - let deposit = Diff { bytes_added, items_added: 2, ..Default::default() } - .update_contract::(None) - .charge_or_zero(); - let code_info = CodeInfo { - owner, - deposit, - refcount: 0, - code_len, - behaviour_version: Default::default(), - }; - let code_hash = H256(sp_io::hashing::keccak_256(&code)); - Ok(ContractBlob { code, code_info, code_hash }) - } - /// Remove the code from storage and refund the deposit to its owner. /// /// Applies all necessary checks before removing the code. @@ -284,119 +254,6 @@ impl CodeInfo { } } -pub struct PreparedCall<'a, E: Ext> { - module: polkavm::Module, - instance: polkavm::RawInstance, - runtime: Runtime<'a, E, polkavm::RawInstance>, -} - -impl<'a, E: Ext> PreparedCall<'a, E> -where - BalanceOf: Into, - BalanceOf: TryFrom, -{ - pub fn call(mut self) -> ExecResult { - let exec_result = loop { - let interrupt = self.instance.run(); - if let Some(exec_result) = - self.runtime.handle_interrupt(interrupt, &self.module, &mut self.instance) - { - break exec_result - } - }; - let _ = self.runtime.ext().gas_meter_mut().sync_from_executor(self.instance.gas())?; - exec_result - } - - /// The guest memory address at which the aux data is located. - #[cfg(feature = "runtime-benchmarks")] - pub fn aux_data_base(&self) -> u32 { - self.instance.module().memory_map().aux_data_address() - } - - /// Copies `data` to the aux data at address `offset`. - /// - /// It sets `a0` to the beginning of data inside the aux data. - /// It sets `a1` to the value passed. - /// - /// Only used in benchmarking so far. - #[cfg(feature = "runtime-benchmarks")] - pub fn setup_aux_data(&mut self, data: &[u8], offset: u32, a1: u64) -> DispatchResult { - let a0 = self.aux_data_base().saturating_add(offset); - self.instance.write_memory(a0, data).map_err(|err| { - log::debug!(target: LOG_TARGET, "failed to write aux data: {err:?}"); - Error::::CodeRejected - })?; - self.instance.set_reg(polkavm::Reg::A0, a0.into()); - self.instance.set_reg(polkavm::Reg::A1, a1); - Ok(()) - } -} - -impl ContractBlob { - /// Compile and instantiate contract. - /// - /// `aux_data_size` is only used for runtime benchmarks. Real contracts - /// don't make use of this buffer. Hence this should not be set to anything - /// other than `0` when not used for benchmarking. - pub fn prepare_call>( - self, - mut runtime: Runtime, - entry_point: ExportedFunction, - aux_data_size: u32, - ) -> Result, ExecError> { - let mut config = polkavm::Config::default(); - config.set_backend(Some(polkavm::BackendKind::Interpreter)); - config.set_cache_enabled(false); - #[cfg(feature = "std")] - if std::env::var_os("REVIVE_USE_COMPILER").is_some() { - log::warn!(target: LOG_TARGET, "Using PolkaVM compiler backend because env var REVIVE_USE_COMPILER is set"); - config.set_backend(Some(polkavm::BackendKind::Compiler)); - } - let engine = polkavm::Engine::new(&config).expect( - "on-chain (no_std) use of interpreter is hard coded. - interpreter is available on all platforms; qed", - ); - - let mut module_config = polkavm::ModuleConfig::new(); - module_config.set_page_size(limits::PAGE_SIZE); - module_config.set_gas_metering(Some(polkavm::GasMeteringKind::Sync)); - module_config.set_allow_sbrk(false); - module_config.set_aux_data_size(aux_data_size); - let module = polkavm::Module::new(&engine, &module_config, self.code.into_inner().into()) - .map_err(|err| { - log::debug!(target: LOG_TARGET, "failed to create polkavm module: {err:?}"); - Error::::CodeRejected - })?; - - let entry_program_counter = module - .exports() - .find(|export| export.symbol().as_bytes() == entry_point.identifier().as_bytes()) - .ok_or_else(|| >::CodeRejected)? - .program_counter(); - - let gas_limit_polkavm: polkavm::Gas = runtime.ext().gas_meter_mut().engine_fuel_left()?; - - let mut instance = module.instantiate().map_err(|err| { - log::debug!(target: LOG_TARGET, "failed to instantiate polkavm module: {err:?}"); - Error::::CodeRejected - })?; - - instance.set_gas(gas_limit_polkavm); - instance - .set_interpreter_cache_size_limit(Some(polkavm::SetCacheSizeLimitArgs { - max_block_size: limits::code::BASIC_BLOCK_SIZE, - max_cache_size_bytes: limits::code::INTERPRETER_CACHE_BYTES - .try_into() - .map_err(|_| Error::::CodeRejected)?, - })) - .map_err(|_| Error::::CodeRejected)?; - instance.prepare_call_untyped(entry_program_counter, &[]); - - Ok(PreparedCall { module, instance, runtime }) - } -} - impl Executable for ContractBlob where BalanceOf: Into + TryFrom, @@ -414,8 +271,13 @@ where function: ExportedFunction, input_data: Vec, ) -> ExecResult { - let prepared_call = self.prepare_call(Runtime::new(ext, input_data), function, 0)?; - prepared_call.call() + if self.is_pvm() { + let prepared_call = + self.prepare_call(pvm::Runtime::new(ext, input_data), function, 0)?; + prepared_call.call() + } else { + Err(Error::::CodeRejected.into()) + } } fn code(&self) -> &[u8] { diff --git a/substrate/frame/revive/src/vm/pvm.rs b/substrate/frame/revive/src/vm/pvm.rs new file mode 100644 index 0000000000000..b0a2ed8264b24 --- /dev/null +++ b/substrate/frame/revive/src/vm/pvm.rs @@ -0,0 +1,960 @@ +// This file is part of Substrate. + +// Copyright (C) Parity Technologies (UK) Ltd. +// SPDX-License-Identifier: Apache-2.0 + +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +//! Environment definition of the vm smart-contract runtime. + +pub mod env; + +#[cfg(doc)] +pub use env::SyscallDoc; + +use crate::{ + evm::runtime::GAS_PRICE, + exec::{ExecError, ExecResult, Ext, Key}, + gas::ChargedAmount, + limits, + precompiles::{All as AllPrecompiles, Precompiles}, + primitives::ExecReturnValue, + BalanceOf, Config, Error, Pallet, RuntimeCosts, LOG_TARGET, SENTINEL, +}; +use alloc::{vec, vec::Vec}; +use codec::Encode; +use core::{fmt, marker::PhantomData, mem}; +use frame_support::{ensure, weights::Weight}; +use pallet_revive_uapi::{CallFlags, ReturnErrorCode, ReturnFlags, StorageFlags}; +use sp_core::{H160, H256, U256}; +use sp_runtime::{DispatchError, RuntimeDebug}; + +/// Abstraction over the memory access within syscalls. +/// +/// The reason for this abstraction is that we run syscalls on the host machine when +/// benchmarking them. In that case we have direct access to the contract's memory. However, when +/// running within PolkaVM we need to resort to copying as we can't map the contracts memory into +/// the host (as of now). +pub trait Memory { + /// Read designated chunk from the sandbox memory into the supplied buffer. + /// + /// Returns `Err` if one of the following conditions occurs: + /// + /// - requested buffer is not within the bounds of the sandbox memory. + fn read_into_buf(&self, ptr: u32, buf: &mut [u8]) -> Result<(), DispatchError>; + + /// Write the given buffer to the designated location in the sandbox memory. + /// + /// Returns `Err` if one of the following conditions occurs: + /// + /// - designated area is not within the bounds of the sandbox memory. + fn write(&mut self, ptr: u32, buf: &[u8]) -> Result<(), DispatchError>; + + /// Zero the designated location in the sandbox memory. + /// + /// Returns `Err` if one of the following conditions occurs: + /// + /// - designated area is not within the bounds of the sandbox memory. + fn zero(&mut self, ptr: u32, len: u32) -> Result<(), DispatchError>; + + /// This will reset all compilation artifacts of the currently executing instance. + /// + /// This is used before we call into a new contract to free up some memory. Doing + /// so we make sure that we only ever have to hold one compilation cache at a time + /// independtently of of our call stack depth. + fn reset_interpreter_cache(&mut self); + + /// Read designated chunk from the sandbox memory. + /// + /// Returns `Err` if one of the following conditions occurs: + /// + /// - requested buffer is not within the bounds of the sandbox memory. + fn read(&self, ptr: u32, len: u32) -> Result, DispatchError> { + let mut buf = vec![0u8; len as usize]; + self.read_into_buf(ptr, buf.as_mut_slice())?; + Ok(buf) + } + + /// Same as `read` but reads into a fixed size buffer. + fn read_array(&self, ptr: u32) -> Result<[u8; N], DispatchError> { + let mut buf = [0u8; N]; + self.read_into_buf(ptr, &mut buf)?; + Ok(buf) + } + + /// Read a `u32` from the sandbox memory. + fn read_u32(&self, ptr: u32) -> Result { + let buf: [u8; 4] = self.read_array(ptr)?; + Ok(u32::from_le_bytes(buf)) + } + + /// Read a `U256` from the sandbox memory. + fn read_u256(&self, ptr: u32) -> Result { + let buf: [u8; 32] = self.read_array(ptr)?; + Ok(U256::from_little_endian(&buf)) + } + + /// Read a `H160` from the sandbox memory. + fn read_h160(&self, ptr: u32) -> Result { + let mut buf = H160::default(); + self.read_into_buf(ptr, buf.as_bytes_mut())?; + Ok(buf) + } + + /// Read a `H256` from the sandbox memory. + fn read_h256(&self, ptr: u32) -> Result { + let mut code_hash = H256::default(); + self.read_into_buf(ptr, code_hash.as_bytes_mut())?; + Ok(code_hash) + } +} + +/// Allows syscalls access to the PolkaVM instance they are executing in. +/// +/// In case a contract is executing within PolkaVM its `memory` argument will also implement +/// this trait. The benchmarking implementation of syscalls will only require `Memory` +/// to be implemented. +pub trait PolkaVmInstance: Memory { + fn gas(&self) -> polkavm::Gas; + fn set_gas(&mut self, gas: polkavm::Gas); + fn read_input_regs(&self) -> (u64, u64, u64, u64, u64, u64); + fn write_output(&mut self, output: u64); +} + +// Memory implementation used in benchmarking where guest memory is mapped into the host. +// +// Please note that we could optimize the `read_as_*` functions by decoding directly from +// memory without a copy. However, we don't do that because as it would change the behaviour +// of those functions: A `read_as` with a `len` larger than the actual type can succeed +// in the streaming implementation while it could fail with a segfault in the copy implementation. +#[cfg(feature = "runtime-benchmarks")] +impl Memory for [u8] { + fn read_into_buf(&self, ptr: u32, buf: &mut [u8]) -> Result<(), DispatchError> { + let ptr = ptr as usize; + let bound_checked = + self.get(ptr..ptr + buf.len()).ok_or_else(|| Error::::OutOfBounds)?; + buf.copy_from_slice(bound_checked); + Ok(()) + } + + fn write(&mut self, ptr: u32, buf: &[u8]) -> Result<(), DispatchError> { + let ptr = ptr as usize; + let bound_checked = + self.get_mut(ptr..ptr + buf.len()).ok_or_else(|| Error::::OutOfBounds)?; + bound_checked.copy_from_slice(buf); + Ok(()) + } + + fn zero(&mut self, ptr: u32, len: u32) -> Result<(), DispatchError> { + <[u8] as Memory>::write(self, ptr, &vec![0; len as usize]) + } + + fn reset_interpreter_cache(&mut self) {} +} + +impl Memory for polkavm::RawInstance { + fn read_into_buf(&self, ptr: u32, buf: &mut [u8]) -> Result<(), DispatchError> { + self.read_memory_into(ptr, buf) + .map(|_| ()) + .map_err(|_| Error::::OutOfBounds.into()) + } + + fn write(&mut self, ptr: u32, buf: &[u8]) -> Result<(), DispatchError> { + self.write_memory(ptr, buf).map_err(|_| Error::::OutOfBounds.into()) + } + + fn zero(&mut self, ptr: u32, len: u32) -> Result<(), DispatchError> { + self.zero_memory(ptr, len).map_err(|_| Error::::OutOfBounds.into()) + } + + fn reset_interpreter_cache(&mut self) { + self.reset_interpreter_cache(); + } +} + +impl PolkaVmInstance for polkavm::RawInstance { + fn gas(&self) -> polkavm::Gas { + self.gas() + } + + fn set_gas(&mut self, gas: polkavm::Gas) { + self.set_gas(gas) + } + + fn read_input_regs(&self) -> (u64, u64, u64, u64, u64, u64) { + ( + self.reg(polkavm::Reg::A0), + self.reg(polkavm::Reg::A1), + self.reg(polkavm::Reg::A2), + self.reg(polkavm::Reg::A3), + self.reg(polkavm::Reg::A4), + self.reg(polkavm::Reg::A5), + ) + } + + fn write_output(&mut self, output: u64) { + self.set_reg(polkavm::Reg::A0, output); + } +} + +impl From<&ExecReturnValue> for ReturnErrorCode { + fn from(from: &ExecReturnValue) -> Self { + if from.flags.contains(ReturnFlags::REVERT) { + Self::CalleeReverted + } else { + Self::Success + } + } +} + +/// The data passed through when a contract uses `seal_return`. +#[derive(RuntimeDebug)] +pub struct ReturnData { + /// The flags as passed through by the contract. They are still unchecked and + /// will later be parsed into a `ReturnFlags` bitflags struct. + flags: u32, + /// The output buffer passed by the contract as return data. + data: Vec, +} + +/// Enumerates all possible reasons why a trap was generated. +/// +/// This is either used to supply the caller with more information about why an error +/// occurred (the SupervisorError variant). +/// The other case is where the trap does not constitute an error but rather was invoked +/// as a quick way to terminate the application (all other variants). +#[derive(RuntimeDebug)] +pub enum TrapReason { + /// The supervisor trapped the contract because of an error condition occurred during + /// execution in privileged code. + SupervisorError(DispatchError), + /// Signals that trap was generated in response to call `seal_return` host function. + Return(ReturnData), + /// Signals that a trap was generated in response to a successful call to the + /// `seal_terminate` host function. + Termination, +} + +impl> From for TrapReason { + fn from(from: T) -> Self { + Self::SupervisorError(from.into()) + } +} + +impl fmt::Display for TrapReason { + fn fmt(&self, _f: &mut fmt::Formatter<'_>) -> Result<(), fmt::Error> { + Ok(()) + } +} + +/// Same as [`Runtime::charge_gas`]. +/// +/// We need this access as a macro because sometimes hiding the lifetimes behind +/// a function won't work out. +macro_rules! charge_gas { + ($runtime:expr, $costs:expr) => {{ + $runtime.ext.gas_meter_mut().charge($costs) + }}; +} + +/// The kind of call that should be performed. +enum CallType { + /// Execute another instantiated contract + Call { value_ptr: u32 }, + /// Execute another contract code in the context (storage, account ID, value) of the caller + /// contract + DelegateCall, +} + +impl CallType { + fn cost(&self) -> RuntimeCosts { + match self { + CallType::Call { .. } => RuntimeCosts::CallBase, + CallType::DelegateCall => RuntimeCosts::DelegateCallBase, + } + } +} + +/// This is only appropriate when writing out data of constant size that does not depend on user +/// input. In this case the costs for this copy was already charged as part of the token at +/// the beginning of the API entry point. +fn already_charged(_: u32) -> Option { + None +} + +/// Helper to extract two `u32` values from a given `u64` register. +fn extract_hi_lo(reg: u64) -> (u32, u32) { + ((reg >> 32) as u32, reg as u32) +} + +/// Provides storage variants to support standard and Etheruem compatible semantics. +enum StorageValue { + /// Indicates that the storage value should be read from a memory buffer. + /// - `ptr`: A pointer to the start of the data in sandbox memory. + /// - `len`: The length (in bytes) of the data. + Memory { ptr: u32, len: u32 }, + + /// Indicates that the storage value is provided inline as a fixed-size (256-bit) value. + /// This is used by set_storage_or_clear() to avoid double reads. + /// This variant is used to implement Ethereum SSTORE-like semantics. + Value(Vec), +} + +/// Controls the output behavior for storage reads, both when a key is found and when it is not. +enum StorageReadMode { + /// VariableOutput mode: if the key exists, the full stored value is returned + /// using the caller‑provided output length. + VariableOutput { output_len_ptr: u32 }, + /// Ethereum compatible(FixedOutput32) mode: always write a 32-byte value into the output + /// buffer. If the key is missing, write 32 bytes of zeros. + FixedOutput32, +} + +/// Can only be used for one call. +pub struct Runtime<'a, E: Ext, M: ?Sized> { + ext: &'a mut E, + input_data: Option>, + _phantom_data: PhantomData, +} + +impl<'a, E: Ext, M: ?Sized + Memory> Runtime<'a, E, M> { + pub fn new(ext: &'a mut E, input_data: Vec) -> Self { + Self { ext, input_data: Some(input_data), _phantom_data: Default::default() } + } + + /// Get a mutable reference to the inner `Ext`. + pub fn ext(&mut self) -> &mut E { + self.ext + } + + /// Charge the gas meter with the specified token. + /// + /// Returns `Err(HostError)` if there is not enough gas. + fn charge_gas(&mut self, costs: RuntimeCosts) -> Result { + charge_gas!(self, costs) + } + + /// Adjust a previously charged amount down to its actual amount. + /// + /// This is when a maximum a priori amount was charged and then should be partially + /// refunded to match the actual amount. + fn adjust_gas(&mut self, charged: ChargedAmount, actual_costs: RuntimeCosts) { + self.ext.gas_meter_mut().adjust_gas(charged, actual_costs); + } + + /// Write the given buffer and its length to the designated locations in sandbox memory and + /// charge gas according to the token returned by `create_token`. + /// + /// `out_ptr` is the location in sandbox memory where `buf` should be written to. + /// `out_len_ptr` is an in-out location in sandbox memory. It is read to determine the + /// length of the buffer located at `out_ptr`. If that buffer is smaller than the actual + /// `buf.len()`, only what fits into that buffer is written to `out_ptr`. + /// The actual amount of bytes copied to `out_ptr` is written to `out_len_ptr`. + /// + /// If `out_ptr` is set to the sentinel value of `SENTINEL` and `allow_skip` is true the + /// operation is skipped and `Ok` is returned. This is supposed to help callers to make copying + /// output optional. For example to skip copying back the output buffer of an `seal_call` + /// when the caller is not interested in the result. + /// + /// `create_token` can optionally instruct this function to charge the gas meter with the token + /// it returns. `create_token` receives the variable amount of bytes that are about to be copied + /// by this function. + /// + /// In addition to the error conditions of `Memory::write` this functions returns + /// `Err` if the size of the buffer located at `out_ptr` is too small to fit `buf`. + pub fn write_sandbox_output( + &mut self, + memory: &mut M, + out_ptr: u32, + out_len_ptr: u32, + buf: &[u8], + allow_skip: bool, + create_token: impl FnOnce(u32) -> Option, + ) -> Result<(), DispatchError> { + if allow_skip && out_ptr == SENTINEL { + return Ok(()); + } + + let len = memory.read_u32(out_len_ptr)?; + let buf_len = len.min(buf.len() as u32); + + if let Some(costs) = create_token(buf_len) { + self.charge_gas(costs)?; + } + + memory.write(out_ptr, &buf[..buf_len as usize])?; + memory.write(out_len_ptr, &buf_len.encode()) + } + + /// Same as `write_sandbox_output` but for static size output. + pub fn write_fixed_sandbox_output( + &mut self, + memory: &mut M, + out_ptr: u32, + buf: &[u8], + allow_skip: bool, + create_token: impl FnOnce(u32) -> Option, + ) -> Result<(), DispatchError> { + if buf.is_empty() || (allow_skip && out_ptr == SENTINEL) { + return Ok(()); + } + + let buf_len = buf.len() as u32; + if let Some(costs) = create_token(buf_len) { + self.charge_gas(costs)?; + } + + memory.write(out_ptr, buf) + } + + /// Computes the given hash function on the supplied input. + /// + /// Reads from the sandboxed input buffer into an intermediate buffer. + /// Returns the result directly to the output buffer of the sandboxed memory. + /// + /// It is the callers responsibility to provide an output buffer that + /// is large enough to hold the expected amount of bytes returned by the + /// chosen hash function. + /// + /// # Note + /// + /// The `input` and `output` buffers may overlap. + fn compute_hash_on_intermediate_buffer( + &self, + memory: &mut M, + hash_fn: F, + input_ptr: u32, + input_len: u32, + output_ptr: u32, + ) -> Result<(), DispatchError> + where + F: FnOnce(&[u8]) -> R, + R: AsRef<[u8]>, + { + // Copy input into supervisor memory. + let input = memory.read(input_ptr, input_len)?; + // Compute the hash on the input buffer using the given hash function. + let hash = hash_fn(&input); + // Write the resulting hash back into the sandboxed output buffer. + memory.write(output_ptr, hash.as_ref())?; + Ok(()) + } + + /// Fallible conversion of a `ExecError` to `ReturnErrorCode`. + /// + /// This is used when converting the error returned from a subcall in order to decide + /// whether to trap the caller or allow handling of the error. + fn exec_error_into_return_code(from: ExecError) -> Result { + use crate::exec::ErrorOrigin::Callee; + use ReturnErrorCode::*; + + let transfer_failed = Error::::TransferFailed.into(); + let out_of_gas = Error::::OutOfGas.into(); + let out_of_deposit = Error::::StorageDepositLimitExhausted.into(); + let duplicate_contract = Error::::DuplicateContract.into(); + let unsupported_precompile = Error::::UnsupportedPrecompileAddress.into(); + + // errors in the callee do not trap the caller + match (from.error, from.origin) { + (err, _) if err == transfer_failed => Ok(TransferFailed), + (err, _) if err == duplicate_contract => Ok(DuplicateContractAddress), + (err, _) if err == unsupported_precompile => Err(err), + (err, Callee) if err == out_of_gas || err == out_of_deposit => Ok(OutOfResources), + (_, Callee) => Ok(CalleeTrapped), + (err, _) => Err(err), + } + } + + fn decode_key(&self, memory: &M, key_ptr: u32, key_len: u32) -> Result { + let res = match key_len { + SENTINEL => { + let mut buffer = [0u8; 32]; + memory.read_into_buf(key_ptr, buffer.as_mut())?; + Ok(Key::from_fixed(buffer)) + }, + len => { + ensure!(len <= limits::STORAGE_KEY_BYTES, Error::::DecodingFailed); + let key = memory.read(key_ptr, len)?; + Key::try_from_var(key) + }, + }; + + res.map_err(|_| Error::::DecodingFailed.into()) + } + + fn is_transient(flags: u32) -> Result { + StorageFlags::from_bits(flags) + .ok_or_else(|| >::InvalidStorageFlags.into()) + .map(|flags| flags.contains(StorageFlags::TRANSIENT)) + } + + fn set_storage( + &mut self, + memory: &M, + flags: u32, + key_ptr: u32, + key_len: u32, + value: StorageValue, + ) -> Result { + let transient = Self::is_transient(flags)?; + let costs = |new_bytes: u32, old_bytes: u32| { + if transient { + RuntimeCosts::SetTransientStorage { new_bytes, old_bytes } + } else { + RuntimeCosts::SetStorage { new_bytes, old_bytes } + } + }; + + let value_len = match &value { + StorageValue::Memory { ptr: _, len } => *len, + StorageValue::Value(data) => data.len() as u32, + }; + + let max_size = self.ext.max_value_size(); + let charged = self.charge_gas(costs(value_len, self.ext.max_value_size()))?; + if value_len > max_size { + return Err(Error::::ValueTooLarge.into()); + } + + let key = self.decode_key(memory, key_ptr, key_len)?; + + let value = match value { + StorageValue::Memory { ptr, len } => Some(memory.read(ptr, len)?), + StorageValue::Value(data) => Some(data), + }; + + let write_outcome = if transient { + self.ext.set_transient_storage(&key, value, false)? + } else { + self.ext.set_storage(&key, value, false)? + }; + + self.adjust_gas(charged, costs(value_len, write_outcome.old_len())); + Ok(write_outcome.old_len_with_sentinel()) + } + + fn clear_storage( + &mut self, + memory: &M, + flags: u32, + key_ptr: u32, + key_len: u32, + ) -> Result { + let transient = Self::is_transient(flags)?; + let costs = |len| { + if transient { + RuntimeCosts::ClearTransientStorage(len) + } else { + RuntimeCosts::ClearStorage(len) + } + }; + let charged = self.charge_gas(costs(self.ext.max_value_size()))?; + let key = self.decode_key(memory, key_ptr, key_len)?; + let outcome = if transient { + self.ext.set_transient_storage(&key, None, false)? + } else { + self.ext.set_storage(&key, None, false)? + }; + self.adjust_gas(charged, costs(outcome.old_len())); + Ok(outcome.old_len_with_sentinel()) + } + + fn get_storage( + &mut self, + memory: &mut M, + flags: u32, + key_ptr: u32, + key_len: u32, + out_ptr: u32, + read_mode: StorageReadMode, + ) -> Result { + let transient = Self::is_transient(flags)?; + let costs = |len| { + if transient { + RuntimeCosts::GetTransientStorage(len) + } else { + RuntimeCosts::GetStorage(len) + } + }; + let charged = self.charge_gas(costs(self.ext.max_value_size()))?; + let key = self.decode_key(memory, key_ptr, key_len)?; + let outcome = if transient { + self.ext.get_transient_storage(&key) + } else { + self.ext.get_storage(&key) + }; + + if let Some(value) = outcome { + self.adjust_gas(charged, costs(value.len() as u32)); + + match read_mode { + StorageReadMode::FixedOutput32 => { + let mut fixed_output = [0u8; 32]; + let len = value.len().min(fixed_output.len()); + fixed_output[..len].copy_from_slice(&value[..len]); + + self.write_fixed_sandbox_output( + memory, + out_ptr, + &fixed_output, + false, + already_charged, + )?; + Ok(ReturnErrorCode::Success) + }, + StorageReadMode::VariableOutput { output_len_ptr: out_len_ptr } => { + self.write_sandbox_output( + memory, + out_ptr, + out_len_ptr, + &value, + false, + already_charged, + )?; + Ok(ReturnErrorCode::Success) + }, + } + } else { + self.adjust_gas(charged, costs(0)); + + match read_mode { + StorageReadMode::FixedOutput32 => { + self.write_fixed_sandbox_output( + memory, + out_ptr, + &[0u8; 32], + false, + already_charged, + )?; + Ok(ReturnErrorCode::Success) + }, + StorageReadMode::VariableOutput { .. } => Ok(ReturnErrorCode::KeyNotFound), + } + } + } + + fn contains_storage( + &mut self, + memory: &M, + flags: u32, + key_ptr: u32, + key_len: u32, + ) -> Result { + let transient = Self::is_transient(flags)?; + let costs = |len| { + if transient { + RuntimeCosts::ContainsTransientStorage(len) + } else { + RuntimeCosts::ContainsStorage(len) + } + }; + let charged = self.charge_gas(costs(self.ext.max_value_size()))?; + let key = self.decode_key(memory, key_ptr, key_len)?; + let outcome = if transient { + self.ext.get_transient_storage_size(&key) + } else { + self.ext.get_storage_size(&key) + }; + self.adjust_gas(charged, costs(outcome.unwrap_or(0))); + Ok(outcome.unwrap_or(SENTINEL)) + } + + fn take_storage( + &mut self, + memory: &mut M, + flags: u32, + key_ptr: u32, + key_len: u32, + out_ptr: u32, + out_len_ptr: u32, + ) -> Result { + let transient = Self::is_transient(flags)?; + let costs = |len| { + if transient { + RuntimeCosts::TakeTransientStorage(len) + } else { + RuntimeCosts::TakeStorage(len) + } + }; + let charged = self.charge_gas(costs(self.ext.max_value_size()))?; + let key = self.decode_key(memory, key_ptr, key_len)?; + let outcome = if transient { + self.ext.set_transient_storage(&key, None, true)? + } else { + self.ext.set_storage(&key, None, true)? + }; + + if let crate::storage::WriteOutcome::Taken(value) = outcome { + self.adjust_gas(charged, costs(value.len() as u32)); + self.write_sandbox_output( + memory, + out_ptr, + out_len_ptr, + &value, + false, + already_charged, + )?; + Ok(ReturnErrorCode::Success) + } else { + self.adjust_gas(charged, costs(0)); + Ok(ReturnErrorCode::KeyNotFound) + } + } + + fn call( + &mut self, + memory: &mut M, + flags: CallFlags, + call_type: CallType, + callee_ptr: u32, + deposit_ptr: u32, + weight: Weight, + input_data_ptr: u32, + input_data_len: u32, + output_ptr: u32, + output_len_ptr: u32, + ) -> Result { + let callee = memory.read_h160(callee_ptr)?; + let precompile = >::get::(&callee.as_fixed_bytes()); + match &precompile { + Some(precompile) if precompile.has_contract_info() => + self.charge_gas(RuntimeCosts::PrecompileWithInfoBase)?, + Some(_) => self.charge_gas(RuntimeCosts::PrecompileBase)?, + None => self.charge_gas(call_type.cost())?, + }; + + let deposit_limit = memory.read_u256(deposit_ptr)?; + + // we do check this in exec.rs but we want to error out early + if input_data_len > limits::CALLDATA_BYTES { + Err(>::CallDataTooLarge)?; + } + + let input_data = if flags.contains(CallFlags::CLONE_INPUT) { + let input = self.input_data.as_ref().ok_or(Error::::InputForwarded)?; + charge_gas!(self, RuntimeCosts::CallInputCloned(input.len() as u32))?; + input.clone() + } else if flags.contains(CallFlags::FORWARD_INPUT) { + self.input_data.take().ok_or(Error::::InputForwarded)? + } else { + if precompile.is_some() { + self.charge_gas(RuntimeCosts::PrecompileDecode(input_data_len))?; + } else { + self.charge_gas(RuntimeCosts::CopyFromContract(input_data_len))?; + } + memory.read(input_data_ptr, input_data_len)? + }; + + memory.reset_interpreter_cache(); + + let call_outcome = match call_type { + CallType::Call { value_ptr } => { + let read_only = flags.contains(CallFlags::READ_ONLY); + let value = memory.read_u256(value_ptr)?; + if value > 0u32.into() { + // If the call value is non-zero and state change is not allowed, issue an + // error. + if read_only || self.ext.is_read_only() { + return Err(Error::::StateChangeDenied.into()); + } + + self.charge_gas(RuntimeCosts::CallTransferSurcharge { + dust_transfer: Pallet::::has_dust(value), + })?; + } + self.ext.call( + weight, + deposit_limit, + &callee, + value, + input_data, + flags.contains(CallFlags::ALLOW_REENTRY), + read_only, + ) + }, + CallType::DelegateCall => { + if flags.intersects(CallFlags::ALLOW_REENTRY | CallFlags::READ_ONLY) { + return Err(Error::::InvalidCallFlags.into()); + } + self.ext.delegate_call(weight, deposit_limit, callee, input_data) + }, + }; + + match call_outcome { + // `TAIL_CALL` only matters on an `OK` result. Otherwise the call stack comes to + // a halt anyways without anymore code being executed. + Ok(_) if flags.contains(CallFlags::TAIL_CALL) => { + let output = mem::take(self.ext.last_frame_output_mut()); + return Err(TrapReason::Return(ReturnData { + flags: output.flags.bits(), + data: output.data, + })); + }, + Ok(_) => { + let output = mem::take(self.ext.last_frame_output_mut()); + let write_result = self.write_sandbox_output( + memory, + output_ptr, + output_len_ptr, + &output.data, + true, + |len| Some(RuntimeCosts::CopyToContract(len)), + ); + *self.ext.last_frame_output_mut() = output; + write_result?; + Ok(self.ext.last_frame_output().into()) + }, + Err(err) => { + let error_code = Self::exec_error_into_return_code(err)?; + memory.write(output_len_ptr, &0u32.to_le_bytes())?; + Ok(error_code) + }, + } + } + + fn instantiate( + &mut self, + memory: &mut M, + code_hash_ptr: u32, + weight: Weight, + deposit_ptr: u32, + value_ptr: u32, + input_data_ptr: u32, + input_data_len: u32, + address_ptr: u32, + output_ptr: u32, + output_len_ptr: u32, + salt_ptr: u32, + ) -> Result { + let value = match memory.read_u256(value_ptr) { + Ok(value) => { + self.charge_gas(RuntimeCosts::Instantiate { + input_data_len, + balance_transfer: Pallet::::has_balance(value), + dust_transfer: Pallet::::has_dust(value), + })?; + value + }, + Err(err) => { + self.charge_gas(RuntimeCosts::Instantiate { + input_data_len: 0, + balance_transfer: false, + dust_transfer: false, + })?; + return Err(err.into()); + }, + }; + let deposit_limit: U256 = memory.read_u256(deposit_ptr)?; + let code_hash = memory.read_h256(code_hash_ptr)?; + if input_data_len > limits::CALLDATA_BYTES { + Err(>::CallDataTooLarge)?; + } + let input_data = memory.read(input_data_ptr, input_data_len)?; + let salt = if salt_ptr == SENTINEL { + None + } else { + let salt: [u8; 32] = memory.read_array(salt_ptr)?; + Some(salt) + }; + + memory.reset_interpreter_cache(); + + match self.ext.instantiate( + weight, + deposit_limit, + code_hash, + value, + input_data, + salt.as_ref(), + ) { + Ok(address) => { + if !self.ext.last_frame_output().flags.contains(ReturnFlags::REVERT) { + self.write_fixed_sandbox_output( + memory, + address_ptr, + &address.as_bytes(), + true, + already_charged, + )?; + } + let output = mem::take(self.ext.last_frame_output_mut()); + let write_result = self.write_sandbox_output( + memory, + output_ptr, + output_len_ptr, + &output.data, + true, + |len| Some(RuntimeCosts::CopyToContract(len)), + ); + *self.ext.last_frame_output_mut() = output; + write_result?; + Ok(self.ext.last_frame_output().into()) + }, + Err(err) => Ok(Self::exec_error_into_return_code(err)?), + } + } +} + +pub struct PreparedCall<'a, E: Ext> { + module: polkavm::Module, + instance: polkavm::RawInstance, + runtime: Runtime<'a, E, polkavm::RawInstance>, +} + +impl<'a, E: Ext> PreparedCall<'a, E> +where + BalanceOf: Into, + BalanceOf: TryFrom, +{ + pub fn call(mut self) -> ExecResult { + let exec_result = loop { + let interrupt = self.instance.run(); + if let Some(exec_result) = + self.runtime.handle_interrupt(interrupt, &self.module, &mut self.instance) + { + break exec_result + } + }; + let _ = self.runtime.ext().gas_meter_mut().sync_from_executor(self.instance.gas())?; + exec_result + } + + /// The guest memory address at which the aux data is located. + #[cfg(feature = "runtime-benchmarks")] + pub fn aux_data_base(&self) -> u32 { + self.instance.module().memory_map().aux_data_address() + } + + /// Copies `data` to the aux data at address `offset`. + /// + /// It sets `a0` to the beginning of data inside the aux data. + /// It sets `a1` to the value passed. + /// + /// Only used in benchmarking so far. + #[cfg(feature = "runtime-benchmarks")] + pub fn setup_aux_data( + &mut self, + data: &[u8], + offset: u32, + a1: u64, + ) -> frame_support::dispatch::DispatchResult { + let a0 = self.aux_data_base().saturating_add(offset); + self.instance.write_memory(a0, data).map_err(|err| { + log::debug!(target: LOG_TARGET, "failed to write aux data: {err:?}"); + Error::::CodeRejected + })?; + self.instance.set_reg(polkavm::Reg::A0, a0.into()); + self.instance.set_reg(polkavm::Reg::A1, a1); + Ok(()) + } +} diff --git a/substrate/frame/revive/src/vm/pvm/env.rs b/substrate/frame/revive/src/vm/pvm/env.rs new file mode 100644 index 0000000000000..0255670a4f529 --- /dev/null +++ b/substrate/frame/revive/src/vm/pvm/env.rs @@ -0,0 +1,1037 @@ +// This file is part of Substrate. + +// Copyright (C) Parity Technologies (UK) Ltd. +// SPDX-License-Identifier: Apache-2.0 + +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +use super::*; + +use crate::{ + address::AddressMapper, + exec::Ext, + limits, + primitives::ExecReturnValue, + storage::meter::Diff, + vm::{ExportedFunction, RuntimeCosts}, + AccountIdOf, BalanceOf, CodeInfo, Config, ContractBlob, Error, Weight, SENTINEL, +}; +use alloc::vec::Vec; +use codec::{Encode, MaxEncodedLen}; +use core::mem; +use frame_support::traits::Get; +use pallet_revive_proc_macro::define_env; +use pallet_revive_uapi::{CallFlags, ReturnErrorCode, ReturnFlags}; +use sp_core::{H160, H256, U256}; +use sp_io::hashing::keccak_256; +use sp_runtime::DispatchError; + +impl ContractBlob { + /// Compile and instantiate contract. + /// + /// `aux_data_size` is only used for runtime benchmarks. Real contracts + /// don't make use of this buffer. Hence this should not be set to anything + /// other than `0` when not used for benchmarking. + pub fn prepare_call>( + self, + mut runtime: Runtime, + entry_point: ExportedFunction, + aux_data_size: u32, + ) -> Result, ExecError> { + let mut config = polkavm::Config::default(); + config.set_backend(Some(polkavm::BackendKind::Interpreter)); + config.set_cache_enabled(false); + #[cfg(feature = "std")] + if std::env::var_os("REVIVE_USE_COMPILER").is_some() { + log::warn!(target: LOG_TARGET, "Using PolkaVM compiler backend because env var REVIVE_USE_COMPILER is set"); + config.set_backend(Some(polkavm::BackendKind::Compiler)); + } + let engine = polkavm::Engine::new(&config).expect( + "on-chain (no_std) use of interpreter is hard coded. + interpreter is available on all platforms; qed", + ); + + let mut module_config = polkavm::ModuleConfig::new(); + module_config.set_page_size(limits::PAGE_SIZE); + module_config.set_gas_metering(Some(polkavm::GasMeteringKind::Sync)); + module_config.set_allow_sbrk(false); + module_config.set_aux_data_size(aux_data_size); + let module = polkavm::Module::new(&engine, &module_config, self.code.into_inner().into()) + .map_err(|err| { + log::debug!(target: LOG_TARGET, "failed to create polkavm module: {err:?}"); + Error::::CodeRejected + })?; + + let entry_program_counter = module + .exports() + .find(|export| export.symbol().as_bytes() == entry_point.identifier().as_bytes()) + .ok_or_else(|| >::CodeRejected)? + .program_counter(); + + let gas_limit_polkavm: polkavm::Gas = runtime.ext().gas_meter_mut().engine_fuel_left()?; + + let mut instance = module.instantiate().map_err(|err| { + log::debug!(target: LOG_TARGET, "failed to instantiate polkavm module: {err:?}"); + Error::::CodeRejected + })?; + + instance.set_gas(gas_limit_polkavm); + instance + .set_interpreter_cache_size_limit(Some(polkavm::SetCacheSizeLimitArgs { + max_block_size: limits::code::BASIC_BLOCK_SIZE, + max_cache_size_bytes: limits::code::INTERPRETER_CACHE_BYTES + .try_into() + .map_err(|_| Error::::CodeRejected)?, + })) + .map_err(|_| Error::::CodeRejected)?; + instance.prepare_call_untyped(entry_program_counter, &[]); + + Ok(PreparedCall { module, instance, runtime }) + } +} + +impl ContractBlob +where + BalanceOf: Into + TryFrom, +{ + /// We only check for size and nothing else when the code is uploaded. + pub fn from_pvm_code(code: Vec, owner: AccountIdOf) -> Result { + // We do validation only when new code is deployed. This allows us to increase + // the limits later without affecting already deployed code. + let available_syscalls = list_syscalls(T::UnsafeUnstableInterface::get()); + let code = limits::code::enforce::(code, available_syscalls)?; + + let code_len = code.len() as u32; + let bytes_added = code_len.saturating_add(>::max_encoded_len() as u32); + let deposit = Diff { bytes_added, items_added: 2, ..Default::default() } + .update_contract::(None) + .charge_or_zero(); + let code_info = CodeInfo { + owner, + deposit, + refcount: 0, + code_len, + behaviour_version: Default::default(), + }; + let code_hash = H256(sp_io::hashing::keccak_256(&code)); + Ok(ContractBlob { code, code_info, code_hash }) + } +} + +impl<'a, E: Ext, M: PolkaVmInstance> Runtime<'a, E, M> { + pub fn handle_interrupt( + &mut self, + interrupt: Result, + module: &polkavm::Module, + instance: &mut M, + ) -> Option { + use polkavm::InterruptKind::*; + + match interrupt { + Err(error) => { + // in contrast to the other returns this "should" not happen: log level error + log::error!(target: LOG_TARGET, "polkavm execution error: {error}"); + Some(Err(Error::::ExecutionFailed.into())) + }, + Ok(Finished) => + Some(Ok(ExecReturnValue { flags: ReturnFlags::empty(), data: Vec::new() })), + Ok(Trap) => Some(Err(Error::::ContractTrapped.into())), + Ok(Segfault(_)) => Some(Err(Error::::ExecutionFailed.into())), + Ok(NotEnoughGas) => Some(Err(Error::::OutOfGas.into())), + Ok(Step) => None, + Ok(Ecalli(idx)) => { + // This is a special hard coded syscall index which is used by benchmarks + // to abort contract execution. It is used to terminate the execution without + // breaking up a basic block. The fixed index is used so that the benchmarks + // don't have to deal with import tables. + if cfg!(feature = "runtime-benchmarks") && idx == SENTINEL { + return Some(Ok(ExecReturnValue { + flags: ReturnFlags::empty(), + data: Vec::new(), + })) + } + let Some(syscall_symbol) = module.imports().get(idx) else { + return Some(Err(>::InvalidSyscall.into())); + }; + match self.handle_ecall(instance, syscall_symbol.as_bytes()) { + Ok(None) => None, + Ok(Some(return_value)) => { + instance.write_output(return_value); + None + }, + Err(TrapReason::Return(ReturnData { flags, data })) => + match ReturnFlags::from_bits(flags) { + None => Some(Err(Error::::InvalidCallFlags.into())), + Some(flags) => Some(Ok(ExecReturnValue { flags, data })), + }, + Err(TrapReason::Termination) => Some(Ok(Default::default())), + Err(TrapReason::SupervisorError(error)) => Some(Err(error.into())), + } + }, + } + } +} + +// This is the API exposed to contracts. +// +// # Note +// +// Any input that leads to a out of bound error (reading or writing) or failing to decode +// data passed to the supervisor will lead to a trap. This is not documented explicitly +// for every function. +#[define_env] +pub mod env { + /// Noop function used to benchmark the time it takes to execute an empty function. + /// + /// Marked as stable because it needs to be called from benchmarks even when the benchmarked + /// parachain has unstable functions disabled. + #[cfg(feature = "runtime-benchmarks")] + #[stable] + fn noop(&mut self, memory: &mut M) -> Result<(), TrapReason> { + Ok(()) + } + + /// Set the value at the given key in the contract storage. + /// See [`pallet_revive_uapi::HostFn::set_storage_v2`] + #[stable] + #[mutating] + fn set_storage( + &mut self, + memory: &mut M, + flags: u32, + key_ptr: u32, + key_len: u32, + value_ptr: u32, + value_len: u32, + ) -> Result { + self.set_storage( + memory, + flags, + key_ptr, + key_len, + StorageValue::Memory { ptr: value_ptr, len: value_len }, + ) + } + + /// Sets the storage at a fixed 256-bit key with a fixed 256-bit value. + /// See [`pallet_revive_uapi::HostFn::set_storage_or_clear`]. + #[stable] + #[mutating] + fn set_storage_or_clear( + &mut self, + memory: &mut M, + flags: u32, + key_ptr: u32, + value_ptr: u32, + ) -> Result { + let value = memory.read(value_ptr, 32)?; + + if value.iter().all(|&b| b == 0) { + self.clear_storage(memory, flags, key_ptr, SENTINEL) + } else { + self.set_storage(memory, flags, key_ptr, SENTINEL, StorageValue::Value(value)) + } + } + + /// Retrieve the value under the given key from storage. + /// See [`pallet_revive_uapi::HostFn::get_storage`] + #[stable] + fn get_storage( + &mut self, + memory: &mut M, + flags: u32, + key_ptr: u32, + key_len: u32, + out_ptr: u32, + out_len_ptr: u32, + ) -> Result { + self.get_storage( + memory, + flags, + key_ptr, + key_len, + out_ptr, + StorageReadMode::VariableOutput { output_len_ptr: out_len_ptr }, + ) + } + + /// Reads the storage at a fixed 256-bit key and writes back a fixed 256-bit value. + /// See [`pallet_revive_uapi::HostFn::get_storage_or_zero`]. + #[stable] + fn get_storage_or_zero( + &mut self, + memory: &mut M, + flags: u32, + key_ptr: u32, + out_ptr: u32, + ) -> Result<(), TrapReason> { + let _ = self.get_storage( + memory, + flags, + key_ptr, + SENTINEL, + out_ptr, + StorageReadMode::FixedOutput32, + )?; + + Ok(()) + } + + /// Make a call to another contract. + /// See [`pallet_revive_uapi::HostFn::call`]. + #[stable] + fn call( + &mut self, + memory: &mut M, + flags_and_callee: u64, + ref_time_limit: u64, + proof_size_limit: u64, + deposit_and_value: u64, + input_data: u64, + output_data: u64, + ) -> Result { + let (flags, callee_ptr) = extract_hi_lo(flags_and_callee); + let (deposit_ptr, value_ptr) = extract_hi_lo(deposit_and_value); + let (input_data_len, input_data_ptr) = extract_hi_lo(input_data); + let (output_len_ptr, output_ptr) = extract_hi_lo(output_data); + + self.call( + memory, + CallFlags::from_bits(flags).ok_or(Error::::InvalidCallFlags)?, + CallType::Call { value_ptr }, + callee_ptr, + deposit_ptr, + Weight::from_parts(ref_time_limit, proof_size_limit), + input_data_ptr, + input_data_len, + output_ptr, + output_len_ptr, + ) + } + + /// Execute code in the context (storage, caller, value) of the current contract. + /// See [`pallet_revive_uapi::HostFn::delegate_call`]. + #[stable] + fn delegate_call( + &mut self, + memory: &mut M, + flags_and_callee: u64, + ref_time_limit: u64, + proof_size_limit: u64, + deposit_ptr: u32, + input_data: u64, + output_data: u64, + ) -> Result { + let (flags, address_ptr) = extract_hi_lo(flags_and_callee); + let (input_data_len, input_data_ptr) = extract_hi_lo(input_data); + let (output_len_ptr, output_ptr) = extract_hi_lo(output_data); + + self.call( + memory, + CallFlags::from_bits(flags).ok_or(Error::::InvalidCallFlags)?, + CallType::DelegateCall, + address_ptr, + deposit_ptr, + Weight::from_parts(ref_time_limit, proof_size_limit), + input_data_ptr, + input_data_len, + output_ptr, + output_len_ptr, + ) + } + + /// Instantiate a contract with the specified code hash. + /// See [`pallet_revive_uapi::HostFn::instantiate`]. + #[stable] + #[mutating] + fn instantiate( + &mut self, + memory: &mut M, + ref_time_limit: u64, + proof_size_limit: u64, + deposit_and_value: u64, + input_data: u64, + output_data: u64, + address_and_salt: u64, + ) -> Result { + let (deposit_ptr, value_ptr) = extract_hi_lo(deposit_and_value); + let (input_data_len, code_hash_ptr) = extract_hi_lo(input_data); + let (output_len_ptr, output_ptr) = extract_hi_lo(output_data); + let (address_ptr, salt_ptr) = extract_hi_lo(address_and_salt); + let Some(input_data_ptr) = code_hash_ptr.checked_add(32) else { + return Err(Error::::OutOfBounds.into()); + }; + let Some(input_data_len) = input_data_len.checked_sub(32) else { + return Err(Error::::OutOfBounds.into()); + }; + + self.instantiate( + memory, + code_hash_ptr, + Weight::from_parts(ref_time_limit, proof_size_limit), + deposit_ptr, + value_ptr, + input_data_ptr, + input_data_len, + address_ptr, + output_ptr, + output_len_ptr, + salt_ptr, + ) + } + + /// Returns the total size of the contract call input data. + /// See [`pallet_revive_uapi::HostFn::call_data_size `]. + #[stable] + fn call_data_size(&mut self, memory: &mut M) -> Result { + self.charge_gas(RuntimeCosts::CallDataSize)?; + Ok(self + .input_data + .as_ref() + .map(|input| input.len().try_into().expect("usize fits into u64; qed")) + .unwrap_or_default()) + } + + /// Stores the input passed by the caller into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::call_data_copy`]. + #[stable] + fn call_data_copy( + &mut self, + memory: &mut M, + out_ptr: u32, + out_len: u32, + offset: u32, + ) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::CallDataCopy(out_len))?; + + let Some(input) = self.input_data.as_ref() else { + return Err(Error::::InputForwarded.into()); + }; + + let start = offset as usize; + if start >= input.len() { + memory.zero(out_ptr, out_len)?; + return Ok(()); + } + + let end = start.saturating_add(out_len as usize).min(input.len()); + memory.write(out_ptr, &input[start..end])?; + + let bytes_written = (end - start) as u32; + memory.zero(out_ptr.saturating_add(bytes_written), out_len - bytes_written)?; + + Ok(()) + } + + /// Stores the U256 value at given call input `offset` into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::call_data_load`]. + #[stable] + fn call_data_load( + &mut self, + memory: &mut M, + out_ptr: u32, + offset: u32, + ) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::CallDataLoad)?; + + let Some(input) = self.input_data.as_ref() else { + return Err(Error::::InputForwarded.into()); + }; + + let mut data = [0; 32]; + let start = offset as usize; + let data = if start >= input.len() { + data // Any index is valid to request; OOB offsets return zero. + } else { + let end = start.saturating_add(32).min(input.len()); + data[..end - start].copy_from_slice(&input[start..end]); + data.reverse(); + data // Solidity expects right-padded data + }; + + self.write_fixed_sandbox_output(memory, out_ptr, &data, false, already_charged)?; + + Ok(()) + } + + /// Cease contract execution and save a data buffer as a result of the execution. + /// See [`pallet_revive_uapi::HostFn::return_value`]. + #[stable] + fn seal_return( + &mut self, + memory: &mut M, + flags: u32, + data_ptr: u32, + data_len: u32, + ) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::CopyFromContract(data_len))?; + if data_len > limits::CALLDATA_BYTES { + Err(>::ReturnDataTooLarge)?; + } + Err(TrapReason::Return(ReturnData { flags, data: memory.read(data_ptr, data_len)? })) + } + + /// Stores the address of the caller into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::caller`]. + #[stable] + fn caller(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::Caller)?; + let caller = ::AddressMapper::to_address(self.ext.caller().account_id()?); + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + caller.as_bytes(), + false, + already_charged, + )?) + } + + /// Stores the address of the call stack origin into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::origin`]. + #[stable] + fn origin(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::Origin)?; + let origin = ::AddressMapper::to_address(self.ext.origin().account_id()?); + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + origin.as_bytes(), + false, + already_charged, + )?) + } + + /// Retrieve the code hash for a specified contract address. + /// See [`pallet_revive_uapi::HostFn::code_hash`]. + #[stable] + fn code_hash(&mut self, memory: &mut M, addr_ptr: u32, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::CodeHash)?; + let address = memory.read_h160(addr_ptr)?; + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &self.ext.code_hash(&address).as_bytes(), + false, + already_charged, + )?) + } + + /// Retrieve the code size for a given contract address. + /// See [`pallet_revive_uapi::HostFn::code_size`]. + #[stable] + fn code_size(&mut self, memory: &mut M, addr_ptr: u32) -> Result { + self.charge_gas(RuntimeCosts::CodeSize)?; + let address = memory.read_h160(addr_ptr)?; + Ok(self.ext.code_size(&address)) + } + + /// Stores the address of the current contract into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::address`]. + #[stable] + fn address(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::Address)?; + let address = self.ext.address(); + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + address.as_bytes(), + false, + already_charged, + )?) + } + + /// Stores the price for the specified amount of weight into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::weight_to_fee`]. + #[stable] + fn weight_to_fee( + &mut self, + memory: &mut M, + ref_time_limit: u64, + proof_size_limit: u64, + out_ptr: u32, + ) -> Result<(), TrapReason> { + let weight = Weight::from_parts(ref_time_limit, proof_size_limit); + self.charge_gas(RuntimeCosts::WeightToFee)?; + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &self.ext.get_weight_price(weight).encode(), + false, + already_charged, + )?) + } + + /// Stores the immutable data into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::get_immutable_data`]. + #[stable] + fn get_immutable_data( + &mut self, + memory: &mut M, + out_ptr: u32, + out_len_ptr: u32, + ) -> Result<(), TrapReason> { + // quering the length is free as it is stored with the contract metadata + let len = self.ext.immutable_data_len(); + self.charge_gas(RuntimeCosts::GetImmutableData(len))?; + let data = self.ext.get_immutable_data()?; + self.write_sandbox_output(memory, out_ptr, out_len_ptr, &data, false, already_charged)?; + Ok(()) + } + + /// Attaches the supplied immutable data to the currently executing contract. + /// See [`pallet_revive_uapi::HostFn::set_immutable_data`]. + #[stable] + fn set_immutable_data(&mut self, memory: &mut M, ptr: u32, len: u32) -> Result<(), TrapReason> { + if len > limits::IMMUTABLE_BYTES { + return Err(Error::::OutOfBounds.into()); + } + self.charge_gas(RuntimeCosts::SetImmutableData(len))?; + let buf = memory.read(ptr, len)?; + let data = buf.try_into().expect("bailed out earlier; qed"); + self.ext.set_immutable_data(data)?; + Ok(()) + } + + /// Stores the *free* balance of the current account into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::balance`]. + #[stable] + fn balance(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::Balance)?; + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &self.ext.balance().to_little_endian(), + false, + already_charged, + )?) + } + + /// Stores the *free* balance of the supplied address into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::balance`]. + #[stable] + fn balance_of( + &mut self, + memory: &mut M, + addr_ptr: u32, + out_ptr: u32, + ) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::BalanceOf)?; + let address = memory.read_h160(addr_ptr)?; + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &self.ext.balance_of(&address).to_little_endian(), + false, + already_charged, + )?) + } + + /// Returns the chain ID. + /// See [`pallet_revive_uapi::HostFn::chain_id`]. + #[stable] + fn chain_id(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &U256::from(::ChainId::get()).to_little_endian(), + false, + |_| Some(RuntimeCosts::CopyToContract(32)), + )?) + } + + /// Returns the block ref_time limit. + /// See [`pallet_revive_uapi::HostFn::gas_limit`]. + #[stable] + fn gas_limit(&mut self, memory: &mut M) -> Result { + self.charge_gas(RuntimeCosts::GasLimit)?; + Ok(::BlockWeights::get().max_block.ref_time()) + } + + /// Stores the value transferred along with this call/instantiate into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::value_transferred`]. + #[stable] + fn value_transferred(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::ValueTransferred)?; + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &self.ext.value_transferred().to_little_endian(), + false, + already_charged, + )?) + } + + /// Returns the simulated ethereum `GASPRICE` value. + /// See [`pallet_revive_uapi::HostFn::gas_price`]. + #[stable] + fn gas_price(&mut self, memory: &mut M) -> Result { + self.charge_gas(RuntimeCosts::GasPrice)?; + Ok(GAS_PRICE.into()) + } + + /// Returns the simulated ethereum `BASEFEE` value. + /// See [`pallet_revive_uapi::HostFn::base_fee`]. + #[stable] + fn base_fee(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::BaseFee)?; + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &U256::zero().to_little_endian(), + false, + already_charged, + )?) + } + + /// Load the latest block timestamp into the supplied buffer + /// See [`pallet_revive_uapi::HostFn::now`]. + #[stable] + fn now(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::Now)?; + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &self.ext.now().to_little_endian(), + false, + already_charged, + )?) + } + + /// Deposit a contract event with the data buffer and optional list of topics. + /// See [pallet_revive_uapi::HostFn::deposit_event] + #[stable] + #[mutating] + fn deposit_event( + &mut self, + memory: &mut M, + topics_ptr: u32, + num_topic: u32, + data_ptr: u32, + data_len: u32, + ) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::DepositEvent { num_topic, len: data_len })?; + + if num_topic > limits::NUM_EVENT_TOPICS { + return Err(Error::::TooManyTopics.into()); + } + + if data_len > self.ext.max_value_size() { + return Err(Error::::ValueTooLarge.into()); + } + + let topics: Vec = match num_topic { + 0 => Vec::new(), + _ => { + let mut v = Vec::with_capacity(num_topic as usize); + let topics_len = num_topic * H256::len_bytes() as u32; + let buf = memory.read(topics_ptr, topics_len)?; + for chunk in buf.chunks_exact(H256::len_bytes()) { + v.push(H256::from_slice(chunk)); + } + v + }, + }; + + let event_data = memory.read(data_ptr, data_len)?; + self.ext.deposit_event(topics, event_data); + Ok(()) + } + + /// Stores the current block number of the current contract into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::block_number`]. + #[stable] + fn block_number(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::BlockNumber)?; + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &self.ext.block_number().to_little_endian(), + false, + already_charged, + )?) + } + + /// Stores the block hash at given block height into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::block_hash`]. + #[stable] + fn block_hash( + &mut self, + memory: &mut M, + block_number_ptr: u32, + out_ptr: u32, + ) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::BlockHash)?; + let block_number = memory.read_u256(block_number_ptr)?; + let block_hash = self.ext.block_hash(block_number).unwrap_or(H256::zero()); + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &block_hash.as_bytes(), + false, + already_charged, + )?) + } + + /// Stores the current block author into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::block_author`]. + #[stable] + fn block_author(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::BlockAuthor)?; + let block_author = self.ext.block_author().unwrap_or(H160::zero()); + + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &block_author.as_bytes(), + false, + already_charged, + )?) + } + + /// Computes the KECCAK 256-bit hash on the given input buffer. + /// See [`pallet_revive_uapi::HostFn::hash_keccak_256`]. + #[stable] + fn hash_keccak_256( + &mut self, + memory: &mut M, + input_ptr: u32, + input_len: u32, + output_ptr: u32, + ) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::HashKeccak256(input_len))?; + Ok(self.compute_hash_on_intermediate_buffer( + memory, keccak_256, input_ptr, input_len, output_ptr, + )?) + } + + /// Stores the length of the data returned by the last call into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::return_data_size`]. + #[stable] + fn return_data_size(&mut self, memory: &mut M) -> Result { + self.charge_gas(RuntimeCosts::ReturnDataSize)?; + Ok(self + .ext + .last_frame_output() + .data + .len() + .try_into() + .expect("usize fits into u64; qed")) + } + + /// Stores data returned by the last call, starting from `offset`, into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::return_data`]. + #[stable] + fn return_data_copy( + &mut self, + memory: &mut M, + out_ptr: u32, + out_len_ptr: u32, + offset: u32, + ) -> Result<(), TrapReason> { + let output = mem::take(self.ext.last_frame_output_mut()); + let result = if offset as usize > output.data.len() { + Err(Error::::OutOfBounds.into()) + } else { + self.write_sandbox_output( + memory, + out_ptr, + out_len_ptr, + &output.data[offset as usize..], + false, + |len| Some(RuntimeCosts::CopyToContract(len)), + ) + }; + *self.ext.last_frame_output_mut() = output; + Ok(result?) + } + + /// Returns the amount of ref_time left. + /// See [`pallet_revive_uapi::HostFn::ref_time_left`]. + #[stable] + fn ref_time_left(&mut self, memory: &mut M) -> Result { + self.charge_gas(RuntimeCosts::RefTimeLeft)?; + Ok(self.ext.gas_meter().gas_left().ref_time()) + } + + /// Checks whether the caller of the current contract is the origin of the whole call stack. + /// See [`pallet_revive_uapi::HostFn::caller_is_origin`]. + fn caller_is_origin(&mut self, _memory: &mut M) -> Result { + self.charge_gas(RuntimeCosts::CallerIsOrigin)?; + Ok(self.ext.caller_is_origin() as u32) + } + + /// Checks whether the caller of the current contract is root. + /// See [`pallet_revive_uapi::HostFn::caller_is_root`]. + fn caller_is_root(&mut self, _memory: &mut M) -> Result { + self.charge_gas(RuntimeCosts::CallerIsRoot)?; + Ok(self.ext.caller_is_root() as u32) + } + + /// Clear the value at the given key in the contract storage. + /// See [`pallet_revive_uapi::HostFn::clear_storage`] + #[mutating] + fn clear_storage( + &mut self, + memory: &mut M, + flags: u32, + key_ptr: u32, + key_len: u32, + ) -> Result { + self.clear_storage(memory, flags, key_ptr, key_len) + } + + /// Checks whether there is a value stored under the given key. + /// See [`pallet_revive_uapi::HostFn::contains_storage`] + fn contains_storage( + &mut self, + memory: &mut M, + flags: u32, + key_ptr: u32, + key_len: u32, + ) -> Result { + self.contains_storage(memory, flags, key_ptr, key_len) + } + + /// Calculates Ethereum address from the ECDSA compressed public key and stores + /// See [`pallet_revive_uapi::HostFn::ecdsa_to_eth_address`]. + fn ecdsa_to_eth_address( + &mut self, + memory: &mut M, + key_ptr: u32, + out_ptr: u32, + ) -> Result { + self.charge_gas(RuntimeCosts::EcdsaToEthAddress)?; + let mut compressed_key: [u8; 33] = [0; 33]; + memory.read_into_buf(key_ptr, &mut compressed_key)?; + let result = self.ext.ecdsa_to_eth_address(&compressed_key); + match result { + Ok(eth_address) => { + memory.write(out_ptr, eth_address.as_ref())?; + Ok(ReturnErrorCode::Success) + }, + Err(_) => Ok(ReturnErrorCode::EcdsaRecoveryFailed), + } + } + + /// Stores the minimum balance (a.k.a. existential deposit) into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::minimum_balance`]. + fn minimum_balance(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::MinimumBalance)?; + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + &self.ext.minimum_balance().to_little_endian(), + false, + already_charged, + )?) + } + + /// Retrieve the code hash of the currently executing contract. + /// See [`pallet_revive_uapi::HostFn::own_code_hash`]. + fn own_code_hash(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::OwnCodeHash)?; + let code_hash = *self.ext.own_code_hash(); + Ok(self.write_fixed_sandbox_output( + memory, + out_ptr, + code_hash.as_bytes(), + false, + already_charged, + )?) + } + + /// Replace the contract code at the specified address with new code. + /// See [`pallet_revive_uapi::HostFn::set_code_hash`]. + /// + /// Disabled until the internal implementation takes care of collecting + /// the immutable data of the new code hash. + #[mutating] + fn set_code_hash(&mut self, memory: &mut M, code_hash_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::SetCodeHash)?; + let code_hash: H256 = memory.read_h256(code_hash_ptr)?; + self.ext.set_code_hash(code_hash)?; + Ok(()) + } + + /// Verify a sr25519 signature + /// See [`pallet_revive_uapi::HostFn::sr25519_verify`]. + fn sr25519_verify( + &mut self, + memory: &mut M, + signature_ptr: u32, + pub_key_ptr: u32, + message_len: u32, + message_ptr: u32, + ) -> Result { + self.charge_gas(RuntimeCosts::Sr25519Verify(message_len))?; + + let mut signature: [u8; 64] = [0; 64]; + memory.read_into_buf(signature_ptr, &mut signature)?; + + let mut pub_key: [u8; 32] = [0; 32]; + memory.read_into_buf(pub_key_ptr, &mut pub_key)?; + + let message: Vec = memory.read(message_ptr, message_len)?; + + if self.ext.sr25519_verify(&signature, &message, &pub_key) { + Ok(ReturnErrorCode::Success) + } else { + Ok(ReturnErrorCode::Sr25519VerifyFailed) + } + } + + /// Retrieve and remove the value under the given key from storage. + /// See [`pallet_revive_uapi::HostFn::take_storage`] + #[mutating] + fn take_storage( + &mut self, + memory: &mut M, + flags: u32, + key_ptr: u32, + key_len: u32, + out_ptr: u32, + out_len_ptr: u32, + ) -> Result { + self.take_storage(memory, flags, key_ptr, key_len, out_ptr, out_len_ptr) + } + + /// Remove the calling account and transfer remaining **free** balance. + /// See [`pallet_revive_uapi::HostFn::terminate`]. + #[mutating] + fn terminate(&mut self, memory: &mut M, beneficiary_ptr: u32) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::Terminate)?; + let beneficiary = memory.read_h160(beneficiary_ptr)?; + self.ext.terminate(&beneficiary)?; + Err(TrapReason::Termination) + } + + /// Stores the amount of weight left into the supplied buffer. + /// See [`pallet_revive_uapi::HostFn::weight_left`]. + fn weight_left( + &mut self, + memory: &mut M, + out_ptr: u32, + out_len_ptr: u32, + ) -> Result<(), TrapReason> { + self.charge_gas(RuntimeCosts::WeightLeft)?; + let gas_left = &self.ext.gas_meter().gas_left().encode(); + Ok(self.write_sandbox_output( + memory, + out_ptr, + out_len_ptr, + gas_left, + false, + already_charged, + )?) + } +} diff --git a/substrate/frame/revive/src/vm/runtime.rs b/substrate/frame/revive/src/vm/runtime.rs deleted file mode 100644 index 3a1cc07ab31a3..0000000000000 --- a/substrate/frame/revive/src/vm/runtime.rs +++ /dev/null @@ -1,2111 +0,0 @@ -// This file is part of Substrate. - -// Copyright (C) Parity Technologies (UK) Ltd. -// SPDX-License-Identifier: Apache-2.0 - -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -//! Environment definition of the vm smart-contract runtime. - -use crate::{ - address::AddressMapper, - evm::runtime::GAS_PRICE, - exec::{ExecError, ExecResult, Ext, Key}, - gas::{ChargedAmount, Token}, - limits, - precompiles::{All as AllPrecompiles, Precompiles}, - primitives::ExecReturnValue, - weights::WeightInfo, - Config, Error, Pallet, LOG_TARGET, SENTINEL, -}; -use alloc::{vec, vec::Vec}; -use codec::Encode; -use core::{fmt, marker::PhantomData, mem}; -use frame_support::{ensure, traits::Get, weights::Weight}; -use pallet_revive_proc_macro::define_env; -use pallet_revive_uapi::{CallFlags, ReturnErrorCode, ReturnFlags, StorageFlags}; -use sp_core::{H160, H256, U256}; -use sp_io::hashing::keccak_256; -use sp_runtime::{DispatchError, RuntimeDebug}; - -/// Abstraction over the memory access within syscalls. -/// -/// The reason for this abstraction is that we run syscalls on the host machine when -/// benchmarking them. In that case we have direct access to the contract's memory. However, when -/// running within PolkaVM we need to resort to copying as we can't map the contracts memory into -/// the host (as of now). -pub trait Memory { - /// Read designated chunk from the sandbox memory into the supplied buffer. - /// - /// Returns `Err` if one of the following conditions occurs: - /// - /// - requested buffer is not within the bounds of the sandbox memory. - fn read_into_buf(&self, ptr: u32, buf: &mut [u8]) -> Result<(), DispatchError>; - - /// Write the given buffer to the designated location in the sandbox memory. - /// - /// Returns `Err` if one of the following conditions occurs: - /// - /// - designated area is not within the bounds of the sandbox memory. - fn write(&mut self, ptr: u32, buf: &[u8]) -> Result<(), DispatchError>; - - /// Zero the designated location in the sandbox memory. - /// - /// Returns `Err` if one of the following conditions occurs: - /// - /// - designated area is not within the bounds of the sandbox memory. - fn zero(&mut self, ptr: u32, len: u32) -> Result<(), DispatchError>; - - /// This will reset all compilation artifacts of the currently executing instance. - /// - /// This is used before we call into a new contract to free up some memory. Doing - /// so we make sure that we only ever have to hold one compilation cache at a time - /// independtently of of our call stack depth. - fn reset_interpreter_cache(&mut self); - - /// Read designated chunk from the sandbox memory. - /// - /// Returns `Err` if one of the following conditions occurs: - /// - /// - requested buffer is not within the bounds of the sandbox memory. - fn read(&self, ptr: u32, len: u32) -> Result, DispatchError> { - let mut buf = vec![0u8; len as usize]; - self.read_into_buf(ptr, buf.as_mut_slice())?; - Ok(buf) - } - - /// Same as `read` but reads into a fixed size buffer. - fn read_array(&self, ptr: u32) -> Result<[u8; N], DispatchError> { - let mut buf = [0u8; N]; - self.read_into_buf(ptr, &mut buf)?; - Ok(buf) - } - - /// Read a `u32` from the sandbox memory. - fn read_u32(&self, ptr: u32) -> Result { - let buf: [u8; 4] = self.read_array(ptr)?; - Ok(u32::from_le_bytes(buf)) - } - - /// Read a `U256` from the sandbox memory. - fn read_u256(&self, ptr: u32) -> Result { - let buf: [u8; 32] = self.read_array(ptr)?; - Ok(U256::from_little_endian(&buf)) - } - - /// Read a `H160` from the sandbox memory. - fn read_h160(&self, ptr: u32) -> Result { - let mut buf = H160::default(); - self.read_into_buf(ptr, buf.as_bytes_mut())?; - Ok(buf) - } - - /// Read a `H256` from the sandbox memory. - fn read_h256(&self, ptr: u32) -> Result { - let mut code_hash = H256::default(); - self.read_into_buf(ptr, code_hash.as_bytes_mut())?; - Ok(code_hash) - } -} - -/// Allows syscalls access to the PolkaVM instance they are executing in. -/// -/// In case a contract is executing within PolkaVM its `memory` argument will also implement -/// this trait. The benchmarking implementation of syscalls will only require `Memory` -/// to be implemented. -pub trait PolkaVmInstance: Memory { - fn gas(&self) -> polkavm::Gas; - fn set_gas(&mut self, gas: polkavm::Gas); - fn read_input_regs(&self) -> (u64, u64, u64, u64, u64, u64); - fn write_output(&mut self, output: u64); -} - -// Memory implementation used in benchmarking where guest memory is mapped into the host. -// -// Please note that we could optimize the `read_as_*` functions by decoding directly from -// memory without a copy. However, we don't do that because as it would change the behaviour -// of those functions: A `read_as` with a `len` larger than the actual type can succeed -// in the streaming implementation while it could fail with a segfault in the copy implementation. -#[cfg(feature = "runtime-benchmarks")] -impl Memory for [u8] { - fn read_into_buf(&self, ptr: u32, buf: &mut [u8]) -> Result<(), DispatchError> { - let ptr = ptr as usize; - let bound_checked = - self.get(ptr..ptr + buf.len()).ok_or_else(|| Error::::OutOfBounds)?; - buf.copy_from_slice(bound_checked); - Ok(()) - } - - fn write(&mut self, ptr: u32, buf: &[u8]) -> Result<(), DispatchError> { - let ptr = ptr as usize; - let bound_checked = - self.get_mut(ptr..ptr + buf.len()).ok_or_else(|| Error::::OutOfBounds)?; - bound_checked.copy_from_slice(buf); - Ok(()) - } - - fn zero(&mut self, ptr: u32, len: u32) -> Result<(), DispatchError> { - <[u8] as Memory>::write(self, ptr, &vec![0; len as usize]) - } - - fn reset_interpreter_cache(&mut self) {} -} - -impl Memory for polkavm::RawInstance { - fn read_into_buf(&self, ptr: u32, buf: &mut [u8]) -> Result<(), DispatchError> { - self.read_memory_into(ptr, buf) - .map(|_| ()) - .map_err(|_| Error::::OutOfBounds.into()) - } - - fn write(&mut self, ptr: u32, buf: &[u8]) -> Result<(), DispatchError> { - self.write_memory(ptr, buf).map_err(|_| Error::::OutOfBounds.into()) - } - - fn zero(&mut self, ptr: u32, len: u32) -> Result<(), DispatchError> { - self.zero_memory(ptr, len).map_err(|_| Error::::OutOfBounds.into()) - } - - fn reset_interpreter_cache(&mut self) { - self.reset_interpreter_cache(); - } -} - -impl PolkaVmInstance for polkavm::RawInstance { - fn gas(&self) -> polkavm::Gas { - self.gas() - } - - fn set_gas(&mut self, gas: polkavm::Gas) { - self.set_gas(gas) - } - - fn read_input_regs(&self) -> (u64, u64, u64, u64, u64, u64) { - ( - self.reg(polkavm::Reg::A0), - self.reg(polkavm::Reg::A1), - self.reg(polkavm::Reg::A2), - self.reg(polkavm::Reg::A3), - self.reg(polkavm::Reg::A4), - self.reg(polkavm::Reg::A5), - ) - } - - fn write_output(&mut self, output: u64) { - self.set_reg(polkavm::Reg::A0, output); - } -} - -impl From<&ExecReturnValue> for ReturnErrorCode { - fn from(from: &ExecReturnValue) -> Self { - if from.flags.contains(ReturnFlags::REVERT) { - Self::CalleeReverted - } else { - Self::Success - } - } -} - -/// The data passed through when a contract uses `seal_return`. -#[derive(RuntimeDebug)] -pub struct ReturnData { - /// The flags as passed through by the contract. They are still unchecked and - /// will later be parsed into a `ReturnFlags` bitflags struct. - flags: u32, - /// The output buffer passed by the contract as return data. - data: Vec, -} - -/// Enumerates all possible reasons why a trap was generated. -/// -/// This is either used to supply the caller with more information about why an error -/// occurred (the SupervisorError variant). -/// The other case is where the trap does not constitute an error but rather was invoked -/// as a quick way to terminate the application (all other variants). -#[derive(RuntimeDebug)] -pub enum TrapReason { - /// The supervisor trapped the contract because of an error condition occurred during - /// execution in privileged code. - SupervisorError(DispatchError), - /// Signals that trap was generated in response to call `seal_return` host function. - Return(ReturnData), - /// Signals that a trap was generated in response to a successful call to the - /// `seal_terminate` host function. - Termination, -} - -impl> From for TrapReason { - fn from(from: T) -> Self { - Self::SupervisorError(from.into()) - } -} - -impl fmt::Display for TrapReason { - fn fmt(&self, _f: &mut fmt::Formatter<'_>) -> Result<(), fmt::Error> { - Ok(()) - } -} - -#[cfg_attr(test, derive(Debug, PartialEq, Eq))] -#[derive(Copy, Clone)] -pub enum RuntimeCosts { - /// Base Weight of calling a host function. - HostFn, - /// Weight charged for copying data from the sandbox. - CopyFromContract(u32), - /// Weight charged for copying data to the sandbox. - CopyToContract(u32), - /// Weight of calling `seal_call_data_load``. - CallDataLoad, - /// Weight of calling `seal_call_data_copy`. - CallDataCopy(u32), - /// Weight of calling `seal_caller`. - Caller, - /// Weight of calling `seal_call_data_size`. - CallDataSize, - /// Weight of calling `seal_return_data_size`. - ReturnDataSize, - /// Weight of calling `seal_to_account_id`. - ToAccountId, - /// Weight of calling `seal_origin`. - Origin, - /// Weight of calling `seal_code_hash`. - CodeHash, - /// Weight of calling `seal_own_code_hash`. - OwnCodeHash, - /// Weight of calling `seal_code_size`. - CodeSize, - /// Weight of calling `seal_caller_is_origin`. - CallerIsOrigin, - /// Weight of calling `caller_is_root`. - CallerIsRoot, - /// Weight of calling `seal_address`. - Address, - /// Weight of calling `seal_ref_time_left`. - RefTimeLeft, - /// Weight of calling `seal_weight_left`. - WeightLeft, - /// Weight of calling `seal_balance`. - Balance, - /// Weight of calling `seal_balance_of`. - BalanceOf, - /// Weight of calling `seal_value_transferred`. - ValueTransferred, - /// Weight of calling `seal_minimum_balance`. - MinimumBalance, - /// Weight of calling `seal_block_number`. - BlockNumber, - /// Weight of calling `seal_block_hash`. - BlockHash, - /// Weight of calling `seal_block_author`. - BlockAuthor, - /// Weight of calling `seal_gas_price`. - GasPrice, - /// Weight of calling `seal_base_fee`. - BaseFee, - /// Weight of calling `seal_now`. - Now, - /// Weight of calling `seal_gas_limit`. - GasLimit, - /// Weight of calling `seal_weight_to_fee`. - WeightToFee, - /// Weight of calling `seal_terminate`. - Terminate, - /// Weight of calling `seal_deposit_event` with the given number of topics and event size. - DepositEvent { num_topic: u32, len: u32 }, - /// Weight of calling `seal_set_storage` for the given storage item sizes. - SetStorage { old_bytes: u32, new_bytes: u32 }, - /// Weight of calling `seal_clear_storage` per cleared byte. - ClearStorage(u32), - /// Weight of calling `seal_contains_storage` per byte of the checked item. - ContainsStorage(u32), - /// Weight of calling `seal_get_storage` with the specified size in storage. - GetStorage(u32), - /// Weight of calling `seal_take_storage` for the given size. - TakeStorage(u32), - /// Weight of calling `seal_set_transient_storage` for the given storage item sizes. - SetTransientStorage { old_bytes: u32, new_bytes: u32 }, - /// Weight of calling `seal_clear_transient_storage` per cleared byte. - ClearTransientStorage(u32), - /// Weight of calling `seal_contains_transient_storage` per byte of the checked item. - ContainsTransientStorage(u32), - /// Weight of calling `seal_get_transient_storage` with the specified size in storage. - GetTransientStorage(u32), - /// Weight of calling `seal_take_transient_storage` for the given size. - TakeTransientStorage(u32), - /// Base weight of calling `seal_call`. - CallBase, - /// Weight of calling `seal_delegate_call` for the given input size. - DelegateCallBase, - /// Weight of calling a precompile. - PrecompileBase, - /// Weight of calling a precompile that has a contract info. - PrecompileWithInfoBase, - /// Weight of reading and decoding the input to a precompile. - PrecompileDecode(u32), - /// Weight of the transfer performed during a call. - /// parameter `dust_transfer` indicates whether the transfer has a `dust` value. - CallTransferSurcharge { dust_transfer: bool }, - /// Weight per byte that is cloned by supplying the `CLONE_INPUT` flag. - CallInputCloned(u32), - /// Weight of calling `seal_instantiate`. - Instantiate { input_data_len: u32, balance_transfer: bool, dust_transfer: bool }, - /// Weight of calling `Ripemd160` precompile for the given input size. - Ripemd160(u32), - /// Weight of calling `Sha256` precompile for the given input size. - HashSha256(u32), - /// Weight of calling `seal_hash_keccak_256` for the given input size. - HashKeccak256(u32), - /// Weight of calling the `System::hashBlake256` precompile function for the given input - /// size. - HashBlake256(u32), - /// Weight of calling `System::hashBlake128` precompile function for the given input size. - HashBlake128(u32), - /// Weight of calling `ECERecover` precompile. - EcdsaRecovery, - /// Weight of calling `seal_sr25519_verify` for the given input size. - Sr25519Verify(u32), - /// Weight charged by a precompile. - Precompile(Weight), - /// Weight of calling `seal_set_code_hash` - SetCodeHash, - /// Weight of calling `ecdsa_to_eth_address` - EcdsaToEthAddress, - /// Weight of calling `get_immutable_dependency` - GetImmutableData(u32), - /// Weight of calling `set_immutable_dependency` - SetImmutableData(u32), - /// Weight of calling `Bn128Add` precompile - Bn128Add, - /// Weight of calling `Bn128Add` precompile - Bn128Mul, - /// Weight of calling `Bn128Pairing` precompile for the given number of input pairs. - Bn128Pairing(u32), - /// Weight of calling `Identity` precompile for the given number of input length. - Identity(u32), - /// Weight of calling `Blake2F` precompile for the given number of rounds. - Blake2F(u32), - /// Weight of calling `Modexp` precompile - Modexp(u64), -} - -/// For functions that modify storage, benchmarks are performed with one item in the -/// storage. To account for the worst-case scenario, the weight of the overhead of -/// writing to or reading from full storage is included. For transient storage writes, -/// the rollback weight is added to reflect the worst-case scenario for this operation. -macro_rules! cost_storage { - (write_transient, $name:ident $(, $arg:expr )*) => { - T::WeightInfo::$name($( $arg ),*) - .saturating_add(T::WeightInfo::rollback_transient_storage()) - .saturating_add(T::WeightInfo::set_transient_storage_full() - .saturating_sub(T::WeightInfo::set_transient_storage_empty())) - }; - - (read_transient, $name:ident $(, $arg:expr )*) => { - T::WeightInfo::$name($( $arg ),*) - .saturating_add(T::WeightInfo::get_transient_storage_full() - .saturating_sub(T::WeightInfo::get_transient_storage_empty())) - }; - - (write, $name:ident $(, $arg:expr )*) => { - T::WeightInfo::$name($( $arg ),*) - .saturating_add(T::WeightInfo::set_storage_full() - .saturating_sub(T::WeightInfo::set_storage_empty())) - }; - - (read, $name:ident $(, $arg:expr )*) => { - T::WeightInfo::$name($( $arg ),*) - .saturating_add(T::WeightInfo::get_storage_full() - .saturating_sub(T::WeightInfo::get_storage_empty())) - }; -} - -macro_rules! cost_args { - // cost_args!(name, a, b, c) -> T::WeightInfo::name(a, b, c).saturating_sub(T::WeightInfo::name(0, 0, 0)) - ($name:ident, $( $arg: expr ),+) => { - (T::WeightInfo::$name($( $arg ),+).saturating_sub(cost_args!(@call_zero $name, $( $arg ),+))) - }; - // Transform T::WeightInfo::name(a, b, c) into T::WeightInfo::name(0, 0, 0) - (@call_zero $name:ident, $( $arg:expr ),*) => { - T::WeightInfo::$name($( cost_args!(@replace_token $arg) ),*) - }; - // Replace the token with 0. - (@replace_token $_in:tt) => { 0 }; -} - -impl Token for RuntimeCosts { - fn influence_lowest_gas_limit(&self) -> bool { - true - } - - fn weight(&self) -> Weight { - use self::RuntimeCosts::*; - match *self { - HostFn => cost_args!(noop_host_fn, 1), - CopyToContract(len) => T::WeightInfo::seal_copy_to_contract(len), - CopyFromContract(len) => T::WeightInfo::seal_return(len), - CallDataSize => T::WeightInfo::seal_call_data_size(), - ReturnDataSize => T::WeightInfo::seal_return_data_size(), - CallDataLoad => T::WeightInfo::seal_call_data_load(), - CallDataCopy(len) => T::WeightInfo::seal_call_data_copy(len), - Caller => T::WeightInfo::seal_caller(), - Origin => T::WeightInfo::seal_origin(), - ToAccountId => T::WeightInfo::seal_to_account_id(), - CodeHash => T::WeightInfo::seal_code_hash(), - CodeSize => T::WeightInfo::seal_code_size(), - OwnCodeHash => T::WeightInfo::seal_own_code_hash(), - CallerIsOrigin => T::WeightInfo::seal_caller_is_origin(), - CallerIsRoot => T::WeightInfo::seal_caller_is_root(), - Address => T::WeightInfo::seal_address(), - RefTimeLeft => T::WeightInfo::seal_ref_time_left(), - WeightLeft => T::WeightInfo::seal_weight_left(), - Balance => T::WeightInfo::seal_balance(), - BalanceOf => T::WeightInfo::seal_balance_of(), - ValueTransferred => T::WeightInfo::seal_value_transferred(), - MinimumBalance => T::WeightInfo::seal_minimum_balance(), - BlockNumber => T::WeightInfo::seal_block_number(), - BlockHash => T::WeightInfo::seal_block_hash(), - BlockAuthor => T::WeightInfo::seal_block_author(), - GasPrice => T::WeightInfo::seal_gas_price(), - BaseFee => T::WeightInfo::seal_base_fee(), - Now => T::WeightInfo::seal_now(), - GasLimit => T::WeightInfo::seal_gas_limit(), - WeightToFee => T::WeightInfo::seal_weight_to_fee(), - Terminate => T::WeightInfo::seal_terminate(), - DepositEvent { num_topic, len } => T::WeightInfo::seal_deposit_event(num_topic, len), - SetStorage { new_bytes, old_bytes } => { - cost_storage!(write, seal_set_storage, new_bytes, old_bytes) - }, - ClearStorage(len) => cost_storage!(write, seal_clear_storage, len), - ContainsStorage(len) => cost_storage!(read, seal_contains_storage, len), - GetStorage(len) => cost_storage!(read, seal_get_storage, len), - TakeStorage(len) => cost_storage!(write, seal_take_storage, len), - SetTransientStorage { new_bytes, old_bytes } => { - cost_storage!(write_transient, seal_set_transient_storage, new_bytes, old_bytes) - }, - ClearTransientStorage(len) => { - cost_storage!(write_transient, seal_clear_transient_storage, len) - }, - ContainsTransientStorage(len) => { - cost_storage!(read_transient, seal_contains_transient_storage, len) - }, - GetTransientStorage(len) => { - cost_storage!(read_transient, seal_get_transient_storage, len) - }, - TakeTransientStorage(len) => { - cost_storage!(write_transient, seal_take_transient_storage, len) - }, - CallBase => T::WeightInfo::seal_call(0, 0, 0), - DelegateCallBase => T::WeightInfo::seal_delegate_call(), - PrecompileBase => T::WeightInfo::seal_call_precompile(0, 0), - PrecompileWithInfoBase => T::WeightInfo::seal_call_precompile(1, 0), - PrecompileDecode(len) => cost_args!(seal_call_precompile, 0, len), - CallTransferSurcharge { dust_transfer } => - cost_args!(seal_call, 1, dust_transfer.into(), 0), - CallInputCloned(len) => cost_args!(seal_call, 0, 0, len), - Instantiate { input_data_len, balance_transfer, dust_transfer } => - T::WeightInfo::seal_instantiate( - input_data_len, - balance_transfer.into(), - dust_transfer.into(), - ), - HashSha256(len) => T::WeightInfo::sha2_256(len), - Ripemd160(len) => T::WeightInfo::ripemd_160(len), - HashKeccak256(len) => T::WeightInfo::seal_hash_keccak_256(len), - HashBlake256(len) => T::WeightInfo::hash_blake2_256(len), - HashBlake128(len) => T::WeightInfo::hash_blake2_128(len), - EcdsaRecovery => T::WeightInfo::ecdsa_recover(), - Sr25519Verify(len) => T::WeightInfo::seal_sr25519_verify(len), - Precompile(weight) => weight, - SetCodeHash => T::WeightInfo::seal_set_code_hash(), - EcdsaToEthAddress => T::WeightInfo::seal_ecdsa_to_eth_address(), - GetImmutableData(len) => T::WeightInfo::seal_get_immutable_data(len), - SetImmutableData(len) => T::WeightInfo::seal_set_immutable_data(len), - Bn128Add => T::WeightInfo::bn128_add(), - Bn128Mul => T::WeightInfo::bn128_mul(), - Bn128Pairing(len) => T::WeightInfo::bn128_pairing(len), - Identity(len) => T::WeightInfo::identity(len), - Blake2F(rounds) => T::WeightInfo::blake2f(rounds), - Modexp(gas) => { - use frame_support::weights::constants::WEIGHT_REF_TIME_PER_SECOND; - /// Current approximation of the gas/s consumption considering - /// EVM execution over compiled WASM (on 4.4Ghz CPU). - /// Given the 2000ms Weight, from which 75% only are used for transactions, - /// the total EVM execution gas limit is: GAS_PER_SECOND * 2 * 0.75 ~= 60_000_000. - const GAS_PER_SECOND: u64 = 40_000_000; - - /// Approximate ratio of the amount of Weight per Gas. - /// u64 works for approximations because Weight is a very small unit compared to - /// gas. - const WEIGHT_PER_GAS: u64 = WEIGHT_REF_TIME_PER_SECOND / GAS_PER_SECOND; - Weight::from_parts(gas.saturating_mul(WEIGHT_PER_GAS), 0) - }, - } - } -} - -/// Same as [`Runtime::charge_gas`]. -/// -/// We need this access as a macro because sometimes hiding the lifetimes behind -/// a function won't work out. -macro_rules! charge_gas { - ($runtime:expr, $costs:expr) => {{ - $runtime.ext.gas_meter_mut().charge($costs) - }}; -} - -/// The kind of call that should be performed. -enum CallType { - /// Execute another instantiated contract - Call { value_ptr: u32 }, - /// Execute another contract code in the context (storage, account ID, value) of the caller - /// contract - DelegateCall, -} - -impl CallType { - fn cost(&self) -> RuntimeCosts { - match self { - CallType::Call { .. } => RuntimeCosts::CallBase, - CallType::DelegateCall => RuntimeCosts::DelegateCallBase, - } - } -} - -/// This is only appropriate when writing out data of constant size that does not depend on user -/// input. In this case the costs for this copy was already charged as part of the token at -/// the beginning of the API entry point. -fn already_charged(_: u32) -> Option { - None -} - -/// Helper to extract two `u32` values from a given `u64` register. -fn extract_hi_lo(reg: u64) -> (u32, u32) { - ((reg >> 32) as u32, reg as u32) -} - -/// Provides storage variants to support standard and Etheruem compatible semantics. -enum StorageValue { - /// Indicates that the storage value should be read from a memory buffer. - /// - `ptr`: A pointer to the start of the data in sandbox memory. - /// - `len`: The length (in bytes) of the data. - Memory { ptr: u32, len: u32 }, - - /// Indicates that the storage value is provided inline as a fixed-size (256-bit) value. - /// This is used by set_storage_or_clear() to avoid double reads. - /// This variant is used to implement Ethereum SSTORE-like semantics. - Value(Vec), -} - -/// Controls the output behavior for storage reads, both when a key is found and when it is not. -enum StorageReadMode { - /// VariableOutput mode: if the key exists, the full stored value is returned - /// using the caller‑provided output length. - VariableOutput { output_len_ptr: u32 }, - /// Ethereum commpatible(FixedOutput32) mode: always write a 32-byte value into the output - /// buffer. If the key is missing, write 32 bytes of zeros. - FixedOutput32, -} - -/// Can only be used for one call. -pub struct Runtime<'a, E: Ext, M: ?Sized> { - ext: &'a mut E, - input_data: Option>, - _phantom_data: PhantomData, -} - -impl<'a, E: Ext, M: PolkaVmInstance> Runtime<'a, E, M> { - pub fn handle_interrupt( - &mut self, - interrupt: Result, - module: &polkavm::Module, - instance: &mut M, - ) -> Option { - use polkavm::InterruptKind::*; - - match interrupt { - Err(error) => { - // in contrast to the other returns this "should" not happen: log level error - log::error!(target: LOG_TARGET, "polkavm execution error: {error}"); - Some(Err(Error::::ExecutionFailed.into())) - }, - Ok(Finished) => - Some(Ok(ExecReturnValue { flags: ReturnFlags::empty(), data: Vec::new() })), - Ok(Trap) => Some(Err(Error::::ContractTrapped.into())), - Ok(Segfault(_)) => Some(Err(Error::::ExecutionFailed.into())), - Ok(NotEnoughGas) => Some(Err(Error::::OutOfGas.into())), - Ok(Step) => None, - Ok(Ecalli(idx)) => { - // This is a special hard coded syscall index which is used by benchmarks - // to abort contract execution. It is used to terminate the execution without - // breaking up a basic block. The fixed index is used so that the benchmarks - // don't have to deal with import tables. - if cfg!(feature = "runtime-benchmarks") && idx == SENTINEL { - return Some(Ok(ExecReturnValue { - flags: ReturnFlags::empty(), - data: Vec::new(), - })) - } - let Some(syscall_symbol) = module.imports().get(idx) else { - return Some(Err(>::InvalidSyscall.into())); - }; - match self.handle_ecall(instance, syscall_symbol.as_bytes()) { - Ok(None) => None, - Ok(Some(return_value)) => { - instance.write_output(return_value); - None - }, - Err(TrapReason::Return(ReturnData { flags, data })) => - match ReturnFlags::from_bits(flags) { - None => Some(Err(Error::::InvalidCallFlags.into())), - Some(flags) => Some(Ok(ExecReturnValue { flags, data })), - }, - Err(TrapReason::Termination) => Some(Ok(Default::default())), - Err(TrapReason::SupervisorError(error)) => Some(Err(error.into())), - } - }, - } - } -} - -impl<'a, E: Ext, M: ?Sized + Memory> Runtime<'a, E, M> { - pub fn new(ext: &'a mut E, input_data: Vec) -> Self { - Self { ext, input_data: Some(input_data), _phantom_data: Default::default() } - } - - /// Get a mutable reference to the inner `Ext`. - pub fn ext(&mut self) -> &mut E { - self.ext - } - - /// Charge the gas meter with the specified token. - /// - /// Returns `Err(HostError)` if there is not enough gas. - fn charge_gas(&mut self, costs: RuntimeCosts) -> Result { - charge_gas!(self, costs) - } - - /// Adjust a previously charged amount down to its actual amount. - /// - /// This is when a maximum a priori amount was charged and then should be partially - /// refunded to match the actual amount. - fn adjust_gas(&mut self, charged: ChargedAmount, actual_costs: RuntimeCosts) { - self.ext.gas_meter_mut().adjust_gas(charged, actual_costs); - } - - /// Write the given buffer and its length to the designated locations in sandbox memory and - /// charge gas according to the token returned by `create_token`. - /// - /// `out_ptr` is the location in sandbox memory where `buf` should be written to. - /// `out_len_ptr` is an in-out location in sandbox memory. It is read to determine the - /// length of the buffer located at `out_ptr`. If that buffer is smaller than the actual - /// `buf.len()`, only what fits into that buffer is written to `out_ptr`. - /// The actual amount of bytes copied to `out_ptr` is written to `out_len_ptr`. - /// - /// If `out_ptr` is set to the sentinel value of `SENTINEL` and `allow_skip` is true the - /// operation is skipped and `Ok` is returned. This is supposed to help callers to make copying - /// output optional. For example to skip copying back the output buffer of an `seal_call` - /// when the caller is not interested in the result. - /// - /// `create_token` can optionally instruct this function to charge the gas meter with the token - /// it returns. `create_token` receives the variable amount of bytes that are about to be copied - /// by this function. - /// - /// In addition to the error conditions of `Memory::write` this functions returns - /// `Err` if the size of the buffer located at `out_ptr` is too small to fit `buf`. - pub fn write_sandbox_output( - &mut self, - memory: &mut M, - out_ptr: u32, - out_len_ptr: u32, - buf: &[u8], - allow_skip: bool, - create_token: impl FnOnce(u32) -> Option, - ) -> Result<(), DispatchError> { - if allow_skip && out_ptr == SENTINEL { - return Ok(()); - } - - let len = memory.read_u32(out_len_ptr)?; - let buf_len = len.min(buf.len() as u32); - - if let Some(costs) = create_token(buf_len) { - self.charge_gas(costs)?; - } - - memory.write(out_ptr, &buf[..buf_len as usize])?; - memory.write(out_len_ptr, &buf_len.encode()) - } - - /// Same as `write_sandbox_output` but for static size output. - pub fn write_fixed_sandbox_output( - &mut self, - memory: &mut M, - out_ptr: u32, - buf: &[u8], - allow_skip: bool, - create_token: impl FnOnce(u32) -> Option, - ) -> Result<(), DispatchError> { - if buf.is_empty() || (allow_skip && out_ptr == SENTINEL) { - return Ok(()); - } - - let buf_len = buf.len() as u32; - if let Some(costs) = create_token(buf_len) { - self.charge_gas(costs)?; - } - - memory.write(out_ptr, buf) - } - - /// Computes the given hash function on the supplied input. - /// - /// Reads from the sandboxed input buffer into an intermediate buffer. - /// Returns the result directly to the output buffer of the sandboxed memory. - /// - /// It is the callers responsibility to provide an output buffer that - /// is large enough to hold the expected amount of bytes returned by the - /// chosen hash function. - /// - /// # Note - /// - /// The `input` and `output` buffers may overlap. - fn compute_hash_on_intermediate_buffer( - &self, - memory: &mut M, - hash_fn: F, - input_ptr: u32, - input_len: u32, - output_ptr: u32, - ) -> Result<(), DispatchError> - where - F: FnOnce(&[u8]) -> R, - R: AsRef<[u8]>, - { - // Copy input into supervisor memory. - let input = memory.read(input_ptr, input_len)?; - // Compute the hash on the input buffer using the given hash function. - let hash = hash_fn(&input); - // Write the resulting hash back into the sandboxed output buffer. - memory.write(output_ptr, hash.as_ref())?; - Ok(()) - } - - /// Fallible conversion of a `ExecError` to `ReturnErrorCode`. - /// - /// This is used when converting the error returned from a subcall in order to decide - /// whether to trap the caller or allow handling of the error. - fn exec_error_into_return_code(from: ExecError) -> Result { - use crate::exec::ErrorOrigin::Callee; - use ReturnErrorCode::*; - - let transfer_failed = Error::::TransferFailed.into(); - let out_of_gas = Error::::OutOfGas.into(); - let out_of_deposit = Error::::StorageDepositLimitExhausted.into(); - let duplicate_contract = Error::::DuplicateContract.into(); - let unsupported_precompile = Error::::UnsupportedPrecompileAddress.into(); - - // errors in the callee do not trap the caller - match (from.error, from.origin) { - (err, _) if err == transfer_failed => Ok(TransferFailed), - (err, _) if err == duplicate_contract => Ok(DuplicateContractAddress), - (err, _) if err == unsupported_precompile => Err(err), - (err, Callee) if err == out_of_gas || err == out_of_deposit => Ok(OutOfResources), - (_, Callee) => Ok(CalleeTrapped), - (err, _) => Err(err), - } - } - - fn decode_key(&self, memory: &M, key_ptr: u32, key_len: u32) -> Result { - let res = match key_len { - SENTINEL => { - let mut buffer = [0u8; 32]; - memory.read_into_buf(key_ptr, buffer.as_mut())?; - Ok(Key::from_fixed(buffer)) - }, - len => { - ensure!(len <= limits::STORAGE_KEY_BYTES, Error::::DecodingFailed); - let key = memory.read(key_ptr, len)?; - Key::try_from_var(key) - }, - }; - - res.map_err(|_| Error::::DecodingFailed.into()) - } - - fn is_transient(flags: u32) -> Result { - StorageFlags::from_bits(flags) - .ok_or_else(|| >::InvalidStorageFlags.into()) - .map(|flags| flags.contains(StorageFlags::TRANSIENT)) - } - - fn set_storage( - &mut self, - memory: &M, - flags: u32, - key_ptr: u32, - key_len: u32, - value: StorageValue, - ) -> Result { - let transient = Self::is_transient(flags)?; - let costs = |new_bytes: u32, old_bytes: u32| { - if transient { - RuntimeCosts::SetTransientStorage { new_bytes, old_bytes } - } else { - RuntimeCosts::SetStorage { new_bytes, old_bytes } - } - }; - - let value_len = match &value { - StorageValue::Memory { ptr: _, len } => *len, - StorageValue::Value(data) => data.len() as u32, - }; - - let max_size = self.ext.max_value_size(); - let charged = self.charge_gas(costs(value_len, self.ext.max_value_size()))?; - if value_len > max_size { - return Err(Error::::ValueTooLarge.into()); - } - - let key = self.decode_key(memory, key_ptr, key_len)?; - - let value = match value { - StorageValue::Memory { ptr, len } => Some(memory.read(ptr, len)?), - StorageValue::Value(data) => Some(data), - }; - - let write_outcome = if transient { - self.ext.set_transient_storage(&key, value, false)? - } else { - self.ext.set_storage(&key, value, false)? - }; - - self.adjust_gas(charged, costs(value_len, write_outcome.old_len())); - Ok(write_outcome.old_len_with_sentinel()) - } - - fn clear_storage( - &mut self, - memory: &M, - flags: u32, - key_ptr: u32, - key_len: u32, - ) -> Result { - let transient = Self::is_transient(flags)?; - let costs = |len| { - if transient { - RuntimeCosts::ClearTransientStorage(len) - } else { - RuntimeCosts::ClearStorage(len) - } - }; - let charged = self.charge_gas(costs(self.ext.max_value_size()))?; - let key = self.decode_key(memory, key_ptr, key_len)?; - let outcome = if transient { - self.ext.set_transient_storage(&key, None, false)? - } else { - self.ext.set_storage(&key, None, false)? - }; - self.adjust_gas(charged, costs(outcome.old_len())); - Ok(outcome.old_len_with_sentinel()) - } - - fn get_storage( - &mut self, - memory: &mut M, - flags: u32, - key_ptr: u32, - key_len: u32, - out_ptr: u32, - read_mode: StorageReadMode, - ) -> Result { - let transient = Self::is_transient(flags)?; - let costs = |len| { - if transient { - RuntimeCosts::GetTransientStorage(len) - } else { - RuntimeCosts::GetStorage(len) - } - }; - let charged = self.charge_gas(costs(self.ext.max_value_size()))?; - let key = self.decode_key(memory, key_ptr, key_len)?; - let outcome = if transient { - self.ext.get_transient_storage(&key) - } else { - self.ext.get_storage(&key) - }; - - if let Some(value) = outcome { - self.adjust_gas(charged, costs(value.len() as u32)); - - match read_mode { - StorageReadMode::FixedOutput32 => { - let mut fixed_output = [0u8; 32]; - let len = value.len().min(fixed_output.len()); - fixed_output[..len].copy_from_slice(&value[..len]); - - self.write_fixed_sandbox_output( - memory, - out_ptr, - &fixed_output, - false, - already_charged, - )?; - Ok(ReturnErrorCode::Success) - }, - StorageReadMode::VariableOutput { output_len_ptr: out_len_ptr } => { - self.write_sandbox_output( - memory, - out_ptr, - out_len_ptr, - &value, - false, - already_charged, - )?; - Ok(ReturnErrorCode::Success) - }, - } - } else { - self.adjust_gas(charged, costs(0)); - - match read_mode { - StorageReadMode::FixedOutput32 => { - self.write_fixed_sandbox_output( - memory, - out_ptr, - &[0u8; 32], - false, - already_charged, - )?; - Ok(ReturnErrorCode::Success) - }, - StorageReadMode::VariableOutput { .. } => Ok(ReturnErrorCode::KeyNotFound), - } - } - } - - fn contains_storage( - &mut self, - memory: &M, - flags: u32, - key_ptr: u32, - key_len: u32, - ) -> Result { - let transient = Self::is_transient(flags)?; - let costs = |len| { - if transient { - RuntimeCosts::ContainsTransientStorage(len) - } else { - RuntimeCosts::ContainsStorage(len) - } - }; - let charged = self.charge_gas(costs(self.ext.max_value_size()))?; - let key = self.decode_key(memory, key_ptr, key_len)?; - let outcome = if transient { - self.ext.get_transient_storage_size(&key) - } else { - self.ext.get_storage_size(&key) - }; - self.adjust_gas(charged, costs(outcome.unwrap_or(0))); - Ok(outcome.unwrap_or(SENTINEL)) - } - - fn take_storage( - &mut self, - memory: &mut M, - flags: u32, - key_ptr: u32, - key_len: u32, - out_ptr: u32, - out_len_ptr: u32, - ) -> Result { - let transient = Self::is_transient(flags)?; - let costs = |len| { - if transient { - RuntimeCosts::TakeTransientStorage(len) - } else { - RuntimeCosts::TakeStorage(len) - } - }; - let charged = self.charge_gas(costs(self.ext.max_value_size()))?; - let key = self.decode_key(memory, key_ptr, key_len)?; - let outcome = if transient { - self.ext.set_transient_storage(&key, None, true)? - } else { - self.ext.set_storage(&key, None, true)? - }; - - if let crate::storage::WriteOutcome::Taken(value) = outcome { - self.adjust_gas(charged, costs(value.len() as u32)); - self.write_sandbox_output( - memory, - out_ptr, - out_len_ptr, - &value, - false, - already_charged, - )?; - Ok(ReturnErrorCode::Success) - } else { - self.adjust_gas(charged, costs(0)); - Ok(ReturnErrorCode::KeyNotFound) - } - } - - fn call( - &mut self, - memory: &mut M, - flags: CallFlags, - call_type: CallType, - callee_ptr: u32, - deposit_ptr: u32, - weight: Weight, - input_data_ptr: u32, - input_data_len: u32, - output_ptr: u32, - output_len_ptr: u32, - ) -> Result { - let callee = memory.read_h160(callee_ptr)?; - let precompile = >::get::(&callee.as_fixed_bytes()); - match &precompile { - Some(precompile) if precompile.has_contract_info() => - self.charge_gas(RuntimeCosts::PrecompileWithInfoBase)?, - Some(_) => self.charge_gas(RuntimeCosts::PrecompileBase)?, - None => self.charge_gas(call_type.cost())?, - }; - - let deposit_limit = memory.read_u256(deposit_ptr)?; - - // we do check this in exec.rs but we want to error out early - if input_data_len > limits::CALLDATA_BYTES { - Err(>::CallDataTooLarge)?; - } - - let input_data = if flags.contains(CallFlags::CLONE_INPUT) { - let input = self.input_data.as_ref().ok_or(Error::::InputForwarded)?; - charge_gas!(self, RuntimeCosts::CallInputCloned(input.len() as u32))?; - input.clone() - } else if flags.contains(CallFlags::FORWARD_INPUT) { - self.input_data.take().ok_or(Error::::InputForwarded)? - } else { - if precompile.is_some() { - self.charge_gas(RuntimeCosts::PrecompileDecode(input_data_len))?; - } else { - self.charge_gas(RuntimeCosts::CopyFromContract(input_data_len))?; - } - memory.read(input_data_ptr, input_data_len)? - }; - - memory.reset_interpreter_cache(); - - let call_outcome = match call_type { - CallType::Call { value_ptr } => { - let read_only = flags.contains(CallFlags::READ_ONLY); - let value = memory.read_u256(value_ptr)?; - if value > 0u32.into() { - // If the call value is non-zero and state change is not allowed, issue an - // error. - if read_only || self.ext.is_read_only() { - return Err(Error::::StateChangeDenied.into()); - } - - self.charge_gas(RuntimeCosts::CallTransferSurcharge { - dust_transfer: Pallet::::has_dust(value), - })?; - } - self.ext.call( - weight, - deposit_limit, - &callee, - value, - input_data, - flags.contains(CallFlags::ALLOW_REENTRY), - read_only, - ) - }, - CallType::DelegateCall => { - if flags.intersects(CallFlags::ALLOW_REENTRY | CallFlags::READ_ONLY) { - return Err(Error::::InvalidCallFlags.into()); - } - self.ext.delegate_call(weight, deposit_limit, callee, input_data) - }, - }; - - match call_outcome { - // `TAIL_CALL` only matters on an `OK` result. Otherwise the call stack comes to - // a halt anyways without anymore code being executed. - Ok(_) if flags.contains(CallFlags::TAIL_CALL) => { - let output = mem::take(self.ext.last_frame_output_mut()); - return Err(TrapReason::Return(ReturnData { - flags: output.flags.bits(), - data: output.data, - })); - }, - Ok(_) => { - let output = mem::take(self.ext.last_frame_output_mut()); - let write_result = self.write_sandbox_output( - memory, - output_ptr, - output_len_ptr, - &output.data, - true, - |len| Some(RuntimeCosts::CopyToContract(len)), - ); - *self.ext.last_frame_output_mut() = output; - write_result?; - Ok(self.ext.last_frame_output().into()) - }, - Err(err) => { - let error_code = Self::exec_error_into_return_code(err)?; - memory.write(output_len_ptr, &0u32.to_le_bytes())?; - Ok(error_code) - }, - } - } - - fn instantiate( - &mut self, - memory: &mut M, - code_hash_ptr: u32, - weight: Weight, - deposit_ptr: u32, - value_ptr: u32, - input_data_ptr: u32, - input_data_len: u32, - address_ptr: u32, - output_ptr: u32, - output_len_ptr: u32, - salt_ptr: u32, - ) -> Result { - let value = match memory.read_u256(value_ptr) { - Ok(value) => { - self.charge_gas(RuntimeCosts::Instantiate { - input_data_len, - balance_transfer: Pallet::::has_balance(value), - dust_transfer: Pallet::::has_dust(value), - })?; - value - }, - Err(err) => { - self.charge_gas(RuntimeCosts::Instantiate { - input_data_len: 0, - balance_transfer: false, - dust_transfer: false, - })?; - return Err(err.into()); - }, - }; - let deposit_limit: U256 = memory.read_u256(deposit_ptr)?; - let code_hash = memory.read_h256(code_hash_ptr)?; - if input_data_len > limits::CALLDATA_BYTES { - Err(>::CallDataTooLarge)?; - } - let input_data = memory.read(input_data_ptr, input_data_len)?; - let salt = if salt_ptr == SENTINEL { - None - } else { - let salt: [u8; 32] = memory.read_array(salt_ptr)?; - Some(salt) - }; - - memory.reset_interpreter_cache(); - - match self.ext.instantiate( - weight, - deposit_limit, - code_hash, - value, - input_data, - salt.as_ref(), - ) { - Ok(address) => { - if !self.ext.last_frame_output().flags.contains(ReturnFlags::REVERT) { - self.write_fixed_sandbox_output( - memory, - address_ptr, - &address.as_bytes(), - true, - already_charged, - )?; - } - let output = mem::take(self.ext.last_frame_output_mut()); - let write_result = self.write_sandbox_output( - memory, - output_ptr, - output_len_ptr, - &output.data, - true, - |len| Some(RuntimeCosts::CopyToContract(len)), - ); - *self.ext.last_frame_output_mut() = output; - write_result?; - Ok(self.ext.last_frame_output().into()) - }, - Err(err) => Ok(Self::exec_error_into_return_code(err)?), - } - } -} - -// This is the API exposed to contracts. -// -// # Note -// -// Any input that leads to a out of bound error (reading or writing) or failing to decode -// data passed to the supervisor will lead to a trap. This is not documented explicitly -// for every function. -#[define_env] -pub mod env { - /// Noop function used to benchmark the time it takes to execute an empty function. - /// - /// Marked as stable because it needs to be called from benchmarks even when the benchmarked - /// parachain has unstable functions disabled. - #[cfg(feature = "runtime-benchmarks")] - #[stable] - fn noop(&mut self, memory: &mut M) -> Result<(), TrapReason> { - Ok(()) - } - - /// Set the value at the given key in the contract storage. - /// See [`pallet_revive_uapi::HostFn::set_storage_v2`] - #[stable] - #[mutating] - fn set_storage( - &mut self, - memory: &mut M, - flags: u32, - key_ptr: u32, - key_len: u32, - value_ptr: u32, - value_len: u32, - ) -> Result { - self.set_storage( - memory, - flags, - key_ptr, - key_len, - StorageValue::Memory { ptr: value_ptr, len: value_len }, - ) - } - - /// Sets the storage at a fixed 256-bit key with a fixed 256-bit value. - /// See [`pallet_revive_uapi::HostFn::set_storage_or_clear`]. - #[stable] - #[mutating] - fn set_storage_or_clear( - &mut self, - memory: &mut M, - flags: u32, - key_ptr: u32, - value_ptr: u32, - ) -> Result { - let value = memory.read(value_ptr, 32)?; - - if value.iter().all(|&b| b == 0) { - self.clear_storage(memory, flags, key_ptr, SENTINEL) - } else { - self.set_storage(memory, flags, key_ptr, SENTINEL, StorageValue::Value(value)) - } - } - - /// Retrieve the value under the given key from storage. - /// See [`pallet_revive_uapi::HostFn::get_storage`] - #[stable] - fn get_storage( - &mut self, - memory: &mut M, - flags: u32, - key_ptr: u32, - key_len: u32, - out_ptr: u32, - out_len_ptr: u32, - ) -> Result { - self.get_storage( - memory, - flags, - key_ptr, - key_len, - out_ptr, - StorageReadMode::VariableOutput { output_len_ptr: out_len_ptr }, - ) - } - - /// Reads the storage at a fixed 256-bit key and writes back a fixed 256-bit value. - /// See [`pallet_revive_uapi::HostFn::get_storage_or_zero`]. - #[stable] - fn get_storage_or_zero( - &mut self, - memory: &mut M, - flags: u32, - key_ptr: u32, - out_ptr: u32, - ) -> Result<(), TrapReason> { - let _ = self.get_storage( - memory, - flags, - key_ptr, - SENTINEL, - out_ptr, - StorageReadMode::FixedOutput32, - )?; - - Ok(()) - } - - /// Make a call to another contract. - /// See [`pallet_revive_uapi::HostFn::call`]. - #[stable] - fn call( - &mut self, - memory: &mut M, - flags_and_callee: u64, - ref_time_limit: u64, - proof_size_limit: u64, - deposit_and_value: u64, - input_data: u64, - output_data: u64, - ) -> Result { - let (flags, callee_ptr) = extract_hi_lo(flags_and_callee); - let (deposit_ptr, value_ptr) = extract_hi_lo(deposit_and_value); - let (input_data_len, input_data_ptr) = extract_hi_lo(input_data); - let (output_len_ptr, output_ptr) = extract_hi_lo(output_data); - - self.call( - memory, - CallFlags::from_bits(flags).ok_or(Error::::InvalidCallFlags)?, - CallType::Call { value_ptr }, - callee_ptr, - deposit_ptr, - Weight::from_parts(ref_time_limit, proof_size_limit), - input_data_ptr, - input_data_len, - output_ptr, - output_len_ptr, - ) - } - - /// Execute code in the context (storage, caller, value) of the current contract. - /// See [`pallet_revive_uapi::HostFn::delegate_call`]. - #[stable] - fn delegate_call( - &mut self, - memory: &mut M, - flags_and_callee: u64, - ref_time_limit: u64, - proof_size_limit: u64, - deposit_ptr: u32, - input_data: u64, - output_data: u64, - ) -> Result { - let (flags, address_ptr) = extract_hi_lo(flags_and_callee); - let (input_data_len, input_data_ptr) = extract_hi_lo(input_data); - let (output_len_ptr, output_ptr) = extract_hi_lo(output_data); - - self.call( - memory, - CallFlags::from_bits(flags).ok_or(Error::::InvalidCallFlags)?, - CallType::DelegateCall, - address_ptr, - deposit_ptr, - Weight::from_parts(ref_time_limit, proof_size_limit), - input_data_ptr, - input_data_len, - output_ptr, - output_len_ptr, - ) - } - - /// Instantiate a contract with the specified code hash. - /// See [`pallet_revive_uapi::HostFn::instantiate`]. - #[stable] - #[mutating] - fn instantiate( - &mut self, - memory: &mut M, - ref_time_limit: u64, - proof_size_limit: u64, - deposit_and_value: u64, - input_data: u64, - output_data: u64, - address_and_salt: u64, - ) -> Result { - let (deposit_ptr, value_ptr) = extract_hi_lo(deposit_and_value); - let (input_data_len, code_hash_ptr) = extract_hi_lo(input_data); - let (output_len_ptr, output_ptr) = extract_hi_lo(output_data); - let (address_ptr, salt_ptr) = extract_hi_lo(address_and_salt); - let Some(input_data_ptr) = code_hash_ptr.checked_add(32) else { - return Err(Error::::OutOfBounds.into()); - }; - let Some(input_data_len) = input_data_len.checked_sub(32) else { - return Err(Error::::OutOfBounds.into()); - }; - - self.instantiate( - memory, - code_hash_ptr, - Weight::from_parts(ref_time_limit, proof_size_limit), - deposit_ptr, - value_ptr, - input_data_ptr, - input_data_len, - address_ptr, - output_ptr, - output_len_ptr, - salt_ptr, - ) - } - - /// Returns the total size of the contract call input data. - /// See [`pallet_revive_uapi::HostFn::call_data_size `]. - #[stable] - fn call_data_size(&mut self, memory: &mut M) -> Result { - self.charge_gas(RuntimeCosts::CallDataSize)?; - Ok(self - .input_data - .as_ref() - .map(|input| input.len().try_into().expect("usize fits into u64; qed")) - .unwrap_or_default()) - } - - /// Stores the input passed by the caller into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::call_data_copy`]. - #[stable] - fn call_data_copy( - &mut self, - memory: &mut M, - out_ptr: u32, - out_len: u32, - offset: u32, - ) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::CallDataCopy(out_len))?; - - let Some(input) = self.input_data.as_ref() else { - return Err(Error::::InputForwarded.into()); - }; - - let start = offset as usize; - if start >= input.len() { - memory.zero(out_ptr, out_len)?; - return Ok(()); - } - - let end = start.saturating_add(out_len as usize).min(input.len()); - memory.write(out_ptr, &input[start..end])?; - - let bytes_written = (end - start) as u32; - memory.zero(out_ptr.saturating_add(bytes_written), out_len - bytes_written)?; - - Ok(()) - } - - /// Stores the U256 value at given call input `offset` into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::call_data_load`]. - #[stable] - fn call_data_load( - &mut self, - memory: &mut M, - out_ptr: u32, - offset: u32, - ) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::CallDataLoad)?; - - let Some(input) = self.input_data.as_ref() else { - return Err(Error::::InputForwarded.into()); - }; - - let mut data = [0; 32]; - let start = offset as usize; - let data = if start >= input.len() { - data // Any index is valid to request; OOB offsets return zero. - } else { - let end = start.saturating_add(32).min(input.len()); - data[..end - start].copy_from_slice(&input[start..end]); - data.reverse(); - data // Solidity expects right-padded data - }; - - self.write_fixed_sandbox_output(memory, out_ptr, &data, false, already_charged)?; - - Ok(()) - } - - /// Cease contract execution and save a data buffer as a result of the execution. - /// See [`pallet_revive_uapi::HostFn::return_value`]. - #[stable] - fn seal_return( - &mut self, - memory: &mut M, - flags: u32, - data_ptr: u32, - data_len: u32, - ) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::CopyFromContract(data_len))?; - if data_len > limits::CALLDATA_BYTES { - Err(>::ReturnDataTooLarge)?; - } - Err(TrapReason::Return(ReturnData { flags, data: memory.read(data_ptr, data_len)? })) - } - - /// Stores the address of the caller into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::caller`]. - #[stable] - fn caller(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::Caller)?; - let caller = ::AddressMapper::to_address(self.ext.caller().account_id()?); - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - caller.as_bytes(), - false, - already_charged, - )?) - } - - /// Stores the address of the call stack origin into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::origin`]. - #[stable] - fn origin(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::Origin)?; - let origin = ::AddressMapper::to_address(self.ext.origin().account_id()?); - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - origin.as_bytes(), - false, - already_charged, - )?) - } - - /// Retrieve the code hash for a specified contract address. - /// See [`pallet_revive_uapi::HostFn::code_hash`]. - #[stable] - fn code_hash(&mut self, memory: &mut M, addr_ptr: u32, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::CodeHash)?; - let address = memory.read_h160(addr_ptr)?; - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &self.ext.code_hash(&address).as_bytes(), - false, - already_charged, - )?) - } - - /// Retrieve the code size for a given contract address. - /// See [`pallet_revive_uapi::HostFn::code_size`]. - #[stable] - fn code_size(&mut self, memory: &mut M, addr_ptr: u32) -> Result { - self.charge_gas(RuntimeCosts::CodeSize)?; - let address = memory.read_h160(addr_ptr)?; - Ok(self.ext.code_size(&address)) - } - - /// Stores the address of the current contract into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::address`]. - #[stable] - fn address(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::Address)?; - let address = self.ext.address(); - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - address.as_bytes(), - false, - already_charged, - )?) - } - - /// Stores the price for the specified amount of weight into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::weight_to_fee`]. - #[stable] - fn weight_to_fee( - &mut self, - memory: &mut M, - ref_time_limit: u64, - proof_size_limit: u64, - out_ptr: u32, - ) -> Result<(), TrapReason> { - let weight = Weight::from_parts(ref_time_limit, proof_size_limit); - self.charge_gas(RuntimeCosts::WeightToFee)?; - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &self.ext.get_weight_price(weight).encode(), - false, - already_charged, - )?) - } - - /// Stores the immutable data into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::get_immutable_data`]. - #[stable] - fn get_immutable_data( - &mut self, - memory: &mut M, - out_ptr: u32, - out_len_ptr: u32, - ) -> Result<(), TrapReason> { - // quering the length is free as it is stored with the contract metadata - let len = self.ext.immutable_data_len(); - self.charge_gas(RuntimeCosts::GetImmutableData(len))?; - let data = self.ext.get_immutable_data()?; - self.write_sandbox_output(memory, out_ptr, out_len_ptr, &data, false, already_charged)?; - Ok(()) - } - - /// Attaches the supplied immutable data to the currently executing contract. - /// See [`pallet_revive_uapi::HostFn::set_immutable_data`]. - #[stable] - fn set_immutable_data(&mut self, memory: &mut M, ptr: u32, len: u32) -> Result<(), TrapReason> { - if len > limits::IMMUTABLE_BYTES { - return Err(Error::::OutOfBounds.into()); - } - self.charge_gas(RuntimeCosts::SetImmutableData(len))?; - let buf = memory.read(ptr, len)?; - let data = buf.try_into().expect("bailed out earlier; qed"); - self.ext.set_immutable_data(data)?; - Ok(()) - } - - /// Stores the *free* balance of the current account into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::balance`]. - #[stable] - fn balance(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::Balance)?; - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &self.ext.balance().to_little_endian(), - false, - already_charged, - )?) - } - - /// Stores the *free* balance of the supplied address into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::balance`]. - #[stable] - fn balance_of( - &mut self, - memory: &mut M, - addr_ptr: u32, - out_ptr: u32, - ) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::BalanceOf)?; - let address = memory.read_h160(addr_ptr)?; - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &self.ext.balance_of(&address).to_little_endian(), - false, - already_charged, - )?) - } - - /// Returns the chain ID. - /// See [`pallet_revive_uapi::HostFn::chain_id`]. - #[stable] - fn chain_id(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &U256::from(::ChainId::get()).to_little_endian(), - false, - |_| Some(RuntimeCosts::CopyToContract(32)), - )?) - } - - /// Returns the block ref_time limit. - /// See [`pallet_revive_uapi::HostFn::gas_limit`]. - #[stable] - fn gas_limit(&mut self, memory: &mut M) -> Result { - self.charge_gas(RuntimeCosts::GasLimit)?; - Ok(::BlockWeights::get().max_block.ref_time()) - } - - /// Stores the value transferred along with this call/instantiate into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::value_transferred`]. - #[stable] - fn value_transferred(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::ValueTransferred)?; - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &self.ext.value_transferred().to_little_endian(), - false, - already_charged, - )?) - } - - /// Returns the simulated ethereum `GASPRICE` value. - /// See [`pallet_revive_uapi::HostFn::gas_price`]. - #[stable] - fn gas_price(&mut self, memory: &mut M) -> Result { - self.charge_gas(RuntimeCosts::GasPrice)?; - Ok(GAS_PRICE.into()) - } - - /// Returns the simulated ethereum `BASEFEE` value. - /// See [`pallet_revive_uapi::HostFn::base_fee`]. - #[stable] - fn base_fee(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::BaseFee)?; - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &U256::zero().to_little_endian(), - false, - already_charged, - )?) - } - - /// Load the latest block timestamp into the supplied buffer - /// See [`pallet_revive_uapi::HostFn::now`]. - #[stable] - fn now(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::Now)?; - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &self.ext.now().to_little_endian(), - false, - already_charged, - )?) - } - - /// Deposit a contract event with the data buffer and optional list of topics. - /// See [pallet_revive_uapi::HostFn::deposit_event] - #[stable] - #[mutating] - fn deposit_event( - &mut self, - memory: &mut M, - topics_ptr: u32, - num_topic: u32, - data_ptr: u32, - data_len: u32, - ) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::DepositEvent { num_topic, len: data_len })?; - - if num_topic > limits::NUM_EVENT_TOPICS { - return Err(Error::::TooManyTopics.into()); - } - - if data_len > self.ext.max_value_size() { - return Err(Error::::ValueTooLarge.into()); - } - - let topics: Vec = match num_topic { - 0 => Vec::new(), - _ => { - let mut v = Vec::with_capacity(num_topic as usize); - let topics_len = num_topic * H256::len_bytes() as u32; - let buf = memory.read(topics_ptr, topics_len)?; - for chunk in buf.chunks_exact(H256::len_bytes()) { - v.push(H256::from_slice(chunk)); - } - v - }, - }; - - let event_data = memory.read(data_ptr, data_len)?; - self.ext.deposit_event(topics, event_data); - Ok(()) - } - - /// Stores the current block number of the current contract into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::block_number`]. - #[stable] - fn block_number(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::BlockNumber)?; - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &self.ext.block_number().to_little_endian(), - false, - already_charged, - )?) - } - - /// Stores the block hash at given block height into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::block_hash`]. - #[stable] - fn block_hash( - &mut self, - memory: &mut M, - block_number_ptr: u32, - out_ptr: u32, - ) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::BlockHash)?; - let block_number = memory.read_u256(block_number_ptr)?; - let block_hash = self.ext.block_hash(block_number).unwrap_or(H256::zero()); - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &block_hash.as_bytes(), - false, - already_charged, - )?) - } - - /// Stores the current block author into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::block_author`]. - #[stable] - fn block_author(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::BlockAuthor)?; - let block_author = self.ext.block_author().unwrap_or(H160::zero()); - - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &block_author.as_bytes(), - false, - already_charged, - )?) - } - - /// Computes the KECCAK 256-bit hash on the given input buffer. - /// See [`pallet_revive_uapi::HostFn::hash_keccak_256`]. - #[stable] - fn hash_keccak_256( - &mut self, - memory: &mut M, - input_ptr: u32, - input_len: u32, - output_ptr: u32, - ) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::HashKeccak256(input_len))?; - Ok(self.compute_hash_on_intermediate_buffer( - memory, keccak_256, input_ptr, input_len, output_ptr, - )?) - } - - /// Stores the length of the data returned by the last call into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::return_data_size`]. - #[stable] - fn return_data_size(&mut self, memory: &mut M) -> Result { - self.charge_gas(RuntimeCosts::ReturnDataSize)?; - Ok(self - .ext - .last_frame_output() - .data - .len() - .try_into() - .expect("usize fits into u64; qed")) - } - - /// Stores data returned by the last call, starting from `offset`, into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::return_data`]. - #[stable] - fn return_data_copy( - &mut self, - memory: &mut M, - out_ptr: u32, - out_len_ptr: u32, - offset: u32, - ) -> Result<(), TrapReason> { - let output = mem::take(self.ext.last_frame_output_mut()); - let result = if offset as usize > output.data.len() { - Err(Error::::OutOfBounds.into()) - } else { - self.write_sandbox_output( - memory, - out_ptr, - out_len_ptr, - &output.data[offset as usize..], - false, - |len| Some(RuntimeCosts::CopyToContract(len)), - ) - }; - *self.ext.last_frame_output_mut() = output; - Ok(result?) - } - - /// Returns the amount of ref_time left. - /// See [`pallet_revive_uapi::HostFn::ref_time_left`]. - #[stable] - fn ref_time_left(&mut self, memory: &mut M) -> Result { - self.charge_gas(RuntimeCosts::RefTimeLeft)?; - Ok(self.ext.gas_meter().gas_left().ref_time()) - } - - /// Checks whether the caller of the current contract is the origin of the whole call stack. - /// See [`pallet_revive_uapi::HostFn::caller_is_origin`]. - fn caller_is_origin(&mut self, _memory: &mut M) -> Result { - self.charge_gas(RuntimeCosts::CallerIsOrigin)?; - Ok(self.ext.caller_is_origin() as u32) - } - - /// Checks whether the caller of the current contract is root. - /// See [`pallet_revive_uapi::HostFn::caller_is_root`]. - fn caller_is_root(&mut self, _memory: &mut M) -> Result { - self.charge_gas(RuntimeCosts::CallerIsRoot)?; - Ok(self.ext.caller_is_root() as u32) - } - - /// Clear the value at the given key in the contract storage. - /// See [`pallet_revive_uapi::HostFn::clear_storage`] - #[mutating] - fn clear_storage( - &mut self, - memory: &mut M, - flags: u32, - key_ptr: u32, - key_len: u32, - ) -> Result { - self.clear_storage(memory, flags, key_ptr, key_len) - } - - /// Checks whether there is a value stored under the given key. - /// See [`pallet_revive_uapi::HostFn::contains_storage`] - fn contains_storage( - &mut self, - memory: &mut M, - flags: u32, - key_ptr: u32, - key_len: u32, - ) -> Result { - self.contains_storage(memory, flags, key_ptr, key_len) - } - - /// Calculates Ethereum address from the ECDSA compressed public key and stores - /// See [`pallet_revive_uapi::HostFn::ecdsa_to_eth_address`]. - fn ecdsa_to_eth_address( - &mut self, - memory: &mut M, - key_ptr: u32, - out_ptr: u32, - ) -> Result { - self.charge_gas(RuntimeCosts::EcdsaToEthAddress)?; - let mut compressed_key: [u8; 33] = [0; 33]; - memory.read_into_buf(key_ptr, &mut compressed_key)?; - let result = self.ext.ecdsa_to_eth_address(&compressed_key); - match result { - Ok(eth_address) => { - memory.write(out_ptr, eth_address.as_ref())?; - Ok(ReturnErrorCode::Success) - }, - Err(_) => Ok(ReturnErrorCode::EcdsaRecoveryFailed), - } - } - - /// Stores the minimum balance (a.k.a. existential deposit) into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::minimum_balance`]. - fn minimum_balance(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::MinimumBalance)?; - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - &self.ext.minimum_balance().to_little_endian(), - false, - already_charged, - )?) - } - - /// Retrieve the code hash of the currently executing contract. - /// See [`pallet_revive_uapi::HostFn::own_code_hash`]. - fn own_code_hash(&mut self, memory: &mut M, out_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::OwnCodeHash)?; - let code_hash = *self.ext.own_code_hash(); - Ok(self.write_fixed_sandbox_output( - memory, - out_ptr, - code_hash.as_bytes(), - false, - already_charged, - )?) - } - - /// Replace the contract code at the specified address with new code. - /// See [`pallet_revive_uapi::HostFn::set_code_hash`]. - /// - /// Disabled until the internal implementation takes care of collecting - /// the immutable data of the new code hash. - #[mutating] - fn set_code_hash(&mut self, memory: &mut M, code_hash_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::SetCodeHash)?; - let code_hash: H256 = memory.read_h256(code_hash_ptr)?; - self.ext.set_code_hash(code_hash)?; - Ok(()) - } - - /// Verify a sr25519 signature - /// See [`pallet_revive_uapi::HostFn::sr25519_verify`]. - fn sr25519_verify( - &mut self, - memory: &mut M, - signature_ptr: u32, - pub_key_ptr: u32, - message_len: u32, - message_ptr: u32, - ) -> Result { - self.charge_gas(RuntimeCosts::Sr25519Verify(message_len))?; - - let mut signature: [u8; 64] = [0; 64]; - memory.read_into_buf(signature_ptr, &mut signature)?; - - let mut pub_key: [u8; 32] = [0; 32]; - memory.read_into_buf(pub_key_ptr, &mut pub_key)?; - - let message: Vec = memory.read(message_ptr, message_len)?; - - if self.ext.sr25519_verify(&signature, &message, &pub_key) { - Ok(ReturnErrorCode::Success) - } else { - Ok(ReturnErrorCode::Sr25519VerifyFailed) - } - } - - /// Retrieve and remove the value under the given key from storage. - /// See [`pallet_revive_uapi::HostFn::take_storage`] - #[mutating] - fn take_storage( - &mut self, - memory: &mut M, - flags: u32, - key_ptr: u32, - key_len: u32, - out_ptr: u32, - out_len_ptr: u32, - ) -> Result { - self.take_storage(memory, flags, key_ptr, key_len, out_ptr, out_len_ptr) - } - - /// Remove the calling account and transfer remaining **free** balance. - /// See [`pallet_revive_uapi::HostFn::terminate`]. - #[mutating] - fn terminate(&mut self, memory: &mut M, beneficiary_ptr: u32) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::Terminate)?; - let beneficiary = memory.read_h160(beneficiary_ptr)?; - self.ext.terminate(&beneficiary)?; - Err(TrapReason::Termination) - } - - /// Stores the amount of weight left into the supplied buffer. - /// See [`pallet_revive_uapi::HostFn::weight_left`]. - fn weight_left( - &mut self, - memory: &mut M, - out_ptr: u32, - out_len_ptr: u32, - ) -> Result<(), TrapReason> { - self.charge_gas(RuntimeCosts::WeightLeft)?; - let gas_left = &self.ext.gas_meter().gas_left().encode(); - Ok(self.write_sandbox_output( - memory, - out_ptr, - out_len_ptr, - gas_left, - false, - already_charged, - )?) - } -} diff --git a/substrate/frame/revive/src/vm/runtime_costs.rs b/substrate/frame/revive/src/vm/runtime_costs.rs new file mode 100644 index 0000000000000..7c71a1bb1b933 --- /dev/null +++ b/substrate/frame/revive/src/vm/runtime_costs.rs @@ -0,0 +1,315 @@ +// This file is part of Substrate. + +// Copyright (C) Parity Technologies (UK) Ltd. +// SPDX-License-Identifier: Apache-2.0 + +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +use crate::{gas::Token, weights::WeightInfo, Config}; +use frame_support::weights::{constants::WEIGHT_REF_TIME_PER_SECOND, Weight}; + +/// Current approximation of the gas/s consumption considering +/// EVM execution over compiled WASM (on 4.4Ghz CPU). +/// Given the 2000ms Weight, from which 75% only are used for transactions, +/// the total EVM execution gas limit is: GAS_PER_SECOND * 2 * 0.75 ~= 60_000_000. +const GAS_PER_SECOND: u64 = 40_000_000; + +/// Approximate ratio of the amount of Weight per Gas. +/// u64 works for approximations because Weight is a very small unit compared to +/// gas. +const WEIGHT_PER_GAS: u64 = WEIGHT_REF_TIME_PER_SECOND / GAS_PER_SECOND; + +#[cfg_attr(test, derive(Debug, PartialEq, Eq))] +#[derive(Copy, Clone)] +pub enum RuntimeCosts { + /// Base Weight of calling a host function. + HostFn, + /// Weight charged for copying data from the sandbox. + CopyFromContract(u32), + /// Weight charged for copying data to the sandbox. + CopyToContract(u32), + /// Weight of calling `seal_call_data_load``. + CallDataLoad, + /// Weight of calling `seal_call_data_copy`. + CallDataCopy(u32), + /// Weight of calling `seal_caller`. + Caller, + /// Weight of calling `seal_call_data_size`. + CallDataSize, + /// Weight of calling `seal_return_data_size`. + ReturnDataSize, + /// Weight of calling `seal_to_account_id`. + ToAccountId, + /// Weight of calling `seal_origin`. + Origin, + /// Weight of calling `seal_code_hash`. + CodeHash, + /// Weight of calling `seal_own_code_hash`. + OwnCodeHash, + /// Weight of calling `seal_code_size`. + CodeSize, + /// Weight of calling `seal_caller_is_origin`. + CallerIsOrigin, + /// Weight of calling `caller_is_root`. + CallerIsRoot, + /// Weight of calling `seal_address`. + Address, + /// Weight of calling `seal_ref_time_left`. + RefTimeLeft, + /// Weight of calling `seal_weight_left`. + WeightLeft, + /// Weight of calling `seal_balance`. + Balance, + /// Weight of calling `seal_balance_of`. + BalanceOf, + /// Weight of calling `seal_value_transferred`. + ValueTransferred, + /// Weight of calling `seal_minimum_balance`. + MinimumBalance, + /// Weight of calling `seal_block_number`. + BlockNumber, + /// Weight of calling `seal_block_hash`. + BlockHash, + /// Weight of calling `seal_block_author`. + BlockAuthor, + /// Weight of calling `seal_gas_price`. + GasPrice, + /// Weight of calling `seal_base_fee`. + BaseFee, + /// Weight of calling `seal_now`. + Now, + /// Weight of calling `seal_gas_limit`. + GasLimit, + /// Weight of calling `seal_weight_to_fee`. + WeightToFee, + /// Weight of calling `seal_terminate`. + Terminate, + /// Weight of calling `seal_deposit_event` with the given number of topics and event size. + DepositEvent { num_topic: u32, len: u32 }, + /// Weight of calling `seal_set_storage` for the given storage item sizes. + SetStorage { old_bytes: u32, new_bytes: u32 }, + /// Weight of calling `seal_clear_storage` per cleared byte. + ClearStorage(u32), + /// Weight of calling `seal_contains_storage` per byte of the checked item. + ContainsStorage(u32), + /// Weight of calling `seal_get_storage` with the specified size in storage. + GetStorage(u32), + /// Weight of calling `seal_take_storage` for the given size. + TakeStorage(u32), + /// Weight of calling `seal_set_transient_storage` for the given storage item sizes. + SetTransientStorage { old_bytes: u32, new_bytes: u32 }, + /// Weight of calling `seal_clear_transient_storage` per cleared byte. + ClearTransientStorage(u32), + /// Weight of calling `seal_contains_transient_storage` per byte of the checked item. + ContainsTransientStorage(u32), + /// Weight of calling `seal_get_transient_storage` with the specified size in storage. + GetTransientStorage(u32), + /// Weight of calling `seal_take_transient_storage` for the given size. + TakeTransientStorage(u32), + /// Base weight of calling `seal_call`. + CallBase, + /// Weight of calling `seal_delegate_call` for the given input size. + DelegateCallBase, + /// Weight of calling a precompile. + PrecompileBase, + /// Weight of calling a precompile that has a contract info. + PrecompileWithInfoBase, + /// Weight of reading and decoding the input to a precompile. + PrecompileDecode(u32), + /// Weight of the transfer performed during a call. + /// parameter `dust_transfer` indicates whether the transfer has a `dust` value. + CallTransferSurcharge { dust_transfer: bool }, + /// Weight per byte that is cloned by supplying the `CLONE_INPUT` flag. + CallInputCloned(u32), + /// Weight of calling `seal_instantiate`. + Instantiate { input_data_len: u32, balance_transfer: bool, dust_transfer: bool }, + /// Weight of calling `Ripemd160` precompile for the given input size. + Ripemd160(u32), + /// Weight of calling `Sha256` precompile for the given input size. + HashSha256(u32), + /// Weight of calling the `System::hashBlake256` precompile function for the given input + HashKeccak256(u32), + /// Weight of calling the `System::hash_blake2_256` precompile function for the given input + /// size. + HashBlake256(u32), + /// Weight of calling `System::hashBlake128` precompile function for the given input size. + HashBlake128(u32), + /// Weight of calling `ECERecover` precompile. + EcdsaRecovery, + /// Weight of calling `seal_sr25519_verify` for the given input size. + Sr25519Verify(u32), + /// Weight charged by a precompile. + Precompile(Weight), + /// Weight of calling `seal_set_code_hash` + SetCodeHash, + /// Weight of calling `ecdsa_to_eth_address` + EcdsaToEthAddress, + /// Weight of calling `get_immutable_dependency` + GetImmutableData(u32), + /// Weight of calling `set_immutable_dependency` + SetImmutableData(u32), + /// Weight of calling `Bn128Add` precompile + Bn128Add, + /// Weight of calling `Bn128Add` precompile + Bn128Mul, + /// Weight of calling `Bn128Pairing` precompile for the given number of input pairs. + Bn128Pairing(u32), + /// Weight of calling `Identity` precompile for the given number of input length. + Identity(u32), + /// Weight of calling `Blake2F` precompile for the given number of rounds. + Blake2F(u32), + /// Weight of calling `Modexp` precompile + Modexp(u64), +} + +/// For functions that modify storage, benchmarks are performed with one item in the +/// storage. To account for the worst-case scenario, the weight of the overhead of +/// writing to or reading from full storage is included. For transient storage writes, +/// the rollback weight is added to reflect the worst-case scenario for this operation. +macro_rules! cost_storage { + (write_transient, $name:ident $(, $arg:expr )*) => { + T::WeightInfo::$name($( $arg ),*) + .saturating_add(T::WeightInfo::rollback_transient_storage()) + .saturating_add(T::WeightInfo::set_transient_storage_full() + .saturating_sub(T::WeightInfo::set_transient_storage_empty())) + }; + + (read_transient, $name:ident $(, $arg:expr )*) => { + T::WeightInfo::$name($( $arg ),*) + .saturating_add(T::WeightInfo::get_transient_storage_full() + .saturating_sub(T::WeightInfo::get_transient_storage_empty())) + }; + + (write, $name:ident $(, $arg:expr )*) => { + T::WeightInfo::$name($( $arg ),*) + .saturating_add(T::WeightInfo::set_storage_full() + .saturating_sub(T::WeightInfo::set_storage_empty())) + }; + + (read, $name:ident $(, $arg:expr )*) => { + T::WeightInfo::$name($( $arg ),*) + .saturating_add(T::WeightInfo::get_storage_full() + .saturating_sub(T::WeightInfo::get_storage_empty())) + }; +} + +macro_rules! cost_args { + // cost_args!(name, a, b, c) -> T::WeightInfo::name(a, b, c).saturating_sub(T::WeightInfo::name(0, 0, 0)) + ($name:ident, $( $arg: expr ),+) => { + (T::WeightInfo::$name($( $arg ),+).saturating_sub(cost_args!(@call_zero $name, $( $arg ),+))) + }; + // Transform T::WeightInfo::name(a, b, c) into T::WeightInfo::name(0, 0, 0) + (@call_zero $name:ident, $( $arg:expr ),*) => { + T::WeightInfo::$name($( cost_args!(@replace_token $arg) ),*) + }; + // Replace the token with 0. + (@replace_token $_in:tt) => { 0 }; +} + +impl Token for RuntimeCosts { + fn influence_lowest_gas_limit(&self) -> bool { + true + } + + fn weight(&self) -> Weight { + use self::RuntimeCosts::*; + match *self { + HostFn => cost_args!(noop_host_fn, 1), + CopyToContract(len) => T::WeightInfo::seal_copy_to_contract(len), + CopyFromContract(len) => T::WeightInfo::seal_return(len), + CallDataSize => T::WeightInfo::seal_call_data_size(), + ReturnDataSize => T::WeightInfo::seal_return_data_size(), + CallDataLoad => T::WeightInfo::seal_call_data_load(), + CallDataCopy(len) => T::WeightInfo::seal_call_data_copy(len), + Caller => T::WeightInfo::seal_caller(), + Origin => T::WeightInfo::seal_origin(), + ToAccountId => T::WeightInfo::seal_to_account_id(), + CodeHash => T::WeightInfo::seal_code_hash(), + CodeSize => T::WeightInfo::seal_code_size(), + OwnCodeHash => T::WeightInfo::seal_own_code_hash(), + CallerIsOrigin => T::WeightInfo::seal_caller_is_origin(), + CallerIsRoot => T::WeightInfo::seal_caller_is_root(), + Address => T::WeightInfo::seal_address(), + RefTimeLeft => T::WeightInfo::seal_ref_time_left(), + WeightLeft => T::WeightInfo::seal_weight_left(), + Balance => T::WeightInfo::seal_balance(), + BalanceOf => T::WeightInfo::seal_balance_of(), + ValueTransferred => T::WeightInfo::seal_value_transferred(), + MinimumBalance => T::WeightInfo::seal_minimum_balance(), + BlockNumber => T::WeightInfo::seal_block_number(), + BlockHash => T::WeightInfo::seal_block_hash(), + BlockAuthor => T::WeightInfo::seal_block_author(), + GasPrice => T::WeightInfo::seal_gas_price(), + BaseFee => T::WeightInfo::seal_base_fee(), + Now => T::WeightInfo::seal_now(), + GasLimit => T::WeightInfo::seal_gas_limit(), + WeightToFee => T::WeightInfo::seal_weight_to_fee(), + Terminate => T::WeightInfo::seal_terminate(), + DepositEvent { num_topic, len } => T::WeightInfo::seal_deposit_event(num_topic, len), + SetStorage { new_bytes, old_bytes } => { + cost_storage!(write, seal_set_storage, new_bytes, old_bytes) + }, + ClearStorage(len) => cost_storage!(write, seal_clear_storage, len), + ContainsStorage(len) => cost_storage!(read, seal_contains_storage, len), + GetStorage(len) => cost_storage!(read, seal_get_storage, len), + TakeStorage(len) => cost_storage!(write, seal_take_storage, len), + SetTransientStorage { new_bytes, old_bytes } => { + cost_storage!(write_transient, seal_set_transient_storage, new_bytes, old_bytes) + }, + ClearTransientStorage(len) => { + cost_storage!(write_transient, seal_clear_transient_storage, len) + }, + ContainsTransientStorage(len) => { + cost_storage!(read_transient, seal_contains_transient_storage, len) + }, + GetTransientStorage(len) => { + cost_storage!(read_transient, seal_get_transient_storage, len) + }, + TakeTransientStorage(len) => { + cost_storage!(write_transient, seal_take_transient_storage, len) + }, + CallBase => T::WeightInfo::seal_call(0, 0, 0), + DelegateCallBase => T::WeightInfo::seal_delegate_call(), + PrecompileBase => T::WeightInfo::seal_call_precompile(0, 0), + PrecompileWithInfoBase => T::WeightInfo::seal_call_precompile(1, 0), + PrecompileDecode(len) => cost_args!(seal_call_precompile, 0, len), + CallTransferSurcharge { dust_transfer } => + cost_args!(seal_call, 1, dust_transfer.into(), 0), + CallInputCloned(len) => cost_args!(seal_call, 0, 0, len), + Instantiate { input_data_len, balance_transfer, dust_transfer } => + T::WeightInfo::seal_instantiate( + input_data_len, + balance_transfer.into(), + dust_transfer.into(), + ), + HashSha256(len) => T::WeightInfo::sha2_256(len), + Ripemd160(len) => T::WeightInfo::ripemd_160(len), + HashKeccak256(len) => T::WeightInfo::seal_hash_keccak_256(len), + HashBlake256(len) => T::WeightInfo::hash_blake2_256(len), + HashBlake128(len) => T::WeightInfo::hash_blake2_128(len), + EcdsaRecovery => T::WeightInfo::ecdsa_recover(), + Sr25519Verify(len) => T::WeightInfo::seal_sr25519_verify(len), + Precompile(weight) => weight, + SetCodeHash => T::WeightInfo::seal_set_code_hash(), + EcdsaToEthAddress => T::WeightInfo::seal_ecdsa_to_eth_address(), + GetImmutableData(len) => T::WeightInfo::seal_get_immutable_data(len), + SetImmutableData(len) => T::WeightInfo::seal_set_immutable_data(len), + Bn128Add => T::WeightInfo::bn128_add(), + Bn128Mul => T::WeightInfo::bn128_mul(), + Bn128Pairing(len) => T::WeightInfo::bn128_pairing(len), + Identity(len) => T::WeightInfo::identity(len), + Blake2F(rounds) => T::WeightInfo::blake2f(rounds), + Modexp(gas) => Weight::from_parts(gas.saturating_mul(WEIGHT_PER_GAS), 0), + } + } +} diff --git a/substrate/frame/root-offences/Cargo.toml b/substrate/frame/root-offences/Cargo.toml index 5a28ae7b9697e..d5025d1214172 100644 --- a/substrate/frame/root-offences/Cargo.toml +++ b/substrate/frame/root-offences/Cargo.toml @@ -59,6 +59,7 @@ runtime-benchmarks = [ "frame-support/runtime-benchmarks", "frame-system/runtime-benchmarks", "pallet-balances/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "sp-runtime/runtime-benchmarks", diff --git a/substrate/frame/session/Cargo.toml b/substrate/frame/session/Cargo.toml index 18905d6a56a2d..d754371c38f1f 100644 --- a/substrate/frame/session/Cargo.toml +++ b/substrate/frame/session/Cargo.toml @@ -58,3 +58,11 @@ try-runtime = [ "pallet-timestamp/try-runtime", "sp-runtime/try-runtime", ] +runtime-benchmarks = [ + "frame-support/runtime-benchmarks", + "frame-system/runtime-benchmarks", + "pallet-balances/runtime-benchmarks", + "pallet-timestamp/runtime-benchmarks", + "sp-runtime/runtime-benchmarks", + "sp-staking/runtime-benchmarks", +] diff --git a/substrate/frame/session/benchmarking/Cargo.toml b/substrate/frame/session/benchmarking/Cargo.toml index 1fa7e76bc29b7..384c452364d21 100644 --- a/substrate/frame/session/benchmarking/Cargo.toml +++ b/substrate/frame/session/benchmarking/Cargo.toml @@ -56,6 +56,7 @@ runtime-benchmarks = [ "frame-support/runtime-benchmarks", "frame-system/runtime-benchmarks", "pallet-balances/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "sp-runtime/runtime-benchmarks", diff --git a/substrate/frame/session/benchmarking/src/inner.rs b/substrate/frame/session/benchmarking/src/inner.rs index f3707763f3509..bcff238d4ea0a 100644 --- a/substrate/frame/session/benchmarking/src/inner.rs +++ b/substrate/frame/session/benchmarking/src/inner.rs @@ -23,7 +23,10 @@ use sp_runtime::traits::{One, StaticLookup, TrailingZeroInput}; use codec::Decode; use frame_benchmarking::v2::*; -use frame_support::traits::{Get, KeyOwnerProofSystem, OnInitialize}; +use frame_support::{ + assert_ok, + traits::{Get, KeyOwnerProofSystem, OnInitialize}, +}; use frame_system::{pallet_prelude::BlockNumberFor, RawOrigin}; use pallet_session::{historical::Pallet as Historical, Pallet as Session, *}; use pallet_staking::{ @@ -66,6 +69,7 @@ mod benchmarks { // Whitelist controller account from further DB operations. let v_controller_key = frame_system::Account::::hashed_key_for(&v_controller); frame_benchmarking::benchmarking::add_to_whitelist(v_controller_key.into()); + assert_ok!(Session::::ensure_can_pay_key_deposit(&v_controller)); #[extrinsic_call] _(RawOrigin::Signed(v_controller), keys, proof); @@ -86,6 +90,7 @@ mod benchmarks { let v_controller = pallet_staking::Pallet::::bonded(&v_stash).ok_or("not stash")?; let keys = T::Keys::decode(&mut TrailingZeroInput::zeroes()).unwrap(); let proof: Vec = vec![0, 1, 2, 3]; + assert_ok!(Session::::ensure_can_pay_key_deposit(&v_controller)); Session::::set_keys(RawOrigin::Signed(v_controller.clone()).into(), keys, proof)?; // Whitelist controller account from further DB operations. let v_controller_key = frame_system::Account::::hashed_key_for(&v_controller); diff --git a/substrate/frame/session/benchmarking/src/mock.rs b/substrate/frame/session/benchmarking/src/mock.rs index 288bf56ad25ee..5910772e6d0fa 100644 --- a/substrate/frame/session/benchmarking/src/mock.rs +++ b/substrate/frame/session/benchmarking/src/mock.rs @@ -107,7 +107,9 @@ impl pallet_session::Config for Test { type DisablingStrategy = (); type WeightInfo = (); type Currency = Balances; - type KeyDeposit = (); + // Note: setting to a large amount to ensure bench setup can handle increasing the balance of + // the validator before setting session keys; see `ensure_can_pay_key_deposit`. + type KeyDeposit = ConstU64<2000000000>; } pallet_staking_reward_curve::build! { const I_NPOS: sp_runtime::curve::PiecewiseLinear<'static> = curve!( diff --git a/substrate/frame/session/src/lib.rs b/substrate/frame/session/src/lib.rs index bfa7540132293..ffafbd540d18f 100644 --- a/substrate/frame/session/src/lib.rs +++ b/substrate/frame/session/src/lib.rs @@ -129,7 +129,7 @@ use frame_support::{ dispatch::DispatchResult, ensure, traits::{ - fungible::{hold::Mutate as HoldMutate, Inspect}, + fungible::{hold::Mutate as HoldMutate, Inspect, Mutate}, Defensive, EstimateNextNewSession, EstimateNextSessionRotation, FindAuthor, Get, OneSessionHandler, ValidatorRegistration, ValidatorSet, }, @@ -447,7 +447,7 @@ pub mod pallet { type WeightInfo: WeightInfo; /// The currency type for placing holds when setting keys. - type Currency: Inspect + type Currency: Mutate + HoldMutate>; /// The amount to be held when setting keys. @@ -668,6 +668,25 @@ pub mod pallet { Ok(()) } } + + #[cfg(feature = "runtime-benchmarks")] + impl Pallet { + /// Mint enough funds into `who`, such that they can pay the session key setting deposit. + /// + /// Meant to be used if any pallet's benchmarking code wishes to set session keys, and wants + /// to make sure it will succeed. + pub fn ensure_can_pay_key_deposit(who: &T::AccountId) -> Result<(), DispatchError> { + use frame_support::traits::tokens::{Fortitude, Preservation}; + let deposit = T::KeyDeposit::get(); + let has = T::Currency::reducible_balance(who, Preservation::Protect, Fortitude::Force); + if let Some(deficit) = deposit.checked_sub(&has) { + T::Currency::mint_into(who, deficit.max(T::Currency::minimum_balance())) + .map(|_inc| ()) + } else { + Ok(()) + } + } + } } impl Pallet { diff --git a/substrate/frame/society/src/lib.rs b/substrate/frame/society/src/lib.rs index 5590ccf7e3e0a..9be673f2e1daa 100644 --- a/substrate/frame/society/src/lib.rs +++ b/substrate/frame/society/src/lib.rs @@ -519,13 +519,14 @@ pub mod pallet { #[pallet::constant] type PeriodSpend: Get>; - /// The number of blocks on which new candidates should be voted on. Together with + /// The number of [Config::BlockNumberProvider] blocks on which new candidates should be + /// voted on. Together with /// `ClaimPeriod`, this sums to the number of blocks between candidate intake periods. #[pallet::constant] type VotingPeriod: Get>; - /// The number of blocks on which new candidates can claim their membership and be the - /// named head. + /// The number of [Config::BlockNumberProvider] blocks on which new candidates can claim + /// their membership and be the named head. #[pallet::constant] type ClaimPeriod: Get>; @@ -536,9 +537,9 @@ pub mod pallet { /// The origin that is allowed to call `found`. type FounderSetOrigin: EnsureOrigin; - /// The number of blocks between membership challenges. + /// The number of [Config::BlockNumberProvider] blocks between membership challenges. #[pallet::constant] - type ChallengePeriod: Get>; + type ChallengePeriod: Get>; /// The maximum number of payouts a member may have waiting unclaimed. #[pallet::constant] @@ -784,11 +785,20 @@ pub mod pallet { pub type DefenderVotes, I: 'static = ()> = StorageDoubleMap<_, Twox64Concat, RoundIndex, Twox64Concat, T::AccountId, Vote>; + /// Next intake rotation scheduled with [Config::BlockNumberProvider]. + #[pallet::storage] + pub type NextIntakeAt, I: 'static = ()> = StorageValue<_, BlockNumberFor>; + + /// Next challenge rotation scheduled with [Config::BlockNumberProvider]. + #[pallet::storage] + pub type NextChallengeAt, I: 'static = ()> = StorageValue<_, BlockNumberFor>; + #[pallet::hooks] impl, I: 'static> Hooks> for Pallet { - fn on_initialize(n: SystemBlockNumberFor) -> Weight { + fn on_initialize(_n: SystemBlockNumberFor) -> Weight { let mut weight = Weight::zero(); let weights = T::BlockWeights::get(); + let now = T::BlockNumberProvider::current_block_number(); let phrase = b"society_rotation"; // we'll need a random seed here. @@ -801,18 +811,21 @@ pub mod pallet { let mut rng = ChaChaRng::from_seed(seed); // Run a candidate/membership rotation - match Self::period() { - Period::Voting { elapsed, .. } if elapsed.is_zero() => { - Self::rotate_intake(&mut rng); - weight.saturating_accrue(weights.max_block / 20); - }, - _ => {}, + let is_intake_moment = match Self::period() { + Period::Intake { .. } => true, + _ => false, + }; + if is_intake_moment { + Self::rotate_intake(&mut rng); + weight.saturating_accrue(weights.max_block / 20); + Self::set_next_intake_at(); } // Run a challenge rotation - if (n % T::ChallengePeriod::get()).is_zero() { + if now >= Self::next_challenge_at() { Self::rotate_challenge(&mut rng); weight.saturating_accrue(weights.max_block / 20); + Self::set_next_challenge_at(); } weight @@ -1475,9 +1488,11 @@ impl_ensure_origin_with_arg_ignoring_arg! { {} } +#[derive(Debug, PartialEq, Eq)] pub enum Period { Voting { elapsed: BlockNumber, more: BlockNumber }, Claim { elapsed: BlockNumber, more: BlockNumber }, + Intake { elapsed: BlockNumber }, } impl, I: 'static> Pallet { @@ -1488,13 +1503,72 @@ impl, I: 'static> Pallet { let rotation_period = voting_period + claim_period; let now = T::BlockNumberProvider::current_block_number(); let phase = now % rotation_period; - if phase < voting_period { + if now >= Self::next_intake_at() { + Period::Intake { elapsed: now - Self::next_intake_at() } + } else if phase < voting_period { Period::Voting { elapsed: phase, more: voting_period - phase } } else { Period::Claim { elapsed: phase - voting_period, more: rotation_period - phase } } } + /// Next intake (candidate/membership) rotation scheduled with [Config::BlockNumberProvider]. + /// + /// Rounds the previous block number up to the next rotation period (voting + claim periods). + pub fn next_intake_at() -> BlockNumberFor { + match NextIntakeAt::::get() { + Some(next) => next, + None => { + // executed once. + let now = T::BlockNumberProvider::current_block_number(); + let prev_block = now.saturating_sub(BlockNumberFor::::one()); + let rotation_period = T::VotingPeriod::get().saturating_add(T::ClaimPeriod::get()); + let elapsed = prev_block % rotation_period; + let next_intake_at = prev_block + (rotation_period - elapsed); + NextIntakeAt::::put(next_intake_at); + next_intake_at + }, + } + } + + /// Set the next intake (candidate/membership) rotation. + /// + /// This supposed to be called once the current intake is executed. + fn set_next_intake_at() { + let prev_next_intake_at = Self::next_intake_at(); + let next_intake_at = prev_next_intake_at + .saturating_add(T::VotingPeriod::get().saturating_add(T::ClaimPeriod::get())); + NextIntakeAt::::put(next_intake_at); + } + + /// Returns the next challenge rotation scheduled with [Config::BlockNumberProvider]. + /// + /// Rounds the previous block number up to the next multiple of the challenge duration. + pub fn next_challenge_at() -> BlockNumberFor { + match NextChallengeAt::::get() { + Some(next) => next, + None => { + // executed once. + let now = T::BlockNumberProvider::current_block_number(); + let prev_block = now.saturating_sub(BlockNumberFor::::one()); + let challenge_period = T::ChallengePeriod::get(); + let elapsed = prev_block % challenge_period; + let next_challenge_at = prev_block + (challenge_period - elapsed); + NextChallengeAt::::put(next_challenge_at); + next_challenge_at + }, + } + } + + /// Set the next challenge rotation. + /// + /// This supposed to be called once the current challenge is executed. + fn set_next_challenge_at() { + let prev_next_challenge_at = Self::next_challenge_at(); + let next_challenge_at = prev_next_challenge_at.saturating_add(T::ChallengePeriod::get()); + NextChallengeAt::::put(next_challenge_at); + } + /// Returns true if the given `target_round` is still in its initial voting phase. fn in_progress(target_round: RoundIndex) -> bool { let round = RoundCount::::get(); diff --git a/substrate/frame/society/src/mock.rs b/substrate/frame/society/src/mock.rs index b203dc981769e..de3fb151d8d88 100644 --- a/substrate/frame/society/src/mock.rs +++ b/substrate/frame/society/src/mock.rs @@ -48,6 +48,7 @@ parameter_types! { ord_parameter_types! { pub const ChallengePeriod: u64 = 8; pub const ClaimPeriod: u64 = 1; + pub const VotingPeriod: u64 = 3; pub const FounderSetAccount: u128 = 1; pub const SuspensionJudgementSetAccount: u128 = 2; pub const MaxPayouts: u32 = 10; @@ -75,7 +76,7 @@ impl Config for Test { type Randomness = TestRandomness; type GraceStrikes = ConstU32<1>; type PeriodSpend = ConstU64<1000>; - type VotingPeriod = ConstU64<3>; + type VotingPeriod = VotingPeriod; type ClaimPeriod = ClaimPeriod; type MaxLockDuration = ConstU64<100>; type FounderSetOrigin = EnsureSignedBy; @@ -231,6 +232,7 @@ pub fn next_intake() { ), Period::Claim { more, .. } => System::run_to_block::(System::block_number() + more), + Period::Intake { .. } => {}, } } diff --git a/substrate/frame/society/src/tests.rs b/substrate/frame/society/src/tests.rs index 82ba054501874..d559f6d9c01f7 100644 --- a/substrate/frame/society/src/tests.rs +++ b/substrate/frame/society/src/tests.rs @@ -1469,3 +1469,194 @@ fn poke_deposit_handles_insufficient_balance() { ); }); } + +#[test] +fn challenge_with_non_consecutive_blocks_works() { + EnvBuilder::new().execute(|| { + let challenge_period: u64 = ::ChallengePeriod::get(); + let now = challenge_period + 1; + let next_challenge_at = challenge_period + challenge_period; + ::BlockNumberProvider::set_block_number(now); + + assert_eq!(Society::next_challenge_at(), next_challenge_at); + + Society::on_initialize(0); + + // Add some members + place_members([20, 30, 40, 50]); + // Votes are empty + assert_eq!(DefenderVotes::::get(0, 20), None); + assert_eq!(DefenderVotes::::get(0, 30), None); + assert_eq!(DefenderVotes::::get(0, 40), None); + assert_eq!(DefenderVotes::::get(0, 50), None); + // Check starting point + assert_eq!(members(), vec![10, 20, 30, 40, 50]); + assert_eq!(Defending::::get(), None); + + // early for challenge + let now = next_challenge_at - 1; + ::BlockNumberProvider::set_block_number(now); + Society::on_initialize(0); + assert_eq!(members(), vec![10, 20, 30, 40, 50]); + assert_eq!(Defending::::get(), None); + + // challenge with delay + let now = next_challenge_at + 2; + ::BlockNumberProvider::set_block_number(now); + Society::on_initialize(0); + assert_eq!(Defending::::get().unwrap().0, 40); + // They can always free vote for themselves + assert_ok!(Society::defender_vote(Origin::signed(40), false)); + // everyone votes against 40 + assert_ok!(Society::defender_vote(Origin::signed(20), false)); + assert_ok!(Society::defender_vote(Origin::signed(30), false)); + assert_ok!(Society::defender_vote(Origin::signed(50), false)); + + let next_challenge_at = next_challenge_at + challenge_period; + assert_eq!(Society::next_challenge_at(), next_challenge_at); + + // early for challenge + let now = next_challenge_at - 2; + ::BlockNumberProvider::set_block_number(now); + Society::on_initialize(0); + assert_eq!(members(), vec![10, 20, 30, 40, 50]); + + // challenge with delay + let now = next_challenge_at - 1; + ::BlockNumberProvider::set_block_number(now); + Society::on_initialize(0); + assert_eq!(members(), vec![10, 20, 30, 40, 50]); + + // challenge without delay + let now = next_challenge_at; + ::BlockNumberProvider::set_block_number(now); + Society::on_initialize(0); + // 40 is suspended + assert_eq!(members(), vec![10, 20, 30, 50]); + assert_eq!( + SuspendedMembers::::get(40), + Some(MemberRecord { rank: 0, strikes: 0, vouching: None, index: 3 }) + ); + // Reset votes for last challenge + assert_ok!(Society::cleanup_challenge(Origin::signed(0), 0, 10)); + // New defender is chosen, 30 is challenged + assert_eq!(Defending::::get().unwrap().0, 30); + // Votes are reset + assert_eq!(DefenderVotes::::get(0, 20), None); + assert_eq!(DefenderVotes::::get(0, 30), None); + assert_eq!(DefenderVotes::::get(0, 40), None); + assert_eq!(DefenderVotes::::get(0, 50), None); + }); +} + +#[test] +fn intake_with_non_consecutive_blocks_works() { + EnvBuilder::new().execute(|| { + let voting_period: u64 = ::VotingPeriod::get(); + let claim_period: u64 = ::ClaimPeriod::get(); + let rotation_period = voting_period + claim_period; + let now = rotation_period + 1; + let next_intake_at = rotation_period + rotation_period; + ::BlockNumberProvider::set_block_number(now); + + assert_eq!(Society::next_intake_at(), next_intake_at); + assert_eq!(Society::period(), Period::Voting { elapsed: 1, more: 2 }); + + Society::on_initialize(0); + + assert_eq!(Balances::free_balance(20), 50); + // Bid causes Candidate Deposit to be reserved. + assert_ok!(Society::bid(RuntimeOrigin::signed(20), 0)); + assert_eq!(Balances::free_balance(20), 25); + + // early for intake + let now = next_intake_at - 1; + ::BlockNumberProvider::set_block_number(now); + assert_eq!(Society::period(), Period::Claim { elapsed: 0, more: 1 }); + Society::on_initialize(0); + assert_eq!(candidacies(), vec![]); + + // intake with delay + let now = next_intake_at + 1; + ::BlockNumberProvider::set_block_number(now); + assert_eq!(Society::period(), Period::Intake { elapsed: 1 }); + Society::on_initialize(0); + // 20 is now a candidate + assert_eq!(candidacies(), vec![(20, candidacy(1, 0, Deposit(25), 0, 0))]); + // 10 (a member) can vote for the candidate + assert_ok!(Society::vote(Origin::signed(10), 20, true)); + conclude_intake(true, None); + + let next_intake_at = next_intake_at + rotation_period; + assert_eq!(Society::next_intake_at(), next_intake_at); + + // intake without delay + let now = next_intake_at; + ::BlockNumberProvider::set_block_number(now); + assert_eq!(Society::period(), Period::Intake { elapsed: 0 }); + Society::on_initialize(0); + // 20 is now a member of the society + assert_eq!(members(), vec![10, 20]); + // Reserved balance is returned + assert_eq!(Balances::free_balance(20), 50); + }); +} + +#[test] +fn intake_idempotency() { + EnvBuilder::new().execute(|| { + let voting_period: u64 = ::VotingPeriod::get(); + let claim_period: u64 = ::ClaimPeriod::get(); + let rotation_period = voting_period + claim_period; + let now = rotation_period + 1; + let next_intake_at = rotation_period + rotation_period; + ::BlockNumberProvider::set_block_number(now); + + assert_eq!(Society::next_intake_at(), next_intake_at); + assert_eq!(Society::period(), Period::Voting { elapsed: 1, more: 2 }); + + // initialize the next intake at + Society::on_initialize(0); + + // Bid to become a candidate + assert_eq!(Balances::free_balance(20), 50); + assert_ok!(Society::bid(RuntimeOrigin::signed(20), 0)); + + // intake + let now = next_intake_at; + ::BlockNumberProvider::set_block_number(now); + assert_eq!(Society::period(), Period::Intake { elapsed: 0 }); + Society::on_initialize(0); + // 20 is now a candidate + assert_eq!(candidacies(), vec![(20, candidacy(1, 0, Deposit(25), 0, 0))]); + + // Bid one more account to become a candidate + assert_eq!(Balances::free_balance(40), 50); + assert_ok!(Society::bid(RuntimeOrigin::signed(40), 10)); + + // next intake has updated + let next_intake_at = next_intake_at + rotation_period; + assert_eq!(Society::next_intake_at(), next_intake_at); + + // `on_initialize` at the same block provider block number has not effect + assert_eq!(Society::period(), Period::Voting { elapsed: 0, more: 3 }); + Society::on_initialize(0); + // 20 is still the only candidate + assert_eq!(candidacies(), vec![(20, candidacy(1, 0, Deposit(25), 0, 0))]); + + // 10 (a member) can vote for the candidate + assert_ok!(Society::vote(Origin::signed(10), 20, true)); + // moves the block to the Claim period + conclude_intake(true, None); + + // next intake adds the candidate to the society + let now = next_intake_at; + ::BlockNumberProvider::set_block_number(now); + assert_eq!(Society::period(), Period::Intake { elapsed: 0 }); + Society::on_initialize(0); + // 20 is now a member of the society + assert_eq!(members(), vec![10, 20]); + // Reserved balance is returned + assert_eq!(Balances::free_balance(20), 50); + }); +} diff --git a/substrate/frame/staking-async/ah-client/Cargo.toml b/substrate/frame/staking-async/ah-client/Cargo.toml index 8a85f25375568..64edacc471349 100644 --- a/substrate/frame/staking-async/ah-client/Cargo.toml +++ b/substrate/frame/staking-async/ah-client/Cargo.toml @@ -47,6 +47,7 @@ runtime-benchmarks = [ "frame-benchmarking/runtime-benchmarks", "frame-support/runtime-benchmarks", "frame-system/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking-async-rc-client/runtime-benchmarks", "sp-runtime/runtime-benchmarks", "sp-staking/runtime-benchmarks", diff --git a/substrate/frame/staking-async/runtimes/parachain/Cargo.toml b/substrate/frame/staking-async/runtimes/parachain/Cargo.toml index 59d3a3a96fee7..183424a6b11e9 100644 --- a/substrate/frame/staking-async/runtimes/parachain/Cargo.toml +++ b/substrate/frame/staking-async/runtimes/parachain/Cargo.toml @@ -182,6 +182,7 @@ runtime-benchmarks = [ "pallet-proxy/runtime-benchmarks", "pallet-referenda/runtime-benchmarks", "pallet-scheduler/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking-async-rc-client/runtime-benchmarks", "pallet-staking-async/runtime-benchmarks", "pallet-state-trie-migration/runtime-benchmarks", diff --git a/substrate/frame/staking-async/runtimes/parachain/src/staking.rs b/substrate/frame/staking-async/runtimes/parachain/src/staking.rs index ab5c8f7fe4104..aa9da4dc520f4 100644 --- a/substrate/frame/staking-async/runtimes/parachain/src/staking.rs +++ b/substrate/frame/staking-async/runtimes/parachain/src/staking.rs @@ -81,8 +81,10 @@ parameter_types! { /// better. pub storage Pages: u32 = 4; - /// * Polkadot: 8 * 32 (256 blocks, 25.6m). Enough time to verify up to 8 solutions. - /// * Kusama: 4 * 16 (64 blocks, 6.4m). Enough time to verify up to 4 solutions. + /// * Polkadot: 16 * 32 (512 blocks, 51.2m). + /// * Kusama: 8 * 16 (12 blocks, 12.8m). + /// + /// (MaxSubmissions * Pages) for both, enough to verify all solutions. /// /// Reasoning: Less security needed in Kusama, to compensate for the shorter session duration. pub storage SignedValidationPhase: u32 = Pages::get() * 2; diff --git a/substrate/frame/staking-async/runtimes/parachain/src/weights/cumulus_pallet_xcmp_queue.rs b/substrate/frame/staking-async/runtimes/parachain/src/weights/cumulus_pallet_xcmp_queue.rs index 60543220d68c1..e001f2a2972e1 100644 --- a/substrate/frame/staking-async/runtimes/parachain/src/weights/cumulus_pallet_xcmp_queue.rs +++ b/substrate/frame/staking-async/runtimes/parachain/src/weights/cumulus_pallet_xcmp_queue.rs @@ -186,12 +186,15 @@ impl cumulus_pallet_xcmp_queue::WeightInfo for WeightIn .saturating_add(T::DbWeight::get().reads(1_u64)) .saturating_add(T::DbWeight::get().writes(1_u64)) } - fn take_first_concatenated_xcm() -> Weight { + /// The range of component `n` is `[0, 92]`. + fn take_first_concatenated_xcm(n: u32, ) -> Weight { // Proof Size summary in bytes: // Measured: `0` // Estimated: `0` - // Minimum execution time: 4_749_000 picoseconds. - Weight::from_parts(5_937_000, 0) + // Minimum execution time: 1_000_000 picoseconds. + Weight::from_parts(1_806_940, 0) + // Standard Error: 541 + .saturating_add(Weight::from_parts(46_068, 0).saturating_mul(n.into())) } /// Storage: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) /// Proof: UNKNOWN KEY `0x7b3237373ffdfeb1cab4222e3b520d6b345d8e88afa015075c945637c07e8f20` (r:1 w:1) diff --git a/substrate/frame/staking-async/runtimes/rc/Cargo.toml b/substrate/frame/staking-async/runtimes/rc/Cargo.toml index 5f9987431b3c6..273ac3f1f8799 100644 --- a/substrate/frame/staking-async/runtimes/rc/Cargo.toml +++ b/substrate/frame/staking-async/runtimes/rc/Cargo.toml @@ -257,6 +257,7 @@ runtime-benchmarks = [ "pallet-root-offences/runtime-benchmarks", "pallet-scheduler/runtime-benchmarks", "pallet-session-benchmarking/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-staking-async-ah-client/runtime-benchmarks", "pallet-staking-async-rc-client/runtime-benchmarks", "pallet-staking/runtime-benchmarks", diff --git a/substrate/frame/staking-async/src/pallet/impls.rs b/substrate/frame/staking-async/src/pallet/impls.rs index 13bc247bcd6a0..8219aa1293f42 100644 --- a/substrate/frame/staking-async/src/pallet/impls.rs +++ b/substrate/frame/staking-async/src/pallet/impls.rs @@ -737,11 +737,6 @@ impl Pallet { .defensive_unwrap_or_default(); } Nominators::::insert(who, nominations); - - debug_assert_eq!( - Nominators::::count() + Validators::::count(), - T::VoterList::count() - ); } /// This function will remove a nominator from the `Nominators` storage map, @@ -761,11 +756,6 @@ impl Pallet { false }; - debug_assert_eq!( - Nominators::::count() + Validators::::count(), - T::VoterList::count() - ); - outcome } @@ -782,11 +772,6 @@ impl Pallet { let _ = T::VoterList::on_insert(who.clone(), Self::weight_of(who)); } Validators::::insert(who, prefs); - - debug_assert_eq!( - Nominators::::count() + Validators::::count(), - T::VoterList::count() - ); } /// This function will remove a validator from the `Validators` storage map. @@ -805,11 +790,6 @@ impl Pallet { false }; - debug_assert_eq!( - Nominators::::count() + Validators::::count(), - T::VoterList::count() - ); - outcome } diff --git a/substrate/frame/staking/Cargo.toml b/substrate/frame/staking/Cargo.toml index 0d2457799e941..c2e72e16211fc 100644 --- a/substrate/frame/staking/Cargo.toml +++ b/substrate/frame/staking/Cargo.toml @@ -78,6 +78,7 @@ runtime-benchmarks = [ "frame-system/runtime-benchmarks", "pallet-bags-list/runtime-benchmarks", "pallet-balances/runtime-benchmarks", + "pallet-session/runtime-benchmarks", "pallet-timestamp/runtime-benchmarks", "rand_chacha", "sp-runtime/runtime-benchmarks", diff --git a/substrate/primitives/runtime/Cargo.toml b/substrate/primitives/runtime/Cargo.toml index 10f9ab7daec3b..2f739f7a7ab2b 100644 --- a/substrate/primitives/runtime/Cargo.toml +++ b/substrate/primitives/runtime/Cargo.toml @@ -57,6 +57,7 @@ default = ["std"] std = [ "binary-merkle-tree/std", "codec/std", + "either/std", "either/use_std", "hash256-std-hasher/std", "log/std", diff --git a/umbrella/Cargo.toml b/umbrella/Cargo.toml index c9660322b6501..54b021e719485 100644 --- a/umbrella/Cargo.toml +++ b/umbrella/Cargo.toml @@ -319,6 +319,7 @@ runtime-benchmarks = [ "pallet-salary?/runtime-benchmarks", "pallet-scheduler?/runtime-benchmarks", "pallet-session-benchmarking?/runtime-benchmarks", + "pallet-session?/runtime-benchmarks", "pallet-skip-feeless-payment?/runtime-benchmarks", "pallet-society?/runtime-benchmarks", "pallet-staking-async-ah-client?/runtime-benchmarks",