- Feb 06, 2024
-
-
Alin Dima authored
Fixes https://github.com/paritytech/polkadot-sdk/issues/3129
-
- Feb 05, 2024
-
-
dependabot[bot] authored
Bumps [indicatif](https://github.com/console-rs/indicatif) from 0.17.6 to 0.17.7. <details> <summary>Commits</summary> <ul> <li><a href="https://github.com/console-rs/indicatif/commit/0c037edc86449d84aa457d7d5db80b4166c18d6b"><code>0c037ed</code></a> Bump version to 0.17.7 (<a href="https://redirect.github.com/console-rs/indicatif/issues/589">#589</a>)</li> <li><a href="https://github.com/console-rs/indicatif/commit/44610121c8c0343428c12992a5bbf21255d4120b"><code>4461012</code></a> Fix attempt to subtract with overflow (<a href="https://redirect.github.com/console-rs/indicatif/issues/582">#582</a>) (<a href="https://redirect.github.com/console-rs/indicatif/issues/586">#586</a>)</li> <li><a href="https://github.com/console-rs/indicatif/commit/257d3ecc39f60a366bde98c11c4c703f91d53347"><code>257d3ec</code></a> Bump actions/checkout from 3 to 4</li> <li><a href="https://github.com/console-rs/indicatif/commit/40b40d29b6d06ae18c40b829f77e9c43bcebd7af"><code>40b40d2</code></a> fix unnecessary vec! lint instances</li> <li><a href="https://github.com/console-rs/indicatif/commit/a5a8524b4a62ac97229df5beeeff55c928e051fe"><code>a5a8524</code></a> Tick ProgressTrackers before drawing</li> <li><a href="https://github.com/console-rs/indicatif/commit/75fca29bdb9e1164092d2b40d46d9b9c3d9581f1"><code>75fca29</code></a> Add scheduled CI runs every week</li> <li><a href="https://github.com/console-rs/indicatif/commit/c0ea468ac3bd7ab9abab86a3fd3b251f7cef83b8"><code>c0ea468</code></a> Upgrade to 2021 edition</li> <li><a href="https://github.com/console-rs/indicatif/commit/73a67f8e517c64f919ce51ce62e7c5bf3cb95974"><code>73a67f8</code></a> Bump MSRV to 1.63 for tokio 1.30</li> <li><a href="https://github.com/console-rs/indicatif/commit/de090172485c7638a016b984e0c7c54e40919d34"><code>de09017</code></a> Reorder Cargo metadata fields</li> <li><a href="https://github.com/console-rs/indicatif/commit/cee6fd4fcf85c4eda3a6e5dfb555f8a9c6c62edd"><code>cee6fd4</code></a> Fix a potential overflow with a saturating add.</li> <li>Additional commits viewable in <a href="https://github.com/console-rs/indicatif/compare/0.17.6...0.17.7">compare view</a></li> </ul> </details> <br /> [![Dependabot compatibility score](https://dependabot-badges.githubapp.com/badges/compatibility_score?dependency-name=indicatif&package-manager=cargo&previous-version=0.17.6&new-version=0.17.7)](https://docs.github.com/en/github/managing-security-vulnerabilities/about-dependabot-security-updates#about-compatibility-scores) Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting `@dependabot rebase`. [//]: # (dependabot-automerge-start) [//]: # (dependabot-automerge-end) --- <details> <summary>Dependabot commands and options</summary> <br /> You can trigger Dependabot actions by commenting on this PR: - `@dependabot rebase` will rebase this PR - `@dependabot recreate` will recreate this PR, overwriting any edits that have been made to it - `@dependabot merge` will merge this PR after your CI passes on it - `@dependabot squash and merge` will squash and merge this PR after your CI passes on it - `@dependabot cancel merge` will cancel a previously requested merge and block automerging - `@dependabot reopen` will reopen this PR if it is closed - `@dependabot close` will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually - `@dependabot show <dependency name> ignore conditions` will show all of the ignore conditions of the specified dependency - `@dependabot ignore <dependency name> major version` will close this group update PR and stop Dependabot creating any more for the specific dependency's major version (unless you unignore this specific dependency's major version or upgrade to it yourself) - `@dependabot ignore <dependency name> minor version` will close this group update PR and stop Dependabot creating any more for the specific dependency's minor version (unless you unignore this specific dependency's minor version or upgrade to it yourself) - `@dependabot ignore <dependency name>` will close this group update PR and stop Dependabot creating any more for the specific dependency (unless you unignore this specific dependency or upgrade to it yourself) - `@dependabot unignore <dependency name>` will remove all of the ignore conditions of the specified dependency - `@dependabot unignore <dependency name> <ignore condition>` will remove the ignore condition of the specified dependency and ignore conditions </details> Signed-off-by: dependabot[bot] <[email protected]> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
-
Alexandru Gheorghe authored
## Summary Built on top of the tooling and ideas introduced in https://github.com/paritytech/polkadot-sdk/pull/2528, this PR introduces a synthetic benchmark for measuring and assessing the performance characteristics of the approval-voting and approval-distribution subsystems. Currently this allows, us to simulate the behaviours of these systems based on the following dimensions: ``` TestConfiguration: # Test 1 - objective: !ApprovalsTest last_considered_tranche: 89 min_coalesce: 1 max_coalesce: 6 enable_assignments_v2: true send_till_tranche: 60 stop_when_approved: false coalesce_tranche_diff: 12 workdir_prefix: "/tmp" num_no_shows_per_candidate: 0 approval_distribution_expected_tof: 6.0 approval_distribution_cpu_ms: 3.0 approval_voting_cpu_ms: 4.30 n_validators: 500 n_cores: 100 n_included_candidates: 100 min_pov_size: 1120 max_pov_size: 5120 peer_bandwidth: 524288000000 bandwidth: 524288000000 latency: min_latency: secs: 0 nanos: 1000000 max_latency: secs: 0 nanos: 100000000 error: 0 num_blocks: 10 ``` ## The approach 1. We build a real overseer with the real implementations for approval-voting and approval-distribution subsystems. 2. For a given network size, for each validator we pre-computed all potential assignments and approvals it would send, because this a computation heavy operation this will be cached on a file on disk and be re-used if the generation parameters don't change. 3. The messages will be sent accordingly to the configured parameters and those are split into 3 main benchmarking scenarios. ## Benchmarking scenarios ### Best case scenario *approvals_throughput_best_case.yaml* It send to the approval-distribution only the minimum required tranche to gathered the needed_approvals, so that a candidate is approved. ### Behaviour in the presence of no-shows *approvals_no_shows.yaml* It sends the tranche needed to approve a candidate when we have a maximum of *num_no_shows_per_candidate* tranches with no-shows for each candidate. ### Maximum throughput *approvals_throughput.yaml* It sends all the tranches for each block and measures the used CPU and necessary network bandwidth. by the approval-voting and approval-distribution subsystem. ## How to run it ``` cargo run -p polkadot-subsystem-bench --release -- test-sequence --path polkadot/node/subsystem-bench/examples/approvals_throughput.yaml ``` ## Evaluating performance ### Use the real subsystems metrics If you follow the steps in https://github.com/paritytech/polkadot-sdk/tree/master/polkadot/node/subsystem-bench#install-grafana for installing locally prometheus and grafana, all real metrics for the `approval-distribution`, `approval-voting` and overseer are available. E.g: <img width="2149" alt="Screenshot 2023-12-05 at 11 07 46" src="https://github.com/paritytech/polkadot-sdk/assets/49718502/cb8ae2dd-178b-4922-bfa4-dc37e572ed38"> <img width="2551" alt="Screenshot 2023-12-05 at 11 09 42" src="https://github.com/paritytech/polkadot-sdk/assets/49718502/8b4542ba-88b9-46f9-9b70-cc345366081b"> <img width="2154" alt="Screenshot 2023-12-05 at 11 10 15" src="https://github.com/paritytech/polkadot-sdk/assets/49718502/b8874d8d-632e-443a-9840-14ad8e90c54f"> <img width="2535" alt="Screenshot 2023-12-05 at 11 10 52" src="https://github.com/paritytech/polkadot-sdk/assets/49718502/779a439f-fd18-4985-bb80-85d5afad78e2"> ### Profile with pyroscope 1. Setup pyroscope following the steps in https://github.com/paritytech/polkadot-sdk/tree/master/polkadot/node/subsystem-bench#install-pyroscope, then run any of the benchmark scenario with `--profile` as the arguments. 2. Open the pyroscope dashboard in grafana, e.g: <img width="2544" alt="Screenshot 2024-01-09 at 17 09 58" src="https://github.com/paritytech/polkadot-sdk/assets/49718502/58f50c99-a910-4d20-951a-8b16639303d9"> ### Useful logs 1. Network bandwidth requirements: ``` Payload bytes received from peers: 503993 KiB total, 50399 KiB/block Payload bytes sent to peers: 629971 KiB total, 62997 KiB/block ``` 2. Cpu usage by the approval-distribution/approval-voting subsystems. ``` approval-distribution CPU usage 84.061s approval-distribution CPU usage per block 8.406s approval-voting CPU usage 96.532s approval-voting CPU usage per block 9.653s ``` 3. Time passed until a given block is approved ``` Chain selection approved after 3500 ms hash=0x0101010101010101010101010101010101010101010101010101010101010101 Chain selection approved after 4500 ms hash=0x0202020202020202020202020202020202020202020202020202020202020202 ``` ### Using benchmark to quantify improvements from https://github.com/paritytech/polkadot-sdk/pull/1178 + https://github.com/paritytech/polkadot-sdk/pull/1191 Using a versi-node we compare the scenarios where all new optimisations are disabled with a scenarios where tranche0 assignments are sent in a single message and a conservative simulation where the coalescing of approvals gives us just 50% reduction in the number of messages we send. Overall, what we see is a speedup of around 30-40% in the time it takes to process the necessary messages and a 30-40% reduction in the necessary bandwidth. #### Best case scenario comparison(minimum required tranches sent). Unoptimised ``` Number of blocks: 10 Payload bytes received from peers: 53289 KiB total, 5328 KiB/block Payload bytes sent to peers: 52489 KiB total, 5248 KiB/block approval-distribution CPU usage 6.732s approval-distribution CPU usage per block 0.673s approval-voting CPU usage 9.523s approval-voting CPU usage per block 0.952s ``` vs Optimisation enabled ``` Number of blocks: 10 Payload bytes received from peers: 32141 KiB total, 3214 KiB/block Payload bytes sent to peers: 37314 KiB total, 3731 KiB/block approval-distribution CPU usage 4.658s approval-distribution CPU usage per block 0.466s approval-voting CPU usage 6.236s approval-voting CPU usage per block 0.624s ``` #### Worst case all tranches sent, very unlikely happens when sharding breaks. Unoptimised ``` Number of blocks: 10 Payload bytes received from peers: 746393 KiB total, 74639 KiB/block Payload bytes sent to peers: 729151 KiB total, 72915 KiB/block approval-distribution CPU usage 118.681s approval-distribution CPU usage per block 11.868s approval-voting CPU usage 124.118s approval-voting CPU usage per block 12.412s ``` vs optimised ``` Number of blocks: 10 Payload bytes received from peers: 503993 KiB total, 50399 KiB/block Payload bytes sent to peers: 629971 KiB total, 62997 KiB/block approval-distribution CPU usage 84.061s approval-distribution CPU usage per block 8.406s approval-voting CPU usage 96.532s approval-voting CPU usage per block 9.653s ``` ## TODOs [x] Polish implementation. [x] Use what we have so far to evaluate https://github.com/paritytech/polkadot-sdk/pull/1191 before merging. [x] List of features and additional dimensions we want to use for benchmarking. [x] Run benchmark on hardware similar with versi and kusama nodes. [ ] Add benchmark to be run in CI for catching regression in performance. [ ] Rebase on latest changes for network emulation. --------- Signed-off-by: Andrei Sandu <[email protected]> Signed-off-by: Alexandru Gheorghe <[email protected]> Co-authored-by: Andrei Sandu <[email protected]> Co-authored-by: Andrei Sandu <[email protected]>
-
dependabot[bot] authored
Bumps [paritytech/review-bot](https://github.com/paritytech/review-bot) from 2.3.0 to 2.4.0. <details> <summary>Release notes</summary> <p><em>Sourced from <a href="https://github.com/paritytech/review-bot/releases">paritytech/review-bot's releases</a>.</em></p> <blockquote> <h2>v2.4.0</h2> <h2>What's Changed</h2> <ul> <li>Updated node and dependencies by <a href="https://github.com/Bullrich"><code>@Bullrich</code></a> in <a href="https://redirect.github.com/paritytech/review-bot/pull/111">paritytech/review-bot#111</a></li> <li>Refactor of failed reviews objects by <a href="https://github.com/Bullrich"><code>@Bullrich</code></a> in <a href="https://redirect.github.com/paritytech/review-bot/pull/112">paritytech/review-bot#112</a></li> <li>Added required score grouping to fellows reviews by <a href="https://github.com/Bullrich"><code>@Bullrich</code></a> in <a href="https://redirect.github.com/paritytech/review-bot/pull/113">paritytech/review-bot#113</a></li> </ul> <p><strong>Full Changelog</strong>: <a href="https://github.com/paritytech/review-bot/compare/v2.3.1...v2.4.0">https://github.com/paritytech/review-bot/compare/v2.3.1...v2.4.0</a></p> <h2>v2.3.1</h2> <h2>What's Changed</h2> <ul> <li>Fellows: Added search of super identity by <a href="https://github.com/Bullrich"><code>@Bullrich</code></a> in <a href="https://redirect.github.com/paritytech/review-bot/pull/108">paritytech/review-bot#108</a></li> </ul> <p><strong>Full Changelog</strong>: <a href="https://github.com/paritytech/review-bot/compare/v2.3.0...v2.3.1">https://github.com/paritytech/review-bot/compare/v2.3.0...v2.3.1</a></p> </blockquote> </details> <details> <summary>Commits</summary> <ul> <li><a href="https://github.com/paritytech/review-bot/commit/280018363a131c5b59fcdb9c6f1a85a50bdb31e9"><code>2800183</code></a> Added required score grouping to fellows reviews (<a href="https://redirect.github.com/paritytech/review-bot/issues/113">#113</a>)</li> <li><a href="https://github.com/paritytech/review-bot/commit/53718073fee3b3af31a9d1bba9c900d989699e55"><code>5371807</code></a> Refactor of failed reviews objects (<a href="https://redirect.github.com/paritytech/review-bot/issues/112">#112</a>)</li> <li><a href="https://github.com/paritytech/review-bot/commit/5f58f48fed7d174d382989940cbbf47dbd5ee41e"><code>5f58f48</code></a> Updated node and dependencies (<a href="https://redirect.github.com/paritytech/review-bot/issues/111">#111</a>)</li> <li><a href="https://github.com/paritytech/review-bot/commit/4ea00441b921cfdbbd47dcd95f1f6e3e0ab0b691"><code>4ea0044</code></a> Fellows: Added search of super identity (<a href="https://redirect.github.com/paritytech/review-bot/issues/108">#108</a>)</li> <li>See full diff in <a href="https://github.com/paritytech/review-bot/compare/v2.3.0...v2.4.0">compare view</a></li> </ul> </details> <br /> [![Dependabot compatibility score](https://dependabot-badges.githubapp.com/badges/compatibility_score?dependency-name=paritytech/review-bot&package-manager=github_actions&previous-version=2.3.0&new-version=2.4.0)](https://docs.github.com/en/github/managing-security-vulnerabilities/about-dependabot-security-updates#about-compatibility-scores) Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting `@dependabot rebase`. [//]: # (dependabot-automerge-start) [//]: # (dependabot-automerge-end) --- <details> <summary>Dependabot commands and options</summary> <br /> You can trigger Dependabot actions by commenting on this PR: - `@dependabot rebase` will rebase this PR - `@dependabot recreate` will recreate this PR, overwriting any edits that have been made to it - `@dependabot merge` will merge this PR after your CI passes on it - `@dependabot squash and merge` will squash and merge this PR after your CI passes on it - `@dependabot cancel merge` will cancel a previously requested merge and block automerging - `@dependabot reopen` will reopen this PR if it is closed - `@dependabot close` will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually - `@dependabot show <dependency name> ignore conditions` will show all of the ignore conditions of the specified dependency - `@dependabot ignore this major version` will close this PR and stop Dependabot creating any more for this major version (unless you reopen the PR or upgrade to it yourself) - `@dependabot ignore this minor version` will close this PR and stop Dependabot creating any more for this minor version (unless you reopen the PR or upgrade to it yourself) - `@dependabot ignore this dependency` will close this PR and stop Dependabot creating any more for this dependency (unless you reopen the PR or upgrade to it yourself) </details> Signed-off-by: dependabot[bot] <[email protected]> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
-
- Feb 03, 2024
-
-
Nazar Mokrynskyi authored
This allows to build a custom version of `spawn_tasks` with less copy-paste required. Resolves https://github.com/paritytech/polkadot-sdk/issues/2110 --------- Co-authored-by: Bastian Köcher <[email protected]>
-
Cyrill Leutwiler authored
Can this API be marked stable? Implemented in [solang here](https://github.com/hyperledger/solang/pull/1620) --------- Signed-off-by: Cyrill Leutwiler <[email protected]>
-
Koute authored
This PR adds initial support for building RISC-V runtimes targeting PolkaVM. - Setting the `SUBSTRATE_RUNTIME_TARGET=riscv` environment variable will now build a RISC-V runtime instead of a WASM runtime. - This only adds support for *building* runtimes; running them will need a PolkaVM-based executor, which I will add in a future PR. - Only building the minimal runtime is supported (building the Polkadot runtime doesn't work *yet* due to one of the dependencies). - The builder now sets a `substrate_runtime` cfg flag when building the runtimes, with the idea being that instead of doing `#[cfg(not(feature = "std"))]` or `#[cfg(target_arch = "wasm32")]` to detect that we're building a runtime you'll do `#[cfg(substrate_runtime)]`. (Switching the whole codebase to use this will be done in a future PR; I deliberately didn't do this here to keep this PR minimal and reviewable.) - Further renaming of things (e.g. types, environment variables and proc macro attributes having "wasm" in their name) to be target-agnostic will also be done in a future refactoring PR (while keeping backwards compatibility where it makes sense; I don't intend to break anyone's workflow or create unnecessary churn). - This PR also fixes two bugs in the `wasm-builder` crate: * The `RUSTC` environment variable is now removed when invoking the compiler. This prevents the toolchain version from being overridden when called from a `build.rs` script. * When parsing the `rustup toolchain list` output the `(default)` is now properly stripped and not treated as part of the version. - I've also added a minimal CI job that makes sure this doesn't break in the future. (cc @paritytech/ci) cc @athei ------ Also, just a fun little tidbit: quickly comparing the size of the built runtimes it seems that the PolkaVM runtime is slightly smaller than the WASM one. (`production` build, with the `names` section substracted from the WASM's size to keep things fair, since for the PolkaVM runtime we're currently stripping out everything) - `.wasm`: 625505 bytes - `.wasm` (after wasm-opt -O3): 563205 bytes - `.wasm` (after wasm-opt -Os): 562987 bytes - `.wasm` (after wasm-opt -Oz): 536852 bytes - `.polkavm`: ~~580338 bytes~~ 550476 bytes (after enabling extra target features; I'll add those in another PR once we have an executor working) --------- Co-authored-by: Bastian Köcher <[email protected]>
-
- Feb 02, 2024
-
-
dependabot[bot] authored
Bumps [wasmi](https://github.com/paritytech/wasmi) from 0.31.0 to 0.31.2. <details> <summary>Release notes</summary> <p><em>Sourced from <a href="https://github.com/paritytech/wasmi/releases">wasmi's releases</a>.</em></p> <blockquote> <h2>v0.31.1 - 2023-12-01</h2> <h3>Fixes</h3> <ul> <li>Fixed a bug, in the <code>wasmi</code> engine executor, that causes an out of bounds buffer write when calling or resuming a Wasm function with a high number of parameters from the host side.</li> </ul> </blockquote> </details> <details> <summary>Changelog</summary> <p><em>Sourced from <a href="https://github.com/paritytech/wasmi/blob/master/CHANGELOG.md">wasmi's changelog</a>.</em></p> <blockquote> <h1>Changelog</h1> <p>All notable changes to this project will be documented in this file.</p> <p>The format is loosely based on <a href="https://keepachangelog.com/en/1.0.0/">Keep a Changelog</a>, and this project adheres to <a href="https://semver.org/spec/v2.0.0.html">Semantic Versioning</a>. Additionally we have an <code>Internal</code> section for changes that are of interest to developers.</p> <p>Dates in this file are formattes as <code>YYYY-MM-DD</code>.</p> <h2>[<code>0.32.0-beta.5</code>] - 2024-01-15</h2> <p><strong>Note:</strong></p> <ul> <li>This is the beta of the upcoming <code>v0.32.0</code> release. This version is not production ready yet and might contain serious bugs. Please use this only for experimentation or at your own risk.</li> <li>Performance tests indicated that the new register-machine bytecode based Wasmi engine performance is very sensitive to hardware or OS specifics which may lead to very different performance characteristics. <ul> <li>We are working on fixing this until the stable release.</li> <li>Measurements concluded that execution performance can be equal or sometimes even surpass Wasm3 execution performance.</li> </ul> </li> </ul> <h3>Added</h3> <ul> <li>Added a new execution engine based on register-machine bytecode. (<a href="https://redirect.github.com/paritytech/wasmi/pull/729">paritytech/wasmi#729</a>) <ul> <li>The register-machine Wasmi <code>Engine</code> executes roughly 80-100% faster and compiles roughly 30% slower according to benchmarks conducted so far.</li> </ul> </li> <li>Added <code>Module::new_unchecked</code> API. (<a href="https://redirect.github.com/paritytech/wasmi/pull/829">paritytech/wasmi#829</a>) <ul> <li>This allows to compile a Wasm module without Wasm validation which can be useful when users know that their inputs are valid Wasm binaries.</li> <li>This improves Wasm compilation performance for faster startup times by roughly 10-20%.</li> </ul> </li> <li>Added Wasm compilation modes. (<a href="https://redirect.github.com/paritytech/wasmi/pull/844">paritytech/wasmi#844</a>) <ul> <li>When using <code>Module::new</code> Wasmi eagerly compiles Wasm bytecode into Wasmi bytecode which is optimized for efficient execution. However, this compilation can become very costly especially for large Wasm binaries.</li> <li>The solution to this problem is to introduce new compilation modes, namely: <ul> <li><code>CompilationMode::Eager</code>: Eager compilation, what Wasmi did so far. (default)</li> <li><code>CompilationMode::LazyTranslation</code>: Eager Wasm validation and lazy Wasm translation.</li> <li><code>CompilationMode::Lazy</code>: Lazy Wasm validation and translation.</li> </ul> </li> <li>Benchmarks concluded that <ul> <li><code>CompilationMode::LazyTanslation</code>: Usually improves startup performance by a factor of 2 to 3.</li> <li><code>CompilationMode::Lazy</code>: Usually improves startup performance by a factor of up to 27.</li> </ul> </li> <li>Note that <code>CompilationMode::Lazy</code> can lead to partially validated Wasm modules which can introduce non-determinism when using different Wasm implementations. Therefore users should know what they are doing when using <code>CompilationMode::Lazy</code> if this is a concern.</li> <li>Enable lazy Wasm compilation with: <pre lang="rust"><code>let mut config = wasmi::Config::default(); </code></pre> </li> </ul> </li> </ul> <!-- raw HTML omitted --> </blockquote> <p>... (truncated)</p> </details> <details> <summary>Commits</summary> <ul> <li><a href="https://github.com/paritytech/wasmi/commit/0218dfc74b4c4a83261d46d90ac83fb513fd6b3f"><code>0218dfc</code></a> Fix <code>InstanceCache</code> bug (<a href="https://redirect.github.com/paritytech/wasmi/issues/904">#904</a>)</li> <li><a href="https://github.com/paritytech/wasmi/commit/3fd0cc2b2d7b7a55142e6a6cffffbe4212ed00ae"><code>3fd0cc2</code></a> Bump <code>wasmi_arena</code> version (<a href="https://redirect.github.com/paritytech/wasmi/issues/903">#903</a>)</li> <li><a href="https://github.com/paritytech/wasmi/commit/86c874029eba5067f4ecd01bc3c4f6dacab5a16e"><code>86c8740</code></a> Fix <code>Sync</code> impl bug in <code>wasmi_arena</code> crate (<a href="https://redirect.github.com/paritytech/wasmi/issues/902">#902</a>)</li> <li><a href="https://github.com/paritytech/wasmi/commit/27def282b06613e770d0ab96de88b9909973a12b"><code>27def28</code></a> Bump actions/cache from 3 to 4 (<a href="https://redirect.github.com/paritytech/wasmi/issues/900">#900</a>)</li> <li><a href="https://github.com/paritytech/wasmi/commit/59f9acc4776c09a35c6d563609de6818e9b65084"><code>59f9acc</code></a> Fix typos (<a href="https://redirect.github.com/paritytech/wasmi/issues/899">#899</a>)</li> <li><a href="https://github.com/paritytech/wasmi/commit/4c06acd816ccde6f45f9cc16aac4e18d36066054"><code>4c06acd</code></a> Update and improve Wasmi's readme (<a href="https://redirect.github.com/paritytech/wasmi/issues/898">#898</a>)</li> <li><a href="https://github.com/paritytech/wasmi/commit/2354a20ecc5e4209af2ba7458a8c383789ad8b4f"><code>2354a20</code></a> Prepare release for Wasmi <code>v0.32.0 beta.5</code> (<a href="https://redirect.github.com/paritytech/wasmi/issues/893">#893</a>)</li> <li><a href="https://github.com/paritytech/wasmi/commit/a4dc251bf066c362a2fc6acf00da924659894c6d"><code>a4dc251</code></a> Fix heap buffer overflow due to Wasmi codegen bug (<a href="https://redirect.github.com/paritytech/wasmi/issues/892">#892</a>)</li> <li><a href="https://github.com/paritytech/wasmi/commit/e60da4979009370cb1149b29dbb612886854efa9"><code>e60da49</code></a> Add CI test job using LLVM's Address Sanitizer (<a href="https://redirect.github.com/paritytech/wasmi/issues/891">#891</a>)</li> <li><a href="https://github.com/paritytech/wasmi/commit/28c770ac9623d78ce10c67d9bec013e0d3a43bcb"><code>28c770a</code></a> Prepare release for Wasmi <code>v0.32.0-beta.4</code> (<a href="https://redirect.github.com/paritytech/wasmi/issues/889">#889</a>)</li> <li>Additional commits viewable in <a href="https://github.com/paritytech/wasmi/compare/v0.31.0...v0.31.2">compare view</a></li> </ul> </details> <br /> [![Dependabot compatibility score](https://dependabot-badges.githubapp.com/badges/compatibility_score?dependency-name=wasmi&package-manager=cargo&previous-version=0.31.0&new-version=0.31.2)](https://docs.github.com/en/github/managing-security-vulnerabilities/about-dependabot-security-updates#about-compatibility-scores) Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting `@dependabot rebase`. [//]: # (dependabot-automerge-start) [//]: # (dependabot-automerge-end) --- <details> <summary>Dependabot commands and options</summary> <br /> You can trigger Dependabot actions by commenting on this PR: - `@dependabot rebase` will rebase this PR - `@dependabot recreate` will recreate this PR, overwriting any edits that have been made to it - `@dependabot merge` will merge this PR after your CI passes on it - `@dependabot squash and merge` will squash and merge this PR after your CI passes on it - `@dependabot cancel merge` will cancel a previously requested merge and block automerging - `@dependabot reopen` will reopen this PR if it is closed - `@dependabot close` will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually - `@dependabot show <dependency name> ignore conditions` will show all of the ignore conditions of the specified dependency - `@dependabot ignore <dependency name> major version` will close this group update PR and stop Dependabot creating any more for the specific dependency's major version (unless you unignore this specific dependency's major version or upgrade to it yourself) - `@dependabot ignore <dependency name> minor version` will close this group update PR and stop Dependabot creating any more for the specific dependency's minor version (unless you unignore this specific dependency's minor version or upgrade to it yourself) - `@dependabot ignore <dependency name>` will close this group update PR and stop Dependabot creating any more for the specific dependency (unless you unignore this specific dependency or upgrade to it yourself) - `@dependabot unignore <dependency name>` will remove all of the ignore conditions of the specified dependency - `@dependabot unignore <dependency name> <ignore condition>` will remove the ignore condition of the specified dependency and ignore conditions </details> Signed-off-by: dependabot[bot] <[email protected]> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
-
Bastian Köcher authored
This change is mainly for people running the local variants. They can directly start with async backing. --------- Signed-off-by: Alexandru Gheorghe <[email protected]> Co-authored-by: Alexandru Gheorghe <[email protected]>
-
Tsvetomir Dimitrov authored
The PR contains small fixes for: * A test `HostConfig v11` storage migration - v11 was compared with itself instead of with `v10`. * Outdated comment for `ClaimQueue` * Typos
-
Clara van Staden authored
Removes the `bridges/snowbridge/parachain` directory and moves everything up to under `snowbridge` directly. We are cleaning up our local dev env after merging our crates into the polkadot-sdk. --------- Co-authored-by: claravanstaden <Cats 4 life!>
-
Marcin S. authored
Built on top of https://github.com/paritytech/polkadot-sdk/pull/2826/ which was a trial run. Guide: https://github.com/w3f/polkadot-wiki/blob/master/docs/maintain/maintain-guides-async-backing.md --------- Signed-off-by: georgepisaltu <[email protected]> Co-authored-by: Branislav Kontur <[email protected]> Co-authored-by: Dónal Murray <[email protected]> Co-authored-by: Dmitry Sinyavin <[email protected]> Co-authored-by: s0me0ne-unkn0wn <[email protected]> Co-authored-by: Svyatoslav Nikolsky <[email protected]> Co-authored-by: Bastian Köcher <[email protected]> Co-authored-by: georgepisaltu <[email protected]>
-
Branislav Kontur authored
## TODO - [x] change constants when CI fails (should fail :) ) ## Result On the AssetHubRococo: 1701175800126 -> 1700929825257 = 0.15 % decreased. ``` # Before ( [xcm] Fix `SovereignPaidRemoteExporter` and `DepositAsset` handling (#3157)) Feb 02 12:59:05.520 ERROR bridges::estimate: `bridging::XcmBridgeHubRouterBaseFee` actual value: 1701175800126 for runtime: statemine-1006000 (statemine-0.tx14.au1) # After Feb 02 13:02:40.647 ERROR bridges::estimate: `bridging::XcmBridgeHubRouterBaseFee` actual value: 1700929825257 for runtime: statemine-1006000 (statemine-0.tx14.au1) ``` On the AssetHubWestend: 2116038876326 -> 1641718372993 = 22.4 % decreased. ``` # Before ( [xcm] Fix `SovereignPaidRemoteExporter` and `DepositAsset` handling (#3157)) Feb 02 12:56:00.880 ERROR bridges::estimate: `bridging::XcmBridgeHubRouterBaseFee` actual value: 2116038876326 for runtime: westmint-1006000 (westmint-0.tx14.au1) # After Feb 02 13:04:42.515 ERROR bridges::estimate: `bridging::XcmBridgeHubRouterBaseFee` actual value: 1641718372993 for runtime: westmint-1006000 (westmint-0.tx14.au1) ```
-
Alexandru Gheorghe authored
Fixes: https://github.com/paritytech/polkadot-sdk/issues/3165 --------- Signed-off-by: Alexandru Gheorghe <[email protected]>
-
- Feb 01, 2024
-
-
Oliver Tale-Yazdi authored
Changes: - Add three missing crates to the workspace <s>claravanstaden are these two snowbridge crates supposed to go into the workspace?</s>
✅ @alvicsam can you please make the `Check workspace` required? Signed-off-by: Oliver Tale-Yazdi <[email protected]> -
Serban Iorga authored
Related to https://github.com/paritytech/polkadot-sdk/issues/3003 and https://github.com/paritytech/polkadot-sdk/issues/2842 --------- Co-authored-by: Adrian Catangiu <[email protected]>
-
- Jan 31, 2024
-
-
Pablo Andrés Dorado Suárez authored
# Description While methods' names on [`VoteTally`][1] trait might be self-explanatory at first sight, the distinction between `support` and `approval` can be a bit ambiguous for some readers. This PR aims to clarify the distinction and inform about the expected values for every not yet documented method on this trait. # Checklist - [x] My PR includes a detailed description as outlined in the "Description" section above - [ ] My PR follows the [labeling requirements](CONTRIBUTING.md#Process) of this project (at minimum one label for `T` required) - [x] I have made corresponding changes to the documentation (if applicable) - [x] I have added tests that prove my fix is effective or that my feature works (if applicable) [1]: https://docs.rs/frame-support/latest/frame_support/traits/trait.VoteTally.html --------- Co-authored-by: Bastian Köcher <[email protected]>
-
Oliver Tale-Yazdi authored
Fixup for https://github.com/paritytech/polkadot-sdk/pull/2587 to make the `core-fellowship` crate work with swapped members. Adds a `MemberSwappedHandler` to the `ranked-collective` pallet that are implemented by `core-fellowship+salary`. There is are exhaustive tests [here](https://github.com/paritytech/polkadot-sdk/blob/72aa7ac1/substrate/frame/core-fellowship/src/tests/integration.rs#L338) and [here](https://github.com/paritytech/polkadot-sdk/blob/ab3cdb05 /substrate/frame/salary/src/tests/integration.rs#L224) to check that adding member `1` is equivalent to adding member `0` and then swapping. --------- Signed-off-by: Oliver Tale-Yazdi <[email protected]>
-
Branislav Kontur authored
This PR addresses two issues: - It modifies `DepositAsset`'s asset filter from `All` to `AllCounted(1)` to prevent potentially charging excessive weight/fees. This adjustment avoids situations where fees could be calculated based on the count of assets, as illustrated [here](https://github.com/paritytech/polkadot-sdk/blob/master/cumulus/parachains/runtimes/bridge-hubs/bridge-hub-rococo/src/weights/xcm/mod.rs#L38-L46). - It encapsulates `DepositAsset` with `SetAppendix` to ensure that `fees` are not trapped in any case. For instance, this prevents issues when `ExportXcm::validate` encounters an error during the processing of `ExportMessage`.
-
dependabot[bot] authored
Bumps [bounded-collections](https://github.com/paritytech/parity-common) from 0.1.9 to 0.2.0. <details> <summary>Commits</summary> <ul> <li>See full diff in <a href="https://github.com/paritytech/parity-common/commits/impl-rlp-v0.2.0">compare view</a></li> </ul> </details> <br /> [![Dependabot compatibility score](https://dependabot-badges.githubapp.com/badges/compatibility_score?dependency-name=bounded-collections&package-manager=cargo&previous-version=0.1.9&new-version=0.2.0)](https://docs.github.com/en/github/managing-security-vulnerabilities/about-dependabot-security-updates#about-compatibility-scores) Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting `@dependabot rebase`. [//]: # (dependabot-automerge-start) [//]: # (dependabot-automerge-end) --- <details> <summary>Dependabot commands and options</summary> <br /> You can trigger Dependabot actions by commenting on this PR: - `@dependabot rebase` will rebase this PR - `@dependabot recreate` will recreate this PR, overwriting any edits that have been made to it - `@dependabot merge` will merge this PR after your CI passes on it - `@dependabot squash and merge` will squash and merge this PR after your CI passes on it - `@dependabot cancel merge` will cancel a previously requested merge and block automerging - `@dependabot reopen` will reopen this PR if it is closed - `@dependabot close` will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually - `@dependabot show <dependency name> ignore conditions` will show all of the ignore conditions of the specified dependency - `@dependabot ignore <dependency name> major version` will close this group update PR and stop Dependabot creating any more for the specific dependency's major version (unless you unignore this specific dependency's major version or upgrade to it yourself) - `@dependabot ignore <dependency name> minor version` will close this group update PR and stop Dependabot creating any more for the specific dependency's minor version (unless you unignore this specific dependency's minor version or upgrade to it yourself) - `@dependabot ignore <dependency name>` will close this group update PR and stop Dependabot creating any more for the specific dependency (unless you unignore this specific dependency or upgrade to it yourself) - `@dependabot unignore <dependency name>` will remove all of the ignore conditions of the specified dependency - `@dependabot unignore <dependency name> <ignore condition>` will remove the ignore condition of the specified dependency and ignore conditions </details> Signed-off-by: dependabot[bot] <[email protected]> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Liam Aharon <[email protected]>
-
-
Alexandru Gheorghe authored
Signed-off-by: Alexandru Gheorghe <[email protected]>
-
Adrian Catangiu authored
This fix aims to solve an issue in Kusama that resulted in failed reserve asset transfers. During multi-hop XCMs, like reserve asset transfers where the reserve is not the sender nor the destination, but a third remote chain, the origin is not available to pay for delivery fees out of their account directly, so delivery fees should be paid out of transferred assets. This commit also adds an xcm-emulator regression test that validates this scenario is now working. Signed-off-by: Adrian Catangiu <[email protected]> Co-authored-by: Francisco Aguirre <[email protected]>
-
Vladimir Istyufeev authored
Usual chore after bumping Rust toolchain version.
-
Branislav Kontur authored
Found it when trying to run: ``` bot bench-all pallet --pallet=pallet_balances ``` https://gitlab.parity.io/parity/mirrors/polkadot-sdk/-/jobs/5081585 ## TODO - [x] check/fix command bot for `people-westend-dev` / `people-rococo-dev` https://github.com/paritytech/command-bot-scripts/pull/67
-
Branislav Kontur authored
[frame] `#[pallet::composite_enum]` improved variant count handling + removed `pallet_balances`'s `MaxHolds` config (#2657) I started this investigation/issue based on @liamaharon question [here](https://github.com/paritytech/polkadot-sdk/pull/1801#discussion_r1410452499). ## Problem The `pallet_balances` integrity test should correctly detect that the runtime has correct distinct `HoldReasons` variant count. I assume the same situation exists for RuntimeFreezeReason. It is not a critical problem, if we set `MaxHolds` with a sufficiently large value, everything should be ok. However, in this case, the integrity_test check becomes less useful. **Situation for "any" runtime:** - `HoldReason` enums from different pallets: ```rust /// from pallet_nis #[pallet::composite_enum] pub enum HoldReason { NftReceipt, } /// from pallet_preimage #[pallet::composite_enum] pub enum HoldReason { Preimage, } // from pallet_state-trie-migration #[pallet::composite_enum] pub enum HoldReason { SlashForContinueMigrate, SlashForMigrateCustomTop, SlashForMigrateCustomChild, } ``` - generated `RuntimeHoldReason` enum looks like: ```rust pub enum RuntimeHoldReason { #[codec(index = 32u8)] Preimage(pallet_preimage::HoldReason), #[codec(index = 38u8)] Nis(pallet_nis::HoldReason), #[codec(index = 42u8)] StateTrieMigration(pallet_state_trie_migration::HoldReason), } ``` - composite enum `RuntimeHoldReason` variant count is detected as `3` - we set `type MaxHolds = ConstU32<3>` - `pallet_balances::integrity_test` is ok with `3`(at least 3) However, the real problem can occur in a live runtime where some functionality might stop working. This is due to a total of 5 distinct hold reasons (for pallets with multi-instance support, it is even more), and not all of them can be used because of an incorrect `MaxHolds`, which is deemed acceptable according to the `integrity_test`: ``` // pseudo-code - if we try to call all of these: T::Currency::hold(&pallet_nis::HoldReason::NftReceipt.into(), &nft_owner, deposit)?; T::Currency::hold(&pallet_preimage::HoldReason::Preimage.into(), &nft_owner, deposit)?; T::Currency::hold(&pallet_state_trie_migration::HoldReason::SlashForContinueMigrate.into(), &nft_owner, deposit)?; // With `type MaxHolds = ConstU32<3>` these two will fail T::Currency::hold(&pallet_state_trie_migration::HoldReason::SlashForMigrateCustomTop.into(), &nft_owner, deposit)?; T::Currency::hold(&pallet_state_trie_migration::HoldReason::SlashForMigrateCustomChild.into(), &nft_owner, deposit)?; ``` ## Solutions A macro `#[pallet::*]` expansion is extended of `VariantCount` implementation for the `#[pallet::composite_enum]` enum type. This expansion generates the `VariantCount` implementation for pallets' `HoldReason`, `FreezeReason`, `LockId`, and `SlashReason`. Enum variants must be plain enum values without fields to ensure a deterministic count. The composite runtime enum, `RuntimeHoldReason` and `RuntimeFreezeReason`, now sets `VariantCount::VARIANT_COUNT` as the sum of pallets' enum `VariantCount::VARIANT_COUNT`: ```rust #[frame_support::pallet(dev_mode)] mod module_single_instance { #[pallet::composite_enum] pub enum HoldReason { ModuleSingleInstanceReason1, ModuleSingleInstanceReason2, } ... } #[frame_support::pallet(dev_mode)] mod module_multi_instance { #[pallet::composite_enum] pub enum HoldReason<I: 'static = ()> { ModuleMultiInstanceReason1, ModuleMultiInstanceReason2, ModuleMultiInstanceReason3, } ... } impl self::sp_api_hidden_includes_construct_runtime::hidden_include::traits::VariantCount for RuntimeHoldReason { const VARIANT_COUNT: u32 = 0 + module_single_instance::HoldReason::VARIANT_COUNT + module_multi_instance::HoldReason::<module_multi_instance::Instance1>::VARIANT_COUNT + module_multi_instance::HoldReason::<module_multi_instance::Instance2>::VARIANT_COUNT + module_multi_instance::HoldReason::<module_multi_instance::Instance3>::VARIANT_COUNT; } ``` In addition, `MaxHolds` is removed (as suggested [here](https://github.com/paritytech/polkadot-sdk/pull/2657#discussion_r1443324573)) from `pallet_balances`, and its `Holds` are now bounded to `RuntimeHoldReason::VARIANT_COUNT`. Therefore, there is no need to let the runtime specify `MaxHolds`. ## For reviewers Relevant changes can be found here: - `substrate/frame/support/procedural/src/lib.rs` - `substrate/frame/support/procedural/src/pallet/parse/composite.rs` - `substrate/frame/support/procedural/src/pallet/expand/composite.rs` - `substrate/frame/support/procedural/src/construct_runtime/expand/composite_helper.rs` - `substrate/frame/support/procedural/src/construct_runtime/expand/hold_reason.rs` - `substrate/frame/support/procedural/src/construct_runtime/expand/freeze_reason.rs` - `substrate/frame/support/src/traits/misc.rs` And the rest of the files is just about removed `MaxHolds` from `pallet_balances` ## Next steps Do the same for `MaxFreezes` https://github.com/paritytech/polkadot-sdk/issues/2997. --------- Co-authored-by: command-bot <> Co-authored-by: Bastian Köcher <[email protected]> Co-authored-by: Dónal Murray <[email protected]> Co-authored-by: gupnik <[email protected]>
-
Francisco Aguirre authored
Some more work regarding XCMv4. Two limits from v3 were not transferred over, those are: - The instructions limit - The number of assets limit Both of these are now in v4. For some reason `AssetInstance` increased in size, don't know why CI didn't catch that before. --------- Co-authored-by: Bastian Köcher <[email protected]> Co-authored-by: command-bot <>
-
Branislav Kontur authored
The `parachains-common` contains a lots of constants and type definitions which are used for `polkadot-sdk`'s testnet runtimes and also for `polkadot-fellows`'s production [SP runtimes](https://github.com/polkadot-fellows/runtimes/tree/main/system-parachains/constants). This PR cleans `parachains-common` module to contain only common and generic functionality. Testnet-specific constants have been moved to the separate module dedicated just for testnets: `polkadot-sdk/cumulus/parachains/runtimes/constants/` Part of: https://github.com/paritytech/polkadot-sdk/issues/3054 --------- Co-authored-by: georgepisaltu <[email protected]>
-
- Jan 30, 2024
-
-
Alexander Samusev authored
cc https://github.com/paritytech/ci_cd/issues/926 --------- Signed-off-by: Oliver Tale-Yazdi <[email protected]> Co-authored-by: command-bot <> Co-authored-by: Oliver Tale-Yazdi <[email protected]> Co-authored-by: Bastian Köcher <[email protected]> Co-authored-by: Liam Aharon <[email protected]> Co-authored-by: Dónal Murray <[email protected]> Co-authored-by: Vladimir Istyufeev <[email protected]>
-
Oliver Tale-Yazdi authored
Add `Balances::force_adjust_total_issuance` as preparation for fixing https://github.com/polkadot-fellows/runtimes/issues/147. Important changes in `substrate/frame/balances/src/lib.rs`. TODO: - [x] Update weights --------- Signed-off-by: Oliver Tale-Yazdi <[email protected]> Co-authored-by: command-bot <> Co-authored-by: Bastian Köcher <[email protected]>
-
Andrei Sandu authored
fixes #675 --------- Signed-off-by: Andrei Sandu <[email protected]>
-
dharjeezy authored
closes https://github.com/polkadot-fellows/help-center/issues/1 --------- Signed-off-by: Oliver Tale-Yazdi <[email protected]> Co-authored-by: command-bot <> Co-authored-by: Oliver Tale-Yazdi <[email protected]>
-
Robert Hambrock authored
Moves `pallet_mmr` back behind `pallet_session` to address polkadot-fellows/runtimes#160. Opening draft for CI - should be merged or closed depending on outcome of w3f/polkadot-spec#718. --------- Co-authored-by: Adrian Catangiu <[email protected]>
-
Kian Paimani authored
This fixes a bug in nomination pools that msitakenly claimed the rewards, upon pool destruction, into the caller of `unbond` and not the actual member. More description and a PA coming soon. Opening this for now to expediate backport. --------- Co-authored-by: Gonçalo Pestana <[email protected]>
-
Clara van Staden authored
To deploy https://github.com/paritytech/polkadot-sdk/pull/3029 Co-authored-by: claravanstaden <Cats 4 life!>
-
Oliver Tale-Yazdi authored
Reverts paritytech/polkadot-sdk#2302.
🤦 ♂️ should have checked the migration CI first. We either need to reduce the `max_message_size` for the open HRMP channels on the failing chains or increase the `PageSize` of the XCMP queue. Both would be fine on a test-net, but i assume this will also fail before the next SP runtime upgrade so first need to think what best to do. AFAIK its not possible currently to change the `max_message_size` of an open HRMP channel. -
Bastian Köcher authored
Closes: https://github.com/paritytech/polkadot-sdk/issues/3123
-
Sebastian Kunert authored
In CI jobs I see calls to `forklift clean`, which apparently does not exist. From CI logs: ``` 1m$ forklift clean[0;m Cargo cache management utility Usage: forklift [command] Available Commands: completion Generate the autocompletion script for the specified shell help Help about any command serve Run forklift coordinator server for current location start Start detached forklift coordinator server for current location stop Stop forklift coordinator server for current location Flags: -c, --compression string Compression algorithm to use Available: none, xz (default "zstd") -h, --help help for forklift -p, --param stringToString map of additional parameters ex: -p S3_BUCKET_NAME=my_bucket (default []) -s, --storage string Storage driver Available: s3, fs (default "s3") -v, --verbose string Available: panic, fatal, error, warn, warning, info, debug, trace (default "info") --version version for forklift Use "forklift [command] --help" for more information about a command. ```
-
Alexandru Gheorghe authored
Candidate validation has a lot of operations that are cpu bound on its main loop things, like: ``` validation_code.hash() sp_maybe_compressed_blob::decompress( &validation_code.0, VALIDATION_CODE_BOMB_LIMIT, ) sp_maybe_compressed_blob::decompress(&pov.block_data.0, POV_BOMB_LIMIT) let code_hash = sp_crypto_hashing::blake2_256(&code).into(); ``` When you add all that you for large POV and CODE it is going to take in the order of 10s of ms and because these are cpu bound operation it is going to hog the executor thread and negatively affect other subsystems around it, so it is better to just move the subsystem on the blocking pool to make sure such unexpected behaviour is avoided. Note! In practice this subsystem does not have a high number of work to be done, so probably the impact of it is really low, but better safe than sorry. Signed-off-by: Alexandru Gheorghe <[email protected]>
-
Clara van Staden authored
- Prepares for the Deneb hardfork on Sepolia testnet on 31 January (needs to be deployed to Rococo before then) - Removes `beacon-minimal-spec` flag for simpler config - Adds test comments --------- Co-authored-by: Ron <[email protected]> Co-authored-by: claravanstaden <Cats 4 life!> Co-authored-by: Alistair Singh <[email protected]>
-