diff --git a/.test-node-subtree/.github/CODEOWNERS b/.test-node-subtree/.github/CODEOWNERS new file mode 100644 index 00000000..d150257f --- /dev/null +++ b/.test-node-subtree/.github/CODEOWNERS @@ -0,0 +1,10 @@ +# This CODEOWNERS file sets the individuals responsible for code in the era-test-node repository. + +# These users are the default owners for everything in the repo. +# They will be requested for review when someone opens a pull request. +* @matter-labs/devxp + +# You can also specify code owners for specific directories or files. +# For example: +# /src/ @developer1 @developer2 +# /docs/ @documenter diff --git a/.test-node-subtree/.github/CONTRIBUTING.md b/.test-node-subtree/.github/CONTRIBUTING.md new file mode 100644 index 00000000..d9e893b8 --- /dev/null +++ b/.test-node-subtree/.github/CONTRIBUTING.md @@ -0,0 +1,72 @@ +# Contributing + +## Welcome! 👋 + +Hello there, contributor! We're delighted that you're considering contributing to the `era-test-node` project. This document is here to guide you through the steps and best practices for contributing to this Rust-based repository. + +Please take a moment to review this document to ensure a smooth and efficient contribution process for everyone involved. + +## Getting Started + +- **Fork the repository.** Begin by forking the main `era-test-node` repository to your personal GitHub account. + +- **Clone the repository.** After forking, clone the repository to your local machine: + +```bash +git clone https://github.com//era-test-node.git +``` + +- **Create a new branch.** Use descriptive names for your branches to help identify the feature, bugfix, or enhancement you're addressing: + +```bash +git checkout -b feature/description-of-your-feature +``` + +## Making Changes + +- **Write your code.** Ensure your code is thoroughly tested and functions as expected. Clear, well-commented code is always appreciated. + +- **Compile and test.** Before submitting a pull request, ensure your code compiles, passes lint checks, and all tests are successful. You should also write unit tests for your contributions. Use the following command for these checks: + +```bash +make all +``` + +- **Commit your changes.** Adhere to the [Conventional Commits](https://www.conventionalcommits.org/) standard when writing commit messages. + +- **Push your changes.** Push the changes to your forked repository: + +```bash +git push origin feature/description-of-your-feature +``` + +## Submitting a Pull Request + +- **Initiate a pull request (PR).** Go to the main `era-test-node` repository. Your recently pushed branch should be highlighted, showing a "Compare & pull request" button. Click on it and provide a clear, detailed description of your changes in the PR. + +- **Await a review.** Our maintainers will review your PR. They might request changes or clarifications, so be ready to address any feedback. + +## Code Style Guide + +We follow Rust's official coding style guidelines. Before committing, ensure your code is formatted and lint checks pass: + +```bash +cargo fmt --all -- --check && +cargo clippy -Zunstable-options -- -D warnings --allow clippy::unwrap_used +``` + +This ensures consistent code style throughout the project and helps identify potential issues early. + +## Need Assistance? + +If you're unsure about something or have questions, don't hesitate to open an issue or initiate a discussion in our [zkSync Community Hub](https://github.com/zkSync-Community-Hub/zkync-developers/discussions). We're here to assist! + +## What's Next? + +Once your PR is approved and merged, your contribution will be integrated into the `era-test-node` repository. Congratulations, and thank you! We value your contribution and look forward to future collaborations. + +Remember, the best contributions come from enjoying the process, being respectful, and continuously learning. Thanks for being a part of our community! + +--- + +*Last updated: July 24, 2023* \ No newline at end of file diff --git a/.test-node-subtree/.github/ISSUE_TEMPLATE/bug_report.md b/.test-node-subtree/.github/ISSUE_TEMPLATE/bug_report.md new file mode 100644 index 00000000..e0a3324a --- /dev/null +++ b/.test-node-subtree/.github/ISSUE_TEMPLATE/bug_report.md @@ -0,0 +1,44 @@ +--- +name: Bug report +about: Use this template for reporting issues +title: "" +labels: bug +assignees: '' + +--- + +### 🐛 Bug Report for zkSync Era In-Memory Node + +#### 📝 Description + +Provide a clear and concise description of the bug. + +#### 🔄 Reproduction Steps + +1. Step 1 +2. Step 2 +3. ... + +#### 🤔 Expected Behavior + +Describe what you expected to happen. + +#### 😯 Current Behavior + +Describe what actually happened. + +#### 🖥️ Environment + +- **Rust version**: [e.g., rustc 1.52.0] +- **Operating System & Version**: [e.g., Ubuntu 20.04] +- **Other relevant environment details**: + +#### 📋 Additional Context + +Add any other context about the problem here. If applicable, add screenshots to help explain. + +#### 📎 Log Output + +``` +Paste any relevant log output here. +``` \ No newline at end of file diff --git a/.test-node-subtree/.github/ISSUE_TEMPLATE/config.yml b/.test-node-subtree/.github/ISSUE_TEMPLATE/config.yml new file mode 100644 index 00000000..ac7ef2e7 --- /dev/null +++ b/.test-node-subtree/.github/ISSUE_TEMPLATE/config.yml @@ -0,0 +1,8 @@ +blank_issues_enabled: true +contact_links: + - name: zksync-developers Discussion + url: https://github.com/zkSync-Community-Hub/zkync-developers/discussions + about: Please provide feedback, and ask questions here. + - name: In-memory documentation page + url: https://era.zksync.io/docs/tools/testing/era-test-node.html + about: Please refer to the documentation for immediate answers. diff --git a/.test-node-subtree/.github/ISSUE_TEMPLATE/feature_report.md b/.test-node-subtree/.github/ISSUE_TEMPLATE/feature_report.md new file mode 100644 index 00000000..4e30b239 --- /dev/null +++ b/.test-node-subtree/.github/ISSUE_TEMPLATE/feature_report.md @@ -0,0 +1,26 @@ +--- +name: Feature request +about: Use this template for requesting features +title: "" +labels: feat +assignees: '' + +--- + +### 🌟 Feature Request + +#### 📝 Description + +Provide a clear and concise description of the feature you'd like to see. + +#### 🤔 Rationale + +Explain why this feature is important and how it benefits the project. + +#### 🖼️ Mockups/Examples + +If applicable, provide mockups or examples of how the feature would work. + +#### 📋 Additional Context + +Add any other context or information about the feature request here. \ No newline at end of file diff --git a/.test-node-subtree/.github/assets/era_test_node_banner_dark.png b/.test-node-subtree/.github/assets/era_test_node_banner_dark.png new file mode 100644 index 00000000..858dafd0 Binary files /dev/null and b/.test-node-subtree/.github/assets/era_test_node_banner_dark.png differ diff --git a/.test-node-subtree/.github/assets/era_test_node_banner_light.png b/.test-node-subtree/.github/assets/era_test_node_banner_light.png new file mode 100644 index 00000000..c2cfcb17 Binary files /dev/null and b/.test-node-subtree/.github/assets/era_test_node_banner_light.png differ diff --git a/.test-node-subtree/.github/pull_request_template.md b/.test-node-subtree/.github/pull_request_template.md new file mode 100644 index 00000000..9edb5bc9 --- /dev/null +++ b/.test-node-subtree/.github/pull_request_template.md @@ -0,0 +1,17 @@ +# What :computer: +* First thing updated with this PR +* Second thing updated with this PR +* Third thing updated with this PR + +# Why :hand: +* Reason why first thing was added to PR +* Reason why second thing was added to PR +* Reason why third thing was added to PR + +# Evidence :camera: +Include screenshots, screen recordings, or `console` output here demonstrating that your changes work as intended + + + + diff --git a/.test-node-subtree/.github/workflows/check-pr-title.yml b/.test-node-subtree/.github/workflows/check-pr-title.yml new file mode 100644 index 00000000..2c79d9b6 --- /dev/null +++ b/.test-node-subtree/.github/workflows/check-pr-title.yml @@ -0,0 +1,18 @@ +name: Check PR title +on: + pull_request_target: + types: + - opened + - reopened + - edited + - synchronize + +jobs: + lint: + runs-on: ubuntu-latest + permissions: + statuses: write + steps: + - uses: aslafy-z/conventional-pr-title-action@v3 + env: + GITHUB_TOKEN: ${{ github.token }} diff --git a/.test-node-subtree/.github/workflows/checks.yaml b/.test-node-subtree/.github/workflows/checks.yaml new file mode 100644 index 00000000..f25074c6 --- /dev/null +++ b/.test-node-subtree/.github/workflows/checks.yaml @@ -0,0 +1,65 @@ +name: checks + +on: + push: + branches: [main] + tags: + - 'v*' + pull_request: + branches: [main] + workflow_dispatch: + +jobs: + # ensures proper formatting and clippy lint + lint: + name: lint + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + - name: Install Rust + uses: actions-rust-lang/setup-rust-toolchain@v1 + with: + toolchain: nightly-2023-07-23 + components: rustfmt, clippy + + - uses: actions/setup-node@v3 + with: + node-version: 18.x + cache: "yarn" + cache-dependency-path: 'e2e-tests/yarn.lock' + + - name: Run Linters + run: make lint + + # ensures build is successful + build: + name: build + runs-on: ${{ matrix.os }} + strategy: + matrix: + os: [ubuntu-latest, macos-latest] + steps: + - uses: actions/checkout@v3 + + - name: Install Rust + uses: actions-rust-lang/setup-rust-toolchain@v1 + with: + toolchain: nightly-2023-07-23 + + - name: Build Code + run: make all + + - name: Create artifact + run: | + cd ./target/release + tar -czf era_test_node-${{ matrix.os }}.tar.gz ./era_test_node* + + - name: Upload artifact + uses: actions/upload-artifact@v3 + with: + name: era_test_node-${{ matrix.os }}.tar.gz + path: ./target/release/era_test_node-${{ matrix.os }}.tar.gz + e2e: + needs: build + uses: ./.github/workflows/e2e.yml + name: e2e-tests \ No newline at end of file diff --git a/.test-node-subtree/.github/workflows/docs.yaml b/.test-node-subtree/.github/workflows/docs.yaml new file mode 100644 index 00000000..2a4eef9d --- /dev/null +++ b/.test-node-subtree/.github/workflows/docs.yaml @@ -0,0 +1,78 @@ +# Simple workflow for deploying static content to GitHub Pages +name: Deploy static content to Pages + +on: + push: + branches: ["main"] + + # Allows you to run this workflow manually from the Actions tab + workflow_dispatch: + +# Sets permissions of the GITHUB_TOKEN to allow deployment to GitHub Pages +permissions: + contents: read + pages: write + id-token: write + +# Allow only one concurrent deployment, skipping runs queued between the run in-progress and latest queued. +# However, do NOT cancel in-progress runs as we want to allow these production deployments to complete. +concurrency: + group: "pages" + cancel-in-progress: false + +jobs: + deploy: + environment: + name: github-pages + url: ${{ steps.deployment.outputs.page_url }} + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v3 + + - name: Install Rust + uses: actions-rust-lang/setup-rust-toolchain@v1 + with: + toolchain: nightly-2023-07-21 + - name: Setup Pages + uses: actions/configure-pages@v3 + + - name: Install mdbook + run: cargo install mdbook + + - name: Generate rust docs + run: | + echo "Generating docs..." + cargo doc --no-deps + + - name: Make index.html + run: echo ' + + + + + + Page Redirection + + + If you are not redirected automatically, follow this link to example. + + ' > ./target/doc/index.html + - name: Generate rustbook + run: | + make book + cp -r docs/rustbook/book target/doc + - name: Fix permissions + run: | + chmod -c -R +rX "target/doc/" | while read line; do + echo "::warning title=Invalid file permissions automatically fixed::$line" + done + - name: Upload artifact + uses: actions/upload-pages-artifact@v2 + with: + path: 'target/doc' + - name: Deploy to GitHub Pages + id: deployment + uses: actions/deploy-pages@v2 \ No newline at end of file diff --git a/.test-node-subtree/.github/workflows/e2e.yml b/.test-node-subtree/.github/workflows/e2e.yml new file mode 100644 index 00000000..4db7e764 --- /dev/null +++ b/.test-node-subtree/.github/workflows/e2e.yml @@ -0,0 +1,50 @@ +name: Testing era_test_node using e2e +on: + workflow_call: + +jobs: + e2e: + runs-on: ${{ matrix.os }} + strategy: + fail-fast: false + matrix: + os: [ubuntu-latest, macos-latest] + name: e2e + steps: + - uses: actions/checkout@v3 + with: + fetch-depth: 0 + + - uses: actions/setup-node@v3 + with: + node-version: 18.x + cache: "yarn" + cache-dependency-path: 'e2e-tests/yarn.lock' + + - name: Download artifacts + uses: actions/download-artifact@v3 + with: + name: era_test_node-${{ matrix.os }}.tar.gz + + - name: Start the era_test_node + id: start_node + run: | + echo "Extracting era_test_node binary" + tar -xzf era_test_node-${{ matrix.os }}.tar.gz + chmod +x era_test_node + echo "Starting node in background" + ./era_test_node run 2>&1 | tee era_test_node_output.log & + echo "PID=$!" >> $GITHUB_ENV + + - name: Launch tests + id: launch + run: | + echo "Run tests" + make test-e2e + + - name: Stop the era_test_node and print output logs + id: stop_node + if: always() + run: | + cat era_test_node_output.log + kill $PID diff --git a/.test-node-subtree/.github/workflows/release.yml b/.test-node-subtree/.github/workflows/release.yml new file mode 100644 index 00000000..67154c52 --- /dev/null +++ b/.test-node-subtree/.github/workflows/release.yml @@ -0,0 +1,182 @@ +# This workflow is borrowed from reth, which is borrowed from Lighthouse: +# reth: https://github.com/paradigmxyz/reth/blob/500b0fac135fe07635d871d64467326599e2b27e/.github/workflows/release.yml +# lighthouse: https://github.com/sigp/lighthouse/blob/693886b94176faa4cb450f024696cb69cda2fe58/.github/workflows/release.yml + +name: release + +on: + push: + tags: + - v* + +env: + REPO_NAME: ${{ github.repository_owner }}/era-test-node + CARGO_TERM_COLOR: always + +jobs: + extract-version: + name: extract version + runs-on: ubuntu-latest + steps: + - name: Extract version + run: echo "VERSION=$(echo ${GITHUB_REF#refs/tags/})" >> $GITHUB_OUTPUT + id: extract_version + outputs: + VERSION: ${{ steps.extract_version.outputs.VERSION }} + + build: + name: build release + strategy: + matrix: + arch: [x86_64-unknown-linux-gnu, aarch64-unknown-linux-gnu, x86_64-apple-darwin, aarch64-apple-darwin] + include: + - arch: x86_64-unknown-linux-gnu + platform: ubuntu-20.04 + - arch: aarch64-unknown-linux-gnu + platform: ubuntu-20.04 + - arch: x86_64-apple-darwin + platform: macos-latest + - arch: aarch64-apple-darwin + platform: macos-latest + + runs-on: ${{ matrix.platform }} + needs: [extract-version] + steps: + - name: Checkout sources + uses: actions/checkout@v3 + + - name: Install Rust + uses: actions-rust-lang/setup-rust-toolchain@v1 + with: + toolchain: nightly-2023-07-21 + - name: Install target + run: rustup target add ${{ matrix.arch }} + + - name: Run cargo clean + run: cargo clean + + # ============================== + # Builds + # ============================== + + - name: Install cross from source + run: | + cargo install --git https://github.com/cross-rs/cross cross --branch main + + - name: Build era-test-node for ${{ matrix.arch }} + run: | + make build-${{ matrix.arch }} + + - name: Rename and move binary + run: | + mkdir artifacts + mv target/${{ matrix.arch }}/release/era_test_node ./artifacts + + - name: Create artifacts + run: | + cd artifacts + tar -czf era_test_node-${{ needs.extract-version.outputs.VERSION }}-${{ matrix.arch }}.tar.gz era_test_node* + mv *tar.gz* .. + + # ======================================================================= + # Upload artifacts + # This is required to share artifacts between different jobs + # ======================================================================= + - name: Upload artifact + uses: actions/upload-artifact@v3 + with: + name: era_test_node-${{ needs.extract-version.outputs.VERSION }}-${{ matrix.arch }}.tar.gz + path: era_test_node-${{ needs.extract-version.outputs.VERSION }}-${{ matrix.arch }}.tar.gz + + - name: Upload signature + uses: actions/upload-artifact@v3 + with: + name: era_test_node-${{ needs.extract-version.outputs.VERSION }}-${{ matrix.arch }}.tar.gz.asc + path: era_test_node-${{ needs.extract-version.outputs.VERSION }}-${{ matrix.arch }}.tar.gz.asc + + draft-release: + name: draft release + needs: [build, extract-version] + runs-on: ubuntu-latest + env: + VERSION: ${{ needs.extract-version.outputs.VERSION }} + permissions: + # Required to post the release + contents: write + steps: + # This is necessary for generating the changelog. It has to come before "Download Artifacts" or else it deletes the artifacts. + - name: Checkout sources + uses: actions/checkout@v3 + with: + fetch-depth: 0 + + # ============================== + # Download artifacts + # ============================== + - name: Download artifacts + uses: actions/download-artifact@v3 + + # ============================== + # Create release draft + # ============================== + - name: Generate full changelog + id: changelog + run: | + echo "CHANGELOG<> $GITHUB_OUTPUT + echo "$(git log --pretty=format:"- %s" $(git describe --tags --abbrev=0 ${{ env.VERSION }}^)..${{ env.VERSION }})" >> $GITHUB_OUTPUT + echo "EOF" >> $GITHUB_OUTPUT + + - name: Generate list of contributors + id: contributors + run: | + echo "CONTRIBUTORS<> $GITHUB_OUTPUT + echo "$(git log --pretty=format:"- %aN (%aE)" $(git describe --tags --abbrev=0 ${{ env.VERSION }}^)..${{ env.VERSION }} | sort | uniq)" >> $GITHUB_OUTPUT + echo "EOF" >> $GITHUB_OUTPUT + + - name: Create release draft + env: + GITHUB_USER: ${{ github.repository_owner }} + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + + # The formatting here is borrowed from reth which borrowed it from Lighthouse (which is borrowed from OpenEthereum): https://github.com/openethereum/openethereum/blob/main/.github/workflows/build.yml + run: | + body=$(cat <<- "ENDBODY" + + + ## 📋 Summary + + ### 🐛 Bug Fixes: + - TBD + + ### ✨ New Features: + - TBD + + ### ⚠️ Breaking Changes: + - TBD + + ## 📜 All Changes + + ${{ steps.changelog.outputs.CHANGELOG }} + + ## ⭐ Contributors + + ${{ steps.contributors.outputs.CONTRIBUTORS }} + + ## 📥 Binaries + + | System | Architecture | Binary | + |:---:|:---:|:---:| + | | x86_64 | [era-test-node-${{ env.VERSION }}-x86_64-unknown-linux-gnu.tar.gz](https://github.com/${{ env.REPO_NAME }}/releases/download/${{ env.VERSION }}/era_test_node-${{ env.VERSION }}-x86_64-unknown-linux-gnu.tar.gz) | + | | aarch64 | [era-test-node-${{ env.VERSION }}-aarch64-unknown-linux-gnu.tar.gz](https://github.com/${{ env.REPO_NAME }}/releases/download/${{ env.VERSION }}/era_test_node-${{ env.VERSION }}-aarch64-unknown-linux-gnu.tar.gz) | + | | x86_64 | [era-test-node-${{ env.VERSION }}-x86_64-apple-darwin.tar.gz](https://github.com/${{ env.REPO_NAME }}/releases/download/${{ env.VERSION }}/era_test_node-${{ env.VERSION }}-x86_64-apple-darwin.tar.gz) | + | | aarch64 | [era-test-node-${{ env.VERSION }}-aarch64-apple-darwin.tar.gz](https://github.com/${{ env.REPO_NAME }}/releases/download/${{ env.VERSION }}/era_test_node-${{ env.VERSION }}-aarch64-apple-darwin.tar.gz) | + | | | | + ENDBODY + ) + assets=() + for asset in ./era_test_node-*.tar.gz*; do + assets+=("$asset/$asset") + done + tag_name="${{ env.VERSION }}" + echo "$body" | gh release create "$tag_name" "${assets[@]}" --draft -F "-" -t "Release: $tag_name" \ No newline at end of file diff --git a/.test-node-subtree/.github/workflows/secret_scanner.yaml b/.test-node-subtree/.github/workflows/secret_scanner.yaml new file mode 100644 index 00000000..1d237c6f --- /dev/null +++ b/.test-node-subtree/.github/workflows/secret_scanner.yaml @@ -0,0 +1,17 @@ +name: Leaked Secrets Scan +on: [pull_request] +jobs: + TruffleHog: + runs-on: ubuntu-latest + steps: + - name: Checkout code + uses: actions/checkout@v3 + with: + fetch-depth: 0 + - name: TruffleHog OSS + uses: trufflesecurity/trufflehog@0c66d30c1f4075cee1aada2e1ab46dabb1b0071a + with: + path: ./ + base: ${{ github.event.repository.default_branch }} + head: HEAD + extra_args: --debug --only-verified \ No newline at end of file diff --git a/.test-node-subtree/.github/workflows/tests.yaml b/.test-node-subtree/.github/workflows/tests.yaml new file mode 100644 index 00000000..8d785306 --- /dev/null +++ b/.test-node-subtree/.github/workflows/tests.yaml @@ -0,0 +1,33 @@ +name: run + +on: + push: + branches: [main] + tags: + - 'v*' + pull_request: + branches: [main] + workflow_dispatch: + +jobs: + test: + name: unit-tests + strategy: + matrix: + platform: [macos-latest, ubuntu-22.04-github-hosted-16core] + runs-on: ${{ matrix.platform }} + + steps: + - name: Checkout Code + uses: actions/checkout@v3 + + - name: Install Rust + uses: actions-rust-lang/setup-rust-toolchain@v1 + with: + toolchain: nightly-2023-07-21 + + - name: Install cargo-nextest + run: cargo install cargo-nextest + + - name: Run tests + run: cargo nextest run diff --git a/.test-node-subtree/.gitignore b/.test-node-subtree/.gitignore new file mode 100644 index 00000000..106a7b11 --- /dev/null +++ b/.test-node-subtree/.gitignore @@ -0,0 +1,17 @@ +/target +etc/system-contracts/.yarn +etc/system-contracts/node_modules +etc/system-contracts/cache-zk +etc/system-contracts/artifacts-zk +etc/system-contracts/typechain-types +etc/system-contracts/.yarnrc.yml +etc/system-contracts/bootloader/build + +etc/**/*.zbin +.vscode/* +!.vscode/extensions.json +!.vscode/launch.json +!.vscode/tasks.json + +*.log +.cache \ No newline at end of file diff --git a/.test-node-subtree/.vscode/extensions.json b/.test-node-subtree/.vscode/extensions.json new file mode 100644 index 00000000..5d899281 --- /dev/null +++ b/.test-node-subtree/.vscode/extensions.json @@ -0,0 +1,8 @@ +{ + "recommendations": [ + "rust-lang.rust-analyzer", + "humao.rest-client", + "vadimcn.vscode-lldb", + "github.vscode-github-actions" + ], +} \ No newline at end of file diff --git a/.test-node-subtree/.vscode/launch.json b/.test-node-subtree/.vscode/launch.json new file mode 100644 index 00000000..2373fac6 --- /dev/null +++ b/.test-node-subtree/.vscode/launch.json @@ -0,0 +1,69 @@ +{ + // Use IntelliSense to learn about possible attributes. + // Hover to view descriptions of existing attributes. + // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 + "version": "0.2.0", + "configurations": [ + { + "type": "lldb", + "request": "launch", + "name": "Debug era_test_node", + "cargo": { + "args": [ + "build", + "--bin=era_test_node", + "--package=era_test_node" + ], + "filter": { + "name": "era_test_node", + "kind": "bin" + } + }, + "args": [ + "run" + ], + "env": { + "CARGO_PROFILE_DEV": "true" + }, + "cwd": "${workspaceFolder}" + }, + { + "type": "lldb", + "request": "launch", + "name": "Debug era_test_node w/ system-contracts", + "cargo": { + "args": [ + "build", + "--bin=era_test_node", + "--package=era_test_node" + ], + "filter": { + "name": "era_test_node", + "kind": "bin" + } + }, + "env": { + "CARGO_PROFILE_DEV": "true", + "RUST_LOG": "vm=trace", + "ZKSYNC_HOME": "${workspaceFolder}" + }, + "args": [ + "--dev-system-contracts=local", + "run" + ], + "preLaunchTask": "rebuild-contracts", + "cwd": "${workspaceFolder}" + }, + { + "name": "E2E Tests", + "type": "node", + "request": "launch", + "console": "integratedTerminal", + "cwd": "${workspaceFolder}/e2e-tests", + "runtimeExecutable": "yarn", + "runtimeArgs": [ + "test" + ] + }, + ] +} \ No newline at end of file diff --git a/.test-node-subtree/.vscode/tasks.json b/.test-node-subtree/.vscode/tasks.json new file mode 100644 index 00000000..f0012bf3 --- /dev/null +++ b/.test-node-subtree/.vscode/tasks.json @@ -0,0 +1,11 @@ +{ + "version": "2.0.0", + "tasks": [{ + "label": "rebuild-contracts", + "command": "make rebuild-contracts", + "type": "shell", + "presentation": { + "close": true + } + }] +} diff --git a/.test-node-subtree/Cargo.lock b/.test-node-subtree/Cargo.lock new file mode 100644 index 00000000..09ddd0f8 --- /dev/null +++ b/.test-node-subtree/Cargo.lock @@ -0,0 +1,10111 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "Inflector" +version = "0.11.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fe438c63458706e03479442743baae6c88256498e6431708f6dfc520a26515d3" +dependencies = [ + "lazy_static", + "regex", +] + +[[package]] +name = "actix-codec" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "617a8268e3537fe1d8c9ead925fca49ef6400927ee7bc26750e90ecee14ce4b8" +dependencies = [ + "bitflags 1.3.2", + "bytes 1.5.0", + "futures-core", + "futures-sink", + "memchr", + "pin-project-lite", + "tokio", + "tokio-util 0.7.10", + "tracing", +] + +[[package]] +name = "actix-cors" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b340e9cfa5b08690aae90fb61beb44e9b06f44fe3d0f93781aaa58cfba86245e" +dependencies = [ + "actix-utils", + "actix-web", + "derive_more", + "futures-util", + "log", + "once_cell", + "smallvec", +] + +[[package]] +name = "actix-http" +version = "3.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a92ef85799cba03f76e4f7c10f533e66d87c9a7e7055f3391f09000ad8351bc9" +dependencies = [ + "actix-codec", + "actix-rt", + "actix-service", + "actix-utils", + "ahash 0.8.6", + "base64 0.21.5", + "bitflags 2.4.1", + "brotli", + "bytes 1.5.0", + "bytestring", + "derive_more", + "encoding_rs", + "flate2", + "futures-core", + "h2", + "http", + "httparse", + "httpdate", + "itoa", + "language-tags", + "local-channel", + "mime", + "percent-encoding", + "pin-project-lite", + "rand 0.8.5", + "sha1", + "smallvec", + "tokio", + "tokio-util 0.7.10", + "tracing", + "zstd 0.12.4", +] + +[[package]] +name = "actix-macros" +version = "0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e01ed3140b2f8d422c68afa1ed2e85d996ea619c988ac834d255db32138655cb" +dependencies = [ + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "actix-router" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d66ff4d247d2b160861fa2866457e85706833527840e4133f8f49aa423a38799" +dependencies = [ + "bytestring", + "http", + "regex", + "serde", + "tracing", +] + +[[package]] +name = "actix-rt" +version = "2.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "28f32d40287d3f402ae0028a9d54bef51af15c8769492826a69d28f81893151d" +dependencies = [ + "actix-macros", + "futures-core", + "tokio", +] + +[[package]] +name = "actix-server" +version = "2.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3eb13e7eef0423ea6eab0e59f6c72e7cb46d33691ad56a726b3cd07ddec2c2d4" +dependencies = [ + "actix-rt", + "actix-service", + "actix-utils", + "futures-core", + "futures-util", + "mio 0.8.9", + "socket2 0.5.5", + "tokio", + "tracing", +] + +[[package]] +name = "actix-service" +version = "2.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3b894941f818cfdc7ccc4b9e60fa7e53b5042a2e8567270f9147d5591893373a" +dependencies = [ + "futures-core", + "paste", + "pin-project-lite", +] + +[[package]] +name = "actix-utils" +version = "3.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "88a1dcdff1466e3c2488e1cb5c36a71822750ad43839937f85d2f4d9f8b705d8" +dependencies = [ + "local-waker", + "pin-project-lite", +] + +[[package]] +name = "actix-web" +version = "4.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0e4a5b5e29603ca8c94a77c65cf874718ceb60292c5a5c3e5f4ace041af462b9" +dependencies = [ + "actix-codec", + "actix-http", + "actix-macros", + "actix-router", + "actix-rt", + "actix-server", + "actix-service", + "actix-utils", + "actix-web-codegen", + "ahash 0.8.6", + "bytes 1.5.0", + "bytestring", + "cfg-if 1.0.0", + "cookie", + "derive_more", + "encoding_rs", + "futures-core", + "futures-util", + "itoa", + "language-tags", + "log", + "mime", + "once_cell", + "pin-project-lite", + "regex", + "serde", + "serde_json", + "serde_urlencoded", + "smallvec", + "socket2 0.5.5", + "time", + "url", +] + +[[package]] +name = "actix-web-codegen" +version = "4.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eb1f50ebbb30eca122b188319a4398b3f7bb4a8cdf50ecfb73bfc6a3c3ce54f5" +dependencies = [ + "actix-router", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "addchain" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3b2e69442aa5628ea6951fa33e24efe8313f4321a91bd729fc2f75bdfc858570" +dependencies = [ + "num-bigint 0.3.3", + "num-integer", + "num-traits", +] + +[[package]] +name = "addr2line" +version = "0.21.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a30b2e23b9e17a9f90641c7ab1549cd9b44f296d3ccbf309d2863cfe398a0cb" +dependencies = [ + "gimli", +] + +[[package]] +name = "adler" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" + +[[package]] +name = "aead" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d122413f284cf2d62fb1b7db97e02edb8cda96d769b16e443a4f6195e35662b0" +dependencies = [ + "crypto-common", + "generic-array 0.14.7", +] + +[[package]] +name = "aes" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "884391ef1066acaa41e766ba8f596341b96e93ce34f9a43e7d24bf0a0eaf0561" +dependencies = [ + "aes-soft", + "aesni", + "cipher 0.2.5", +] + +[[package]] +name = "aes" +version = "0.8.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac1f845298e95f983ff1944b728ae08b8cebab80d684f0a832ed0fc74dfa27e2" +dependencies = [ + "cfg-if 1.0.0", + "cipher 0.4.4", + "cpufeatures", +] + +[[package]] +name = "aes-ctr" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7729c3cde54d67063be556aeac75a81330d802f0259500ca40cb52967f975763" +dependencies = [ + "aes-soft", + "aesni", + "cipher 0.2.5", + "ctr 0.6.0", +] + +[[package]] +name = "aes-gcm" +version = "0.10.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "831010a0f742e1209b3bcea8fab6a8e149051ba6099432c8cb2cc117dec3ead1" +dependencies = [ + "aead", + "aes 0.8.3", + "cipher 0.4.4", + "ctr 0.9.2", + "ghash", + "subtle", +] + +[[package]] +name = "aes-soft" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "be14c7498ea50828a38d0e24a765ed2effe92a705885b57d029cd67d45744072" +dependencies = [ + "cipher 0.2.5", + "opaque-debug 0.3.0", +] + +[[package]] +name = "aesni" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ea2e11f5e94c2f7d386164cc2aa1f97823fed6f259e486940a71c174dd01b0ce" +dependencies = [ + "cipher 0.2.5", + "opaque-debug 0.3.0", +] + +[[package]] +name = "ahash" +version = "0.7.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a824f2aa7e75a0c98c5a504fceb80649e9c35265d44525b5f94de4771a395cd" +dependencies = [ + "getrandom 0.2.11", + "once_cell", + "version_check", +] + +[[package]] +name = "ahash" +version = "0.8.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "91429305e9f0a25f6205c5b8e0d2db09e0708a7a6df0f42212bb56c32c8ac97a" +dependencies = [ + "cfg-if 1.0.0", + "getrandom 0.2.11", + "once_cell", + "version_check", + "zerocopy", +] + +[[package]] +name = "aho-corasick" +version = "1.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b2969dcb958b36655471fc61f7e416fa76033bdd4bfed0678d8fee1e2d07a1f0" +dependencies = [ + "memchr", +] + +[[package]] +name = "alloc-no-stdlib" +version = "2.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cc7bb162ec39d46ab1ca8c77bf72e890535becd1751bb45f64c597edb4c8c6b3" + +[[package]] +name = "alloc-stdlib" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "94fb8275041c72129eb51b7d0322c29b8387a0386127718b096429201a5d6ece" +dependencies = [ + "alloc-no-stdlib", +] + +[[package]] +name = "android-tzdata" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e999941b234f3131b00bc13c22d06e8c5ff726d1b6318ac7eb276997bbb4fef0" + +[[package]] +name = "android_system_properties" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311" +dependencies = [ + "libc", +] + +[[package]] +name = "ansi_term" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d52a9bb7ec0cf484c551830a7ce27bd20d67eac647e1befb56b0be4ee39a55d2" +dependencies = [ + "winapi 0.3.9", +] + +[[package]] +name = "anstream" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2ab91ebe16eb252986481c5b62f6098f3b698a45e34b5b98200cf20dd2484a44" +dependencies = [ + "anstyle", + "anstyle-parse", + "anstyle-query", + "anstyle-wincon", + "colorchoice", + "utf8parse", +] + +[[package]] +name = "anstyle" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7079075b41f533b8c61d2a4d073c4676e1f8b249ff94a393b0595db304e0dd87" + +[[package]] +name = "anstyle-parse" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "317b9a89c1868f5ea6ff1d9539a69f45dffc21ce321ac1fd1160dfa48c8e2140" +dependencies = [ + "utf8parse", +] + +[[package]] +name = "anstyle-query" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5ca11d4be1bab0c8bc8734a9aa7bf4ee8316d462a08c6ac5052f888fef5b494b" +dependencies = [ + "windows-sys 0.48.0", +] + +[[package]] +name = "anstyle-wincon" +version = "3.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f0699d10d2f4d628a98ee7b57b289abbc98ff3bad977cb3152709d4bf2330628" +dependencies = [ + "anstyle", + "windows-sys 0.48.0", +] + +[[package]] +name = "anyhow" +version = "1.0.75" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a4668cab20f66d8d020e1fbc0ebe47217433c1b6c8f2040faf858554e394ace6" + +[[package]] +name = "arr_macro" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6a105bfda48707cf19220129e78fca01e9639433ffaef4163546ed8fb04120a5" +dependencies = [ + "arr_macro_impl", + "proc-macro-hack", +] + +[[package]] +name = "arr_macro_impl" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0609c78bd572f4edc74310dfb63a01f5609d53fa8b4dd7c4d98aef3b3e8d72d1" +dependencies = [ + "proc-macro-hack", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "arrayref" +version = "0.3.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6b4930d2cb77ce62f89ee5d5289b4ac049559b1c45539271f5ed4fdc7db34545" + +[[package]] +name = "arrayvec" +version = "0.4.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cd9fd44efafa8690358b7408d253adf110036b88f55672a933f01d616ad9b1b9" +dependencies = [ + "nodrop", +] + +[[package]] +name = "arrayvec" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b" + +[[package]] +name = "arrayvec" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "96d30a06541fbafbc7f82ed10c06164cfbd2c401138f6addd8404629c4b16711" + +[[package]] +name = "ascii-canvas" +version = "3.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8824ecca2e851cec16968d54a01dd372ef8f95b244fb84b84e70128be347c3c6" +dependencies = [ + "term", +] + +[[package]] +name = "async-compression" +version = "0.4.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bc2d0cfb2a7388d34f590e76686704c494ed7aaceed62ee1ba35cbf363abc2a5" +dependencies = [ + "brotli", + "flate2", + "futures-core", + "memchr", + "pin-project-lite", + "tokio", + "zstd 0.13.0", + "zstd-safe 7.0.0", +] + +[[package]] +name = "async-lock" +version = "2.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "287272293e9d8c41773cec55e365490fe034813a2f172f502d6ddcf75b2f582b" +dependencies = [ + "event-listener", +] + +[[package]] +name = "async-stream" +version = "0.3.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cd56dd203fef61ac097dd65721a419ddccb106b2d2b70ba60a6b529f03961a51" +dependencies = [ + "async-stream-impl", + "futures-core", + "pin-project-lite", +] + +[[package]] +name = "async-stream-impl" +version = "0.3.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "16e62a023e7c117e27523144c5d2459f4397fcc3cab0085af8e2224f643a0193" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "async-trait" +version = "0.1.74" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a66537f1bb974b254c98ed142ff995236e81b9d0fe4db0575f46612cb15eb0f9" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "async_io_stream" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b6d7b9decdf35d8908a7e3ef02f64c5e9b1695e230154c0e8de3969142d9b94c" +dependencies = [ + "futures 0.3.29", + "pharos", + "rustc_version", +] + +[[package]] +name = "atoi" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "616896e05fc0e2649463a93a15183c6a16bf03413a7af88ef1285ddedfa9cda5" +dependencies = [ + "num-traits", +] + +[[package]] +name = "atty" +version = "0.2.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d9b39be18770d11421cdb1b9947a45dd3f37e93092cbf377614828a319d5fee8" +dependencies = [ + "hermit-abi 0.1.19", + "libc", + "winapi 0.3.9", +] + +[[package]] +name = "auto_impl" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fee3da8ef1276b0bee5dd1c7258010d8fffd31801447323115a25560e1327b89" +dependencies = [ + "proc-macro-error", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "autocfg" +version = "0.1.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0dde43e75fd43e8a1bf86103336bc699aa8d17ad1be60c76c0bdfd4828e19b78" +dependencies = [ + "autocfg 1.1.0", +] + +[[package]] +name = "autocfg" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" + +[[package]] +name = "axum" +version = "0.6.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3b829e4e32b91e643de6eafe82b1d90675f5874230191a4ffbc1b336dec4d6bf" +dependencies = [ + "async-trait", + "axum-core", + "bitflags 1.3.2", + "bytes 1.5.0", + "futures-util", + "http", + "http-body", + "hyper", + "itoa", + "matchit", + "memchr", + "mime", + "percent-encoding", + "pin-project-lite", + "rustversion", + "serde", + "serde_json", + "serde_path_to_error", + "sync_wrapper", + "tokio", + "tower", + "tower-layer", + "tower-service", +] + +[[package]] +name = "axum-core" +version = "0.3.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "759fa577a247914fd3f7f76d62972792636412fbfd634cd452f6a385a74d2d2c" +dependencies = [ + "async-trait", + "bytes 1.5.0", + "futures-util", + "http", + "http-body", + "mime", + "rustversion", + "tower-layer", + "tower-service", +] + +[[package]] +name = "backon" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0c1a6197b2120bb2185a267f6515038558b019e92b832bb0320e96d66268dcf9" +dependencies = [ + "fastrand 1.9.0", + "futures-core", + "pin-project", + "tokio", +] + +[[package]] +name = "backtrace" +version = "0.3.69" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2089b7e3f35b9dd2d0ed921ead4f6d318c27680d4a5bd167b3ee120edb105837" +dependencies = [ + "addr2line", + "cc", + "cfg-if 1.0.0", + "libc", + "miniz_oxide", + "object", + "rustc-demangle", +] + +[[package]] +name = "base16ct" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "349a06037c7bf932dd7e7d1f653678b2038b9ad46a74102f1fc7bd7872678cce" + +[[package]] +name = "base16ct" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4c7f02d4ea65f2c1853089ffd8d2787bdbc63de2f0d29dedbcf8ccdfa0ccd4cf" + +[[package]] +name = "base64" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9e1b586273c5702936fe7b7d6896644d8be71e6314cfe09d3167c95f712589e8" + +[[package]] +name = "base64" +version = "0.21.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "35636a1494ede3b646cc98f74f8e62c773a38a659ebc777a2cf26b9b74171df9" + +[[package]] +name = "base64ct" +version = "1.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8c3c1a368f70d6cf7302d78f8f7093da241fb8e8807c05cc9e51a125895a6d5b" + +[[package]] +name = "bech32" +version = "0.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d86b93f97252c47b41663388e6d155714a9d0c398b99f1005cbc5f978b29f445" + +[[package]] +name = "beef" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3a8241f3ebb85c056b509d4327ad0358fbbba6ffb340bf388f26350aeda225b1" +dependencies = [ + "serde", +] + +[[package]] +name = "bellman_ce" +version = "0.3.2" +source = "git+https://github.com/matter-labs/bellman?branch=dev#5520aa2274afe73d281373c92b007a2ecdebfbea" +dependencies = [ + "arrayvec 0.7.4", + "bit-vec", + "blake2s_const 0.6.0 (git+https://github.com/matter-labs/bellman?branch=dev)", + "blake2s_simd", + "byteorder", + "cfg-if 1.0.0", + "crossbeam 0.7.3", + "futures 0.3.29", + "hex", + "lazy_static", + "num_cpus", + "pairing_ce 0.28.5 (registry+https://github.com/rust-lang/crates.io-index)", + "rand 0.4.6", + "serde", + "smallvec", + "tiny-keccak 1.5.0", +] + +[[package]] +name = "bellman_ce" +version = "0.3.2" +source = "git+https://github.com/matter-labs/bellman?branch=snark-wrapper#e01e5fa08a97a113e76ec8a69d06fe6cc2c82d17" +dependencies = [ + "arrayvec 0.7.4", + "bit-vec", + "blake2s_const 0.6.0 (git+https://github.com/matter-labs/bellman?branch=snark-wrapper)", + "blake2s_simd", + "byteorder", + "cfg-if 1.0.0", + "crossbeam 0.7.3", + "futures 0.3.29", + "hex", + "lazy_static", + "num_cpus", + "pairing_ce 0.28.5 (registry+https://github.com/rust-lang/crates.io-index)", + "rand 0.4.6", + "serde", + "smallvec", + "tiny-keccak 1.5.0", +] + +[[package]] +name = "bigdecimal" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d1e50562e37200edf7c6c43e54a08e64a5553bfb59d9c297d5572512aa517256" +dependencies = [ + "num-bigint 0.3.3", + "num-integer", + "num-traits", + "serde", +] + +[[package]] +name = "bincode" +version = "1.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b1f45e9417d87227c7a56d22e471c6206462cba514c7590c09aff4cf6d1ddcad" +dependencies = [ + "serde", +] + +[[package]] +name = "bindgen" +version = "0.65.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cfdf7b466f9a4903edc73f95d6d2bcd5baf8ae620638762244d3f60143643cc5" +dependencies = [ + "bitflags 1.3.2", + "cexpr", + "clang-sys", + "lazy_static", + "lazycell", + "peeking_take_while", + "prettyplease", + "proc-macro2 1.0.70", + "quote 1.0.33", + "regex", + "rustc-hash", + "shlex", + "syn 2.0.39", +] + +[[package]] +name = "bit-set" +version = "0.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0700ddab506f33b20a03b13996eccd309a48e5ff77d0d95926aa0210fb4e95f1" +dependencies = [ + "bit-vec", +] + +[[package]] +name = "bit-vec" +version = "0.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "349f9b6a179ed607305526ca489b34ad0a41aed5f7980fa90eb03160b69598fb" +dependencies = [ + "serde", +] + +[[package]] +name = "bitflags" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" + +[[package]] +name = "bitflags" +version = "2.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "327762f6e5a765692301e5bb513e0d9fef63be86bbc14528052b1cd3e6f03e07" + +[[package]] +name = "bitmaps" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "031043d04099746d8db04daf1fa424b2bc8bd69d92b25962dcde24da39ab64a2" +dependencies = [ + "typenum", +] + +[[package]] +name = "bitvec" +version = "0.20.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7774144344a4faa177370406a7ff5f1da24303817368584c6206c8303eb07848" +dependencies = [ + "funty 1.1.0", + "radium 0.6.2", + "tap", + "wyz 0.2.0", +] + +[[package]] +name = "bitvec" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1bc2832c24239b0141d5674bb9174f9d68a8b5b3f2753311927c172ca46f7e9c" +dependencies = [ + "funty 2.0.0", + "radium 0.7.0", + "tap", + "wyz 0.5.1", +] + +[[package]] +name = "blake2" +version = "0.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0a4e37d16930f5459780f5621038b6382b9bb37c19016f39fb6b5808d831f174" +dependencies = [ + "crypto-mac 0.8.0", + "digest 0.9.0", + "opaque-debug 0.3.0", +] + +[[package]] +name = "blake2" +version = "0.10.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "46502ad458c9a52b69d4d4d32775c788b7a1b85e8bc9d482d92250fc0e3f8efe" +dependencies = [ + "digest 0.10.7", +] + +[[package]] +name = "blake2" +version = "0.10.6" +source = "git+https://github.com/RustCrypto/hashes.git?rev=1f727ce37ff40fa0cce84eb8543a45bdd3ca4a4e#1f727ce37ff40fa0cce84eb8543a45bdd3ca4a4e" +dependencies = [ + "digest 0.10.7", +] + +[[package]] +name = "blake2-rfc_bellman_edition" +version = "0.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fdc60350286c7c3db13b98e91dbe5c8b6830a6821bc20af5b0c310ce94d74915" +dependencies = [ + "arrayvec 0.4.12", + "byteorder", + "constant_time_eq", +] + +[[package]] +name = "blake2s_const" +version = "0.6.0" +source = "git+https://github.com/matter-labs/bellman?branch=dev#5520aa2274afe73d281373c92b007a2ecdebfbea" +dependencies = [ + "arrayref", + "arrayvec 0.5.2", + "constant_time_eq", +] + +[[package]] +name = "blake2s_const" +version = "0.6.0" +source = "git+https://github.com/matter-labs/bellman?branch=snark-wrapper#e01e5fa08a97a113e76ec8a69d06fe6cc2c82d17" +dependencies = [ + "arrayref", + "arrayvec 0.5.2", + "constant_time_eq", +] + +[[package]] +name = "blake2s_simd" +version = "0.5.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9e461a7034e85b211a4acb57ee2e6730b32912b06c08cc242243c39fc21ae6a2" +dependencies = [ + "arrayref", + "arrayvec 0.5.2", + "constant_time_eq", +] + +[[package]] +name = "block-buffer" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c0940dc441f31689269e10ac70eb1002a3a1d3ad1390e030043662eb7fe4688b" +dependencies = [ + "block-padding 0.1.5", + "byte-tools", + "byteorder", + "generic-array 0.12.4", +] + +[[package]] +name = "block-buffer" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4152116fd6e9dadb291ae18fc1ec3575ed6d84c29642d97890f4b4a3417297e4" +dependencies = [ + "block-padding 0.2.1", + "generic-array 0.14.7", +] + +[[package]] +name = "block-buffer" +version = "0.10.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3078c7629b62d3f0439517fa394996acacc5cbc91c5a20d8c658e77abd503a71" +dependencies = [ + "generic-array 0.14.7", +] + +[[package]] +name = "block-modes" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "57a0e8073e8baa88212fb5823574c02ebccb395136ba9a164ab89379ec6072f0" +dependencies = [ + "block-padding 0.2.1", + "cipher 0.2.5", +] + +[[package]] +name = "block-padding" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fa79dedbb091f449f1f39e53edf88d5dbe95f895dae6135a8d7b881fb5af73f5" +dependencies = [ + "byte-tools", +] + +[[package]] +name = "block-padding" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8d696c370c750c948ada61c69a0ee2cbbb9c50b1019ddb86d9317157a99c2cae" + +[[package]] +name = "blst" +version = "0.3.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c94087b935a822949d3291a9989ad2b2051ea141eda0fd4e478a75f6aa3e604b" +dependencies = [ + "cc", + "glob", + "threadpool", + "zeroize", +] + +[[package]] +name = "boojum" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-boojum.git?branch=main#1588de7669b016df3f81f7139a1a4b131840e48b" +dependencies = [ + "arrayvec 0.7.4", + "bincode", + "blake2 0.10.6 (registry+https://github.com/rust-lang/crates.io-index)", + "const_format", + "convert_case 0.6.0", + "crossbeam 0.8.2", + "crypto-bigint 0.5.5", + "cs_derive 0.1.0 (git+https://github.com/matter-labs/era-boojum.git?branch=main)", + "derivative", + "ethereum-types 0.14.1", + "firestorm", + "itertools 0.10.5", + "lazy_static", + "num-modular", + "num_cpus", + "packed_simd", + "pairing_ce 0.28.5 (git+https://github.com/matter-labs/pairing.git)", + "rand 0.8.5", + "rayon", + "serde", + "sha2 0.10.8", + "sha3 0.10.6", + "smallvec", + "unroll", +] + +[[package]] +name = "brotli" +version = "3.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "516074a47ef4bce09577a3b379392300159ce5b1ba2e501ff1c819950066100f" +dependencies = [ + "alloc-no-stdlib", + "alloc-stdlib", + "brotli-decompressor", +] + +[[package]] +name = "brotli-decompressor" +version = "2.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4e2e4afe60d7dd600fdd3de8d0f08c2b7ec039712e3b6137ff98b7004e82de4f" +dependencies = [ + "alloc-no-stdlib", + "alloc-stdlib", +] + +[[package]] +name = "bs58" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f5353f36341f7451062466f0b755b96ac3a9547e4d7f6b70d603fc721a7d7896" +dependencies = [ + "sha2 0.10.8", + "tinyvec", +] + +[[package]] +name = "bstr" +version = "0.2.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ba3569f383e8f1598449f1a423e72e99569137b47740b1da11ef19af3d5c3223" +dependencies = [ + "lazy_static", + "memchr", + "regex-automata 0.1.10", +] + +[[package]] +name = "bstr" +version = "1.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "542f33a8835a0884b006a0c3df3dadd99c0c3f296ed26c2fdc8028e01ad6230c" +dependencies = [ + "memchr", + "serde", +] + +[[package]] +name = "bumpalo" +version = "3.14.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f30e7476521f6f8af1a1c4c0b8cc94f0bee37d91763d0ca2665f299b6cd8aec" + +[[package]] +name = "byte-slice-cast" +version = "1.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c3ac9f8b63eca6fd385229b3675f6cc0dc5c8a5c8a54a59d4f52ffd670d87b0c" + +[[package]] +name = "byte-tools" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3b5ca7a04898ad4bcd41c90c5285445ff5b791899bb1b0abdd2a2aa791211d7" + +[[package]] +name = "bytecount" +version = "0.6.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e1e5f035d16fc623ae5f74981db80a439803888314e3a555fd6f04acd51a3205" + +[[package]] +name = "byteorder" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1fd0f2584146f6f2ef48085050886acf353beff7305ebd1ae69500e27c67f64b" + +[[package]] +name = "bytes" +version = "0.4.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "206fdffcfa2df7cbe15601ef46c813fce0965eb3286db6b56c583b814b51c81c" +dependencies = [ + "byteorder", + "iovec", +] + +[[package]] +name = "bytes" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a2bd12c1caf447e69cd4528f47f94d203fd2582878ecb9e9465484c4148a8223" +dependencies = [ + "serde", +] + +[[package]] +name = "bytestring" +version = "1.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74d80203ea6b29df88012294f62733de21cfeab47f17b41af3a38bc30a03ee72" +dependencies = [ + "bytes 1.5.0", +] + +[[package]] +name = "bzip2" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bdb116a6ef3f6c3698828873ad02c3014b3c85cadb88496095628e3ef1e347f8" +dependencies = [ + "bzip2-sys", + "libc", +] + +[[package]] +name = "bzip2-sys" +version = "0.1.11+1.0.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "736a955f3fa7875102d57c82b8cac37ec45224a07fd32d58f9f7a186b6cd4cdc" +dependencies = [ + "cc", + "libc", + "pkg-config", +] + +[[package]] +name = "camino" +version = "1.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c59e92b5a388f549b863a7bea62612c09f24c8393560709a54558a9abdfb3b9c" +dependencies = [ + "serde", +] + +[[package]] +name = "cargo-platform" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e34637b3140142bdf929fb439e8aa4ebad7651ebf7b1080b3930aa16ac1459ff" +dependencies = [ + "serde", +] + +[[package]] +name = "cargo_metadata" +version = "0.14.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4acbb09d9ee8e23699b9634375c72795d095bf268439da88562cf9b501f181fa" +dependencies = [ + "camino", + "cargo-platform", + "semver", + "serde", + "serde_json", +] + +[[package]] +name = "cargo_metadata" +version = "0.18.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2d886547e41f740c616ae73108f6eb70afe6d940c7bc697cb30f13daec073037" +dependencies = [ + "camino", + "cargo-platform", + "semver", + "serde", + "serde_json", + "thiserror", +] + +[[package]] +name = "cc" +version = "1.0.83" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1174fb0b6ec23863f8b971027804a42614e347eafb0a95bf0b12cdae21fc4d0" +dependencies = [ + "jobserver", + "libc", +] + +[[package]] +name = "cexpr" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6fac387a98bb7c37292057cffc56d62ecb629900026402633ae9160df93a8766" +dependencies = [ + "nom", +] + +[[package]] +name = "cfg-if" +version = "0.1.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822" + +[[package]] +name = "cfg-if" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" + +[[package]] +name = "chacha20" +version = "0.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c3613f74bd2eac03dad61bd53dbe620703d4371614fe0bc3b9f04dd36fe4e818" +dependencies = [ + "cfg-if 1.0.0", + "cipher 0.4.4", + "cpufeatures", +] + +[[package]] +name = "chacha20poly1305" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "10cd79432192d1c0f4e1a0fef9527696cc039165d729fb41b3f4f4f354c2dc35" +dependencies = [ + "aead", + "chacha20", + "cipher 0.4.4", + "poly1305", + "zeroize", +] + +[[package]] +name = "chrono" +version = "0.4.31" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f2c685bad3eb3d45a01354cedb7d5faa66194d1d58ba6e267a8de788f79db38" +dependencies = [ + "android-tzdata", + "iana-time-zone", + "js-sys", + "num-traits", + "serde", + "wasm-bindgen", + "windows-targets 0.48.5", +] + +[[package]] +name = "cipher" +version = "0.2.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "12f8e7987cbd042a63249497f41aed09f8e65add917ea6566effbc56578d6801" +dependencies = [ + "generic-array 0.14.7", +] + +[[package]] +name = "cipher" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "773f3b9af64447d2ce9850330c473515014aa235e6a783b02db81ff39e4a3dad" +dependencies = [ + "crypto-common", + "inout", + "zeroize", +] + +[[package]] +name = "circuit_definitions" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-zkevm_test_harness.git?branch=v1.4.0#d2e3670e0c5115b7cc7cc24e6d3dbdd17a214aad" +dependencies = [ + "crossbeam 0.8.2", + "derivative", + "seq-macro", + "serde", + "snark_wrapper", + "zk_evm 1.4.0", + "zkevm_circuits", +] + +[[package]] +name = "circuit_testing" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-circuit_testing.git?branch=main#164c0adac85be39ee44bd9456b2b91cdede5af80" +dependencies = [ + "bellman_ce 0.3.2 (git+https://github.com/matter-labs/bellman?branch=dev)", +] + +[[package]] +name = "clang-sys" +version = "1.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c688fc74432808e3eb684cae8830a86be1d66a2bd58e1f248ed0960a590baf6f" +dependencies = [ + "glob", + "libc", + "libloading", +] + +[[package]] +name = "clap" +version = "2.34.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a0610544180c38b88101fecf2dd634b174a62eef6946f84dfc6a7127512b381c" +dependencies = [ + "ansi_term", + "atty", + "bitflags 1.3.2", + "strsim 0.8.0", + "textwrap", + "unicode-width", + "vec_map", +] + +[[package]] +name = "clap" +version = "4.4.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "41fffed7514f420abec6d183b1d3acfd9099c79c3a10a06ade4f8203f1411272" +dependencies = [ + "clap_builder", + "clap_derive", +] + +[[package]] +name = "clap_builder" +version = "4.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "63361bae7eef3771745f02d8d892bec2fee5f6e34af316ba556e7f97a7069ff1" +dependencies = [ + "anstream", + "anstyle", + "clap_lex", + "strsim 0.10.0", +] + +[[package]] +name = "clap_derive" +version = "4.4.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cf9804afaaf59a91e75b022a30fb7229a7901f60c755489cc61c9b423b836442" +dependencies = [ + "heck 0.4.1", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "clap_lex" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "702fc72eb24e5a1e48ce58027a675bc24edd52096d5397d4aea7c6dd9eca0bd1" + +[[package]] +name = "cloudabi" +version = "0.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ddfc5b9aa5d4507acaf872de71051dfd0e309860e88966e1051e462a077aac4f" +dependencies = [ + "bitflags 1.3.2", +] + +[[package]] +name = "codegen" +version = "0.1.0" +source = "git+https://github.com/matter-labs/solidity_plonk_verifier.git?branch=dev#82f96b7156551087f1c9bfe4f0ea68845b6debfc" +dependencies = [ + "ethereum-types 0.14.1", + "franklin-crypto 0.0.5 (git+https://github.com/matter-labs/franklin-crypto?branch=dev)", + "handlebars", + "hex", + "paste", + "rescue_poseidon 0.4.1 (git+https://github.com/matter-labs/rescue-poseidon)", + "serde", + "serde_derive", + "serde_json", +] + +[[package]] +name = "codegen" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ff61280aed771c3070e7dcc9e050c66f1eb1e3b96431ba66f9f74641d02fc41d" +dependencies = [ + "indexmap 1.9.3", +] + +[[package]] +name = "coins-bip32" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3b6be4a5df2098cd811f3194f64ddb96c267606bffd9689ac7b0160097b01ad3" +dependencies = [ + "bs58", + "coins-core", + "digest 0.10.7", + "hmac 0.12.1", + "k256 0.13.2", + "serde", + "sha2 0.10.8", + "thiserror", +] + +[[package]] +name = "coins-bip39" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3db8fba409ce3dc04f7d804074039eb68b960b0829161f8e06c95fea3f122528" +dependencies = [ + "bitvec 1.0.1", + "coins-bip32", + "hmac 0.12.1", + "once_cell", + "pbkdf2 0.12.2", + "rand 0.8.5", + "sha2 0.10.8", + "thiserror", +] + +[[package]] +name = "coins-core" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5286a0843c21f8367f7be734f89df9b822e0321d8bcce8d6e735aadff7d74979" +dependencies = [ + "base64 0.21.5", + "bech32", + "bs58", + "digest 0.10.7", + "generic-array 0.14.7", + "hex", + "ripemd", + "serde", + "serde_derive", + "sha2 0.10.8", + "sha3 0.10.8", + "thiserror", +] + +[[package]] +name = "colorchoice" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "acbf1af155f9b9ef647e42cdc158db4b64a1b61f743629225fde6f3e0be2a7c7" + +[[package]] +name = "colored" +version = "2.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2674ec482fbc38012cf31e6c42ba0177b431a0cb6f15fe40efa5aab1bda516f6" +dependencies = [ + "is-terminal", + "lazy_static", + "windows-sys 0.48.0", +] + +[[package]] +name = "combine" +version = "4.6.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "35ed6e9d84f0b51a7f52daf1c7d71dd136fd7a3f41a8462b8cdb8c78d920fad4" +dependencies = [ + "bytes 1.5.0", + "memchr", +] + +[[package]] +name = "const-hex" +version = "1.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a5104de16b218eddf8e34ffe2f86f74bfa4e61e95a1b89732fccf6325efd0557" +dependencies = [ + "cfg-if 1.0.0", + "cpufeatures", + "hex", + "proptest", + "serde", +] + +[[package]] +name = "const-oid" +version = "0.9.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "28c122c3980598d243d63d9a704629a2d748d101f278052ff068be5a4423ab6f" + +[[package]] +name = "const_format" +version = "0.2.32" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3a214c7af3d04997541b18d432afaff4c455e79e2029079647e72fc2bd27673" +dependencies = [ + "const_format_proc_macros", +] + +[[package]] +name = "const_format_proc_macros" +version = "0.2.32" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c7f6ff08fd20f4f299298a28e2dfa8a8ba1036e6cd2460ac1de7b425d76f2500" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "unicode-xid 0.2.4", +] + +[[package]] +name = "constant_time_eq" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "245097e9a4535ee1e3e3931fcfcd55a796a44c643e8596ff6566d68f09b87bbc" + +[[package]] +name = "convert_case" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6245d59a3e82a7fc217c5828a6692dbc6dfb63a0c8c90495621f7b9d79704a0e" + +[[package]] +name = "convert_case" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ec182b0ca2f35d8fc196cf3404988fd8b8c739a4d270ff118a398feb0cbec1ca" +dependencies = [ + "unicode-segmentation", +] + +[[package]] +name = "cookie" +version = "0.16.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e859cd57d0710d9e06c381b550c06e76992472a8c6d527aecd2fc673dcc231fb" +dependencies = [ + "percent-encoding", + "time", + "version_check", +] + +[[package]] +name = "core-foundation" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "194a7a9e6de53fa55116934067c844d9d749312f75c6f6d0980e8c252f8c2146" +dependencies = [ + "core-foundation-sys", + "libc", +] + +[[package]] +name = "core-foundation-sys" +version = "0.8.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e496a50fda8aacccc86d7529e2c1e0892dbd0f898a6b5645b5561b89c3210efa" + +[[package]] +name = "cpufeatures" +version = "0.2.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ce420fe07aecd3e67c5f910618fe65e94158f6dcc0adf44e00d69ce2bdfe0fd0" +dependencies = [ + "libc", +] + +[[package]] +name = "crc" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49fc9a695bca7f35f5f4c15cddc84415f66a74ea78eef08e90c5024f2b540e23" +dependencies = [ + "crc-catalog", +] + +[[package]] +name = "crc-catalog" +version = "1.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ccaeedb56da03b09f598226e25e80088cb4cd25f316e6e4df7d695f0feeb1403" + +[[package]] +name = "crc32fast" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b540bd8bc810d3885c6ea91e2018302f68baba2129ab3e88f32389ee9370880d" +dependencies = [ + "cfg-if 1.0.0", +] + +[[package]] +name = "crossbeam" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "69323bff1fb41c635347b8ead484a5ca6c3f11914d784170b158d8449ab07f8e" +dependencies = [ + "cfg-if 0.1.10", + "crossbeam-channel 0.4.4", + "crossbeam-deque 0.7.4", + "crossbeam-epoch 0.8.2", + "crossbeam-queue 0.2.3", + "crossbeam-utils 0.7.2", +] + +[[package]] +name = "crossbeam" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2801af0d36612ae591caa9568261fddce32ce6e08a7275ea334a06a4ad021a2c" +dependencies = [ + "cfg-if 1.0.0", + "crossbeam-channel 0.5.8", + "crossbeam-deque 0.8.3", + "crossbeam-epoch 0.9.15", + "crossbeam-queue 0.3.8", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "crossbeam-channel" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b153fe7cbef478c567df0f972e02e6d736db11affe43dfc9c56a9374d1adfb87" +dependencies = [ + "crossbeam-utils 0.7.2", + "maybe-uninit", +] + +[[package]] +name = "crossbeam-channel" +version = "0.5.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a33c2bf77f2df06183c3aa30d1e96c0695a313d4f9c453cc3762a6db39f99200" +dependencies = [ + "cfg-if 1.0.0", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "crossbeam-deque" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c20ff29ded3204c5106278a81a38f4b482636ed4fa1e6cfbeef193291beb29ed" +dependencies = [ + "crossbeam-epoch 0.8.2", + "crossbeam-utils 0.7.2", + "maybe-uninit", +] + +[[package]] +name = "crossbeam-deque" +version = "0.8.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ce6fd6f855243022dcecf8702fef0c297d4338e226845fe067f6341ad9fa0cef" +dependencies = [ + "cfg-if 1.0.0", + "crossbeam-epoch 0.9.15", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "crossbeam-epoch" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "058ed274caafc1f60c4997b5fc07bf7dc7cca454af7c6e81edffe5f33f70dace" +dependencies = [ + "autocfg 1.1.0", + "cfg-if 0.1.10", + "crossbeam-utils 0.7.2", + "lazy_static", + "maybe-uninit", + "memoffset 0.5.6", + "scopeguard", +] + +[[package]] +name = "crossbeam-epoch" +version = "0.9.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ae211234986c545741a7dc064309f67ee1e5ad243d0e48335adc0484d960bcc7" +dependencies = [ + "autocfg 1.1.0", + "cfg-if 1.0.0", + "crossbeam-utils 0.8.16", + "memoffset 0.9.0", + "scopeguard", +] + +[[package]] +name = "crossbeam-queue" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "774ba60a54c213d409d5353bda12d49cd68d14e45036a285234c8d6f91f92570" +dependencies = [ + "cfg-if 0.1.10", + "crossbeam-utils 0.7.2", + "maybe-uninit", +] + +[[package]] +name = "crossbeam-queue" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d1cfb3ea8a53f37c40dea2c7bedcbd88bdfae54f5e2175d6ecaff1c988353add" +dependencies = [ + "cfg-if 1.0.0", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "crossbeam-utils" +version = "0.7.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c3c7c73a2d1e9fc0886a08b93e98eb643461230d5f1925e4036204d5f2e261a8" +dependencies = [ + "autocfg 1.1.0", + "cfg-if 0.1.10", + "lazy_static", +] + +[[package]] +name = "crossbeam-utils" +version = "0.8.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a22b2d63d4d1dc0b7f1b6b2747dd0088008a9be28b6ddf0b1e7d335e3037294" +dependencies = [ + "cfg-if 1.0.0", +] + +[[package]] +name = "crunchy" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a81dae078cea95a014a339291cec439d2f232ebe854a9d672b796c6afafa9b7" + +[[package]] +name = "crypto-bigint" +version = "0.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ef2b4b23cddf68b89b8f8069890e8c270d54e2d5fe1b143820234805e4cb17ef" +dependencies = [ + "generic-array 0.14.7", + "rand_core 0.6.4", + "subtle", + "zeroize", +] + +[[package]] +name = "crypto-bigint" +version = "0.5.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0dc92fb57ca44df6db8059111ab3af99a63d5d0f8375d9972e319a379c6bab76" +dependencies = [ + "generic-array 0.14.7", + "rand_core 0.6.4", + "subtle", + "zeroize", +] + +[[package]] +name = "crypto-common" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1bfb12502f3fc46cca1bb51ac28df9d618d813cdc3d2f25b9fe775a34af26bb3" +dependencies = [ + "generic-array 0.14.7", + "rand_core 0.6.4", + "typenum", +] + +[[package]] +name = "crypto-mac" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b584a330336237c1eecd3e94266efb216c56ed91225d634cb2991c5f3fd1aeab" +dependencies = [ + "generic-array 0.14.7", + "subtle", +] + +[[package]] +name = "crypto-mac" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bff07008ec701e8028e2ceb8f83f0e4274ee62bd2dbdc4fefff2e9a91824081a" +dependencies = [ + "generic-array 0.14.7", + "subtle", +] + +[[package]] +name = "cs_derive" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-boojum.git?branch=main#1588de7669b016df3f81f7139a1a4b131840e48b" +dependencies = [ + "proc-macro-error", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "cs_derive" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-sync_vm.git?branch=v1.3.3#ed8ab8984cae05d00d9d62196753c8d40df47c7d" +dependencies = [ + "proc-macro-error", + "proc-macro2 1.0.70", + "quote 1.0.33", + "serde", + "syn 1.0.109", +] + +[[package]] +name = "ctr" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb4a30d54f7443bf3d6191dcd486aca19e67cb3c49fa7a06a319966346707e7f" +dependencies = [ + "cipher 0.2.5", +] + +[[package]] +name = "ctr" +version = "0.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0369ee1ad671834580515889b80f2ea915f23b8be8d0daa4bbaf2ac5c7590835" +dependencies = [ + "cipher 0.4.4", +] + +[[package]] +name = "ctrlc" +version = "3.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "82e95fbd621905b854affdc67943b043a0fbb6ed7385fd5a25650d19a8a6cfdf" +dependencies = [ + "nix", + "windows-sys 0.48.0", +] + +[[package]] +name = "curve25519-dalek" +version = "4.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e89b8c6a2e4b1f45971ad09761aafb85514a84744b67a95e32c3cc1352d1f65c" +dependencies = [ + "cfg-if 1.0.0", + "cpufeatures", + "curve25519-dalek-derive", + "digest 0.10.7", + "fiat-crypto", + "platforms", + "rustc_version", + "subtle", + "zeroize", +] + +[[package]] +name = "curve25519-dalek-derive" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f46882e17999c6cc590af592290432be3bce0428cb0d5f8b6715e4dc7b383eb3" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "darling" +version = "0.13.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a01d95850c592940db9b8194bc39f4bc0e89dee5c4265e4b1807c34a9aba453c" +dependencies = [ + "darling_core", + "darling_macro", +] + +[[package]] +name = "darling_core" +version = "0.13.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "859d65a907b6852c9361e3185c862aae7fafd2887876799fa55f5f99dc40d610" +dependencies = [ + "fnv", + "ident_case", + "proc-macro2 1.0.70", + "quote 1.0.33", + "strsim 0.10.0", + "syn 1.0.109", +] + +[[package]] +name = "darling_macro" +version = "0.13.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c972679f83bdf9c42bd905396b6c3588a843a17f0f16dfcfa3e2c5d57441835" +dependencies = [ + "darling_core", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "dashmap" +version = "5.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "978747c1d849a7d2ee5e8adc0159961c48fb7e5db2f06af6723b80123bb53856" +dependencies = [ + "cfg-if 1.0.0", + "hashbrown 0.14.3", + "lock_api", + "once_cell", + "parking_lot_core 0.9.9", +] + +[[package]] +name = "data-encoding" +version = "2.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7e962a19be5cfc3f3bf6dd8f61eb50107f356ad6270fbb3ed41476571db78be5" + +[[package]] +name = "debugid" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bef552e6f588e446098f6ba40d89ac146c8c7b64aade83c051ee00bb5d2bc18d" +dependencies = [ + "serde", + "uuid 1.6.1", +] + +[[package]] +name = "der" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1a467a65c5e759bce6e65eaf91cc29f466cdc57cb65777bd646872a8a1fd4de" +dependencies = [ + "const-oid", + "zeroize", +] + +[[package]] +name = "der" +version = "0.7.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fffa369a668c8af7dbf8b5e56c9f744fbd399949ed171606040001947de40b1c" +dependencies = [ + "const-oid", + "pem-rfc7468", + "zeroize", +] + +[[package]] +name = "deranged" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0f32d04922c60427da6f9fef14d042d9edddef64cb9d4ce0d64d0685fbeb1fd3" +dependencies = [ + "powerfmt", + "serde", +] + +[[package]] +name = "derivative" +version = "2.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fcc3dd5e9e9c0b295d6e1e4d811fb6f157d5ffd784b8d202fc62eac8035a770b" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "derive_more" +version = "0.99.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4fb810d30a7c1953f91334de7244731fc3f3c10d7fe163338a35b9f640960321" +dependencies = [ + "convert_case 0.4.0", + "proc-macro2 1.0.70", + "quote 1.0.33", + "rustc_version", + "syn 1.0.109", +] + +[[package]] +name = "diff" +version = "0.1.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "56254986775e3233ffa9c4d7d3faaf6d36a2c09d30b20687e9f88bc8bafc16c8" + +[[package]] +name = "digest" +version = "0.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f3d0c8c8752312f9713efd397ff63acb9f85585afbf179282e720e7704954dd5" +dependencies = [ + "generic-array 0.12.4", +] + +[[package]] +name = "digest" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3dd60d1080a57a05ab032377049e0591415d2b31afd7028356dbf3cc6dcb066" +dependencies = [ + "generic-array 0.14.7", +] + +[[package]] +name = "digest" +version = "0.10.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9ed9a281f7bc9b7576e61468ba615a66a5c8cfdff42420a70aa82701a3b1e292" +dependencies = [ + "block-buffer 0.10.4", + "const-oid", + "crypto-common", + "subtle", +] + +[[package]] +name = "dirs" +version = "4.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ca3aa72a6f96ea37bbc5aa912f6788242832f75369bdfdadcb0e38423f100059" +dependencies = [ + "dirs-sys 0.3.7", +] + +[[package]] +name = "dirs" +version = "5.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "44c45a9d03d6676652bcb5e724c7e988de1acad23a711b5217ab9cbecbec2225" +dependencies = [ + "dirs-sys 0.4.1", +] + +[[package]] +name = "dirs-next" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b98cf8ebf19c3d1b223e151f99a4f9f0690dca41414773390fc824184ac833e1" +dependencies = [ + "cfg-if 1.0.0", + "dirs-sys-next", +] + +[[package]] +name = "dirs-sys" +version = "0.3.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1b1d1d91c932ef41c0f2663aa8b0ca0342d444d842c06914aa0a7e352d0bada6" +dependencies = [ + "libc", + "redox_users", + "winapi 0.3.9", +] + +[[package]] +name = "dirs-sys" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "520f05a5cbd335fae5a99ff7a6ab8627577660ee5cfd6a94a6a929b52ff0321c" +dependencies = [ + "libc", + "option-ext", + "redox_users", + "windows-sys 0.48.0", +] + +[[package]] +name = "dirs-sys-next" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4ebda144c4fe02d1f7ea1a7d9641b6fc6b580adcfa024ae48797ecdeb6825b4d" +dependencies = [ + "libc", + "redox_users", + "winapi 0.3.9", +] + +[[package]] +name = "dotenv" +version = "0.15.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77c90badedccf4105eca100756a0b1289e191f6fcbdadd3cee1d2f614f97da8f" + +[[package]] +name = "dtoa" +version = "1.0.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dcbb2bf8e87535c23f7a8a321e364ce21462d0ff10cb6407820e8e96dfff6653" + +[[package]] +name = "dunce" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "56ce8c6da7551ec6c462cbaf3bfbc75131ebbfa1c944aeaa9dab51ca1c5f0c3b" + +[[package]] +name = "ecdsa" +version = "0.14.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "413301934810f597c1d19ca71c8710e99a3f1ba28a0d2ebc01551a2daeea3c5c" +dependencies = [ + "der 0.6.1", + "elliptic-curve 0.12.3", + "rfc6979 0.3.1", + "signature 1.6.4", +] + +[[package]] +name = "ecdsa" +version = "0.16.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ee27f32b5c5292967d2d4a9d7f1e0b0aed2c15daded5a60300e4abb9d8020bca" +dependencies = [ + "der 0.7.8", + "digest 0.10.7", + "elliptic-curve 0.13.8", + "rfc6979 0.4.0", + "signature 2.2.0", + "spki 0.7.3", +] + +[[package]] +name = "ed25519" +version = "2.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "115531babc129696a58c64a4fef0a8bf9e9698629fb97e9e40767d235cfbcd53" +dependencies = [ + "pkcs8 0.10.2", + "signature 2.2.0", +] + +[[package]] +name = "ed25519-dalek" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f628eaec48bfd21b865dc2950cfa014450c01d2fa2b69a86c2fd5844ec523c0" +dependencies = [ + "curve25519-dalek", + "ed25519", + "rand_core 0.6.4", + "serde", + "sha2 0.10.8", + "subtle", + "zeroize", +] + +[[package]] +name = "either" +version = "1.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a26ae43d7bcc3b814de94796a5e736d4029efb0ee900c12e2d54c993ad1a1e07" +dependencies = [ + "serde", +] + +[[package]] +name = "elliptic-curve" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e7bb888ab5300a19b8e5bceef25ac745ad065f3c9f7efc6de1b91958110891d3" +dependencies = [ + "base16ct 0.1.1", + "crypto-bigint 0.4.9", + "der 0.6.1", + "digest 0.10.7", + "ff 0.12.1", + "generic-array 0.14.7", + "group 0.12.1", + "pkcs8 0.9.0", + "rand_core 0.6.4", + "sec1 0.3.0", + "subtle", + "zeroize", +] + +[[package]] +name = "elliptic-curve" +version = "0.13.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b5e6043086bf7973472e0c7dff2142ea0b680d30e18d9cc40f267efbf222bd47" +dependencies = [ + "base16ct 0.2.0", + "crypto-bigint 0.5.5", + "digest 0.10.7", + "ff 0.13.0", + "generic-array 0.14.7", + "group 0.13.0", + "pkcs8 0.10.2", + "rand_core 0.6.4", + "sec1 0.7.3", + "subtle", + "zeroize", +] + +[[package]] +name = "elsa" +version = "1.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "714f766f3556b44e7e4776ad133fcc3445a489517c25c704ace411bb14790194" +dependencies = [ + "stable_deref_trait", +] + +[[package]] +name = "ena" +version = "0.14.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c533630cf40e9caa44bd91aadc88a75d75a4c3a12b4cfde353cbed41daa1e1f1" +dependencies = [ + "log", +] + +[[package]] +name = "encoding_rs" +version = "0.8.33" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7268b386296a025e474d5140678f75d6de9493ae55a5d709eeb9dd08149945e1" +dependencies = [ + "cfg-if 1.0.0", +] + +[[package]] +name = "enr" +version = "0.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fe81b5c06ecfdbc71dd845216f225f53b62a10cb8a16c946836a3467f701d05b" +dependencies = [ + "base64 0.21.5", + "bytes 1.5.0", + "hex", + "k256 0.13.2", + "log", + "rand 0.8.5", + "rlp", + "serde", + "sha3 0.10.8", + "zeroize", +] + +[[package]] +name = "env_logger" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a12e6657c4c97ebab115a42dcee77225f7f482cdd841cf7088c657a42e9e00e7" +dependencies = [ + "atty", + "humantime", + "log", + "regex", + "termcolor", +] + +[[package]] +name = "env_logger" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "95b3f3e67048839cb0d0781f445682a35113da7121f7c949db0e2be96a4fbece" +dependencies = [ + "humantime", + "is-terminal", + "log", + "regex", + "termcolor", +] + +[[package]] +name = "envy" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f47e0157f2cb54f5ae1bd371b30a2ae4311e1c028f575cd4e81de7353215965" +dependencies = [ + "serde", +] + +[[package]] +name = "equivalent" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5" + +[[package]] +name = "era_test_node" +version = "0.1.0-alpha.14" +dependencies = [ + "anyhow", + "bigdecimal", + "chrono", + "clap 4.4.10", + "colored", + "ethabi 16.0.0", + "ethers", + "eyre", + "futures 0.3.29", + "hex", + "httptest", + "indexmap 2.1.0", + "itertools 0.10.5", + "jsonrpc-core 18.0.0 (git+https://github.com/matter-labs/jsonrpc.git?branch=master)", + "jsonrpc-core-client", + "jsonrpc-derive", + "jsonrpc-http-server", + "lazy_static", + "maplit", + "multivm", + "once_cell", + "openssl-sys", + "reqwest", + "rustc-hash", + "serde", + "serde_json", + "sha3 0.10.8", + "tempdir", + "time", + "tokio", + "tracing", + "tracing-subscriber", + "zksync-web3-rs", + "zksync_basic_types", + "zksync_contracts", + "zksync_core", + "zksync_state", + "zksync_types", + "zksync_utils", + "zksync_web3_decl", +] + +[[package]] +name = "errno" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a258e46cdc063eb8519c00b9fc845fc47bcfca4130e2f08e88665ceda8474245" +dependencies = [ + "libc", + "windows-sys 0.52.0", +] + +[[package]] +name = "error-chain" +version = "0.12.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2d2f06b9cac1506ece98fe3231e3cc9c4410ec3d5b1f24ae1c8946f0742cdefc" +dependencies = [ + "version_check", +] + +[[package]] +name = "eth-keystore" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1fda3bf123be441da5260717e0661c25a2fd9cb2b2c1d20bf2e05580047158ab" +dependencies = [ + "aes 0.8.3", + "ctr 0.9.2", + "digest 0.10.7", + "hex", + "hmac 0.12.1", + "pbkdf2 0.11.0", + "rand 0.8.5", + "scrypt 0.10.0", + "serde", + "serde_json", + "sha2 0.10.8", + "sha3 0.10.8", + "thiserror", + "uuid 0.8.2", +] + +[[package]] +name = "ethabi" +version = "16.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a4c98847055d934070b90e806e12d3936b787d0a115068981c1d8dfd5dfef5a5" +dependencies = [ + "ethereum-types 0.12.1", + "hex", + "serde", + "serde_json", + "sha3 0.9.1", + "thiserror", + "uint", +] + +[[package]] +name = "ethabi" +version = "18.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7413c5f74cc903ea37386a8965a936cbeb334bd270862fdece542c1b2dcbc898" +dependencies = [ + "ethereum-types 0.14.1", + "hex", + "once_cell", + "regex", + "serde", + "serde_json", + "sha3 0.10.8", + "thiserror", + "uint", +] + +[[package]] +name = "ethbloom" +version = "0.11.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfb684ac8fa8f6c5759f788862bb22ec6fe3cb392f6bfd08e3c64b603661e3f8" +dependencies = [ + "crunchy", + "fixed-hash 0.7.0", + "impl-rlp", + "impl-serde 0.3.2", + "tiny-keccak 2.0.2", +] + +[[package]] +name = "ethbloom" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c22d4b5885b6aa2fe5e8b9329fb8d232bf739e434e6b87347c63bdd00c120f60" +dependencies = [ + "crunchy", + "fixed-hash 0.8.0", + "impl-codec 0.6.0", + "impl-rlp", + "impl-serde 0.4.0", + "scale-info", + "tiny-keccak 2.0.2", +] + +[[package]] +name = "ethereum-types" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "05136f7057fe789f06e6d41d07b34e6f70d8c86e5693b60f97aaa6553553bdaf" +dependencies = [ + "ethbloom 0.11.1", + "fixed-hash 0.7.0", + "impl-rlp", + "impl-serde 0.3.2", + "primitive-types 0.10.1", + "uint", +] + +[[package]] +name = "ethereum-types" +version = "0.14.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "02d215cbf040552efcbe99a38372fe80ab9d00268e20012b79fcd0f073edd8ee" +dependencies = [ + "ethbloom 0.13.0", + "fixed-hash 0.8.0", + "impl-codec 0.6.0", + "impl-rlp", + "impl-serde 0.4.0", + "primitive-types 0.12.2", + "scale-info", + "uint", +] + +[[package]] +name = "ethers" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a5344eea9b20effb5efeaad29418215c4d27017639fd1f908260f59cbbd226e" +dependencies = [ + "ethers-addressbook", + "ethers-contract", + "ethers-core", + "ethers-etherscan", + "ethers-middleware", + "ethers-providers", + "ethers-signers", + "ethers-solc", +] + +[[package]] +name = "ethers-addressbook" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8c405f24ea3a517899ba7985385c43dc4a7eb1209af3b1e0a1a32d7dcc7f8d09" +dependencies = [ + "ethers-core", + "once_cell", + "serde", + "serde_json", +] + +[[package]] +name = "ethers-contract" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0111ead599d17a7bff6985fd5756f39ca7033edc79a31b23026a8d5d64fa95cd" +dependencies = [ + "const-hex", + "ethers-contract-abigen", + "ethers-contract-derive", + "ethers-core", + "ethers-providers", + "futures-util", + "once_cell", + "pin-project", + "serde", + "serde_json", + "thiserror", +] + +[[package]] +name = "ethers-contract-abigen" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "51258120c6b47ea9d9bec0d90f9e8af71c977fbefbef8213c91bfed385fe45eb" +dependencies = [ + "Inflector", + "const-hex", + "dunce", + "ethers-core", + "ethers-etherscan", + "eyre", + "prettyplease", + "proc-macro2 1.0.70", + "quote 1.0.33", + "regex", + "reqwest", + "serde", + "serde_json", + "syn 2.0.39", + "toml 0.8.8", + "walkdir", +] + +[[package]] +name = "ethers-contract-derive" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "936e7a0f1197cee2b62dc89f63eff3201dbf87c283ff7e18d86d38f83b845483" +dependencies = [ + "Inflector", + "const-hex", + "ethers-contract-abigen", + "ethers-core", + "proc-macro2 1.0.70", + "quote 1.0.33", + "serde_json", + "syn 2.0.39", +] + +[[package]] +name = "ethers-core" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2f03e0bdc216eeb9e355b90cf610ef6c5bb8aca631f97b5ae9980ce34ea7878d" +dependencies = [ + "arrayvec 0.7.4", + "bytes 1.5.0", + "cargo_metadata 0.18.1", + "chrono", + "const-hex", + "elliptic-curve 0.13.8", + "ethabi 18.0.0", + "generic-array 0.14.7", + "k256 0.13.2", + "num_enum 0.7.1", + "once_cell", + "open-fastrlp", + "rand 0.8.5", + "rlp", + "serde", + "serde_json", + "strum 0.25.0", + "syn 2.0.39", + "tempfile", + "thiserror", + "tiny-keccak 2.0.2", + "unicode-xid 0.2.4", +] + +[[package]] +name = "ethers-etherscan" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "abbac2c890bdbe0f1b8e549a53b00e2c4c1de86bb077c1094d1f38cdf9381a56" +dependencies = [ + "chrono", + "ethers-core", + "reqwest", + "semver", + "serde", + "serde_json", + "thiserror", + "tracing", +] + +[[package]] +name = "ethers-middleware" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "681ece6eb1d10f7cf4f873059a77c04ff1de4f35c63dd7bccde8f438374fcb93" +dependencies = [ + "async-trait", + "auto_impl", + "ethers-contract", + "ethers-core", + "ethers-etherscan", + "ethers-providers", + "ethers-signers", + "futures-channel", + "futures-locks", + "futures-util", + "instant", + "reqwest", + "serde", + "serde_json", + "thiserror", + "tokio", + "tracing", + "tracing-futures", + "url", +] + +[[package]] +name = "ethers-providers" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "25d6c0c9455d93d4990c06e049abf9b30daf148cf461ee939c11d88907c60816" +dependencies = [ + "async-trait", + "auto_impl", + "base64 0.21.5", + "bytes 1.5.0", + "const-hex", + "enr", + "ethers-core", + "futures-core", + "futures-timer", + "futures-util", + "hashers", + "http", + "instant", + "jsonwebtoken", + "once_cell", + "pin-project", + "reqwest", + "serde", + "serde_json", + "thiserror", + "tokio", + "tokio-tungstenite", + "tracing", + "tracing-futures", + "url", + "wasm-bindgen", + "wasm-bindgen-futures", + "web-sys", + "ws_stream_wasm", +] + +[[package]] +name = "ethers-signers" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0cb1b714e227bbd2d8c53528adb580b203009728b17d0d0e4119353aa9bc5532" +dependencies = [ + "async-trait", + "coins-bip32", + "coins-bip39", + "const-hex", + "elliptic-curve 0.13.8", + "eth-keystore", + "ethers-core", + "rand 0.8.5", + "sha2 0.10.8", + "thiserror", + "tracing", +] + +[[package]] +name = "ethers-solc" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a64f710586d147864cff66540a6d64518b9ff37d73ef827fee430538265b595f" +dependencies = [ + "cfg-if 1.0.0", + "const-hex", + "dirs 5.0.1", + "dunce", + "ethers-core", + "glob", + "home", + "md-5", + "num_cpus", + "once_cell", + "path-slash", + "rayon", + "regex", + "semver", + "serde", + "serde_json", + "solang-parser", + "svm-rs", + "thiserror", + "tiny-keccak 2.0.2", + "tokio", + "tracing", + "walkdir", + "yansi", +] + +[[package]] +name = "event-listener" +version = "2.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0206175f82b8d6bf6652ff7d71a1e27fd2e4efde587fd368662814d6ec1d9ce0" + +[[package]] +name = "eyre" +version = "0.6.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "80f656be11ddf91bd709454d15d5bd896fbaf4cc3314e69349e4d1569f5b46cd" +dependencies = [ + "indenter", + "once_cell", +] + +[[package]] +name = "fake-simd" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e88a8acf291dafb59c2d96e8f59828f3838bb1a70398823ade51a84de6a6deed" + +[[package]] +name = "fastrand" +version = "1.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e51093e27b0797c359783294ca4f0a911c270184cb10f85783b118614a1501be" +dependencies = [ + "instant", +] + +[[package]] +name = "fastrand" +version = "2.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "25cbce373ec4653f1a01a31e8a5e5ec0c622dc27ff9c4e6606eefef5cbbed4a5" + +[[package]] +name = "ff" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d013fc25338cc558c5c2cfbad646908fb23591e2404481826742b651c9af7160" +dependencies = [ + "rand_core 0.6.4", + "subtle", +] + +[[package]] +name = "ff" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ded41244b729663b1e574f1b4fb731469f69f79c17667b5d776b16cda0479449" +dependencies = [ + "rand_core 0.6.4", + "subtle", +] + +[[package]] +name = "ff_ce" +version = "0.14.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b538e4231443a5b9c507caee3356f016d832cf7393d2d90f03ea3180d4e3fbc" +dependencies = [ + "byteorder", + "ff_derive_ce", + "hex", + "rand 0.4.6", + "serde", +] + +[[package]] +name = "ff_derive_ce" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b96fbccd88dbb1fac4ee4a07c2fcc4ca719a74ffbd9d2b9d41d8c8eb073d8b20" +dependencies = [ + "num-bigint 0.4.4", + "num-integer", + "num-traits", + "proc-macro2 1.0.70", + "quote 1.0.33", + "serde", + "syn 1.0.109", +] + +[[package]] +name = "fiat-crypto" +version = "0.2.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "27573eac26f4dd11e2b1916c3fe1baa56407c83c71a773a8ba17ec0bca03b6b7" + +[[package]] +name = "findshlibs" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "40b9e59cd0f7e0806cca4be089683ecb6434e602038df21fe6bf6711b2f07f64" +dependencies = [ + "cc", + "lazy_static", + "libc", + "winapi 0.3.9", +] + +[[package]] +name = "finl_unicode" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8fcfdc7a0362c9f4444381a9e697c79d435fe65b52a37466fc2c1184cee9edc6" + +[[package]] +name = "firestorm" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2c5f6c2c942da57e2aaaa84b8a521489486f14e75e7fa91dab70aba913975f98" + +[[package]] +name = "fixed-hash" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cfcf0ed7fe52a17a03854ec54a9f76d6d84508d1c0e66bc1793301c73fc8493c" +dependencies = [ + "byteorder", + "rand 0.8.5", + "rustc-hex", + "static_assertions", +] + +[[package]] +name = "fixed-hash" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "835c052cb0c08c1acf6ffd71c022172e18723949c8282f2b9f27efbc51e64534" +dependencies = [ + "byteorder", + "rand 0.8.5", + "rustc-hex", + "static_assertions", +] + +[[package]] +name = "fixedbitset" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0ce7134b9999ecaf8bcd65542e436736ef32ddca1b3e06094cb6ec5755203b80" + +[[package]] +name = "flate2" +version = "1.0.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "46303f565772937ffe1d394a4fac6f411c6013172fadde9dcdb1e147a086940e" +dependencies = [ + "crc32fast", + "miniz_oxide", +] + +[[package]] +name = "fnv" +version = "1.0.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1" + +[[package]] +name = "foreign-types" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f6f339eb8adc052cd2ca78910fda869aefa38d22d5cb648e6485e4d3fc06f3b1" +dependencies = [ + "foreign-types-shared", +] + +[[package]] +name = "foreign-types-shared" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b" + +[[package]] +name = "form_urlencoded" +version = "1.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e13624c2627564efccf4934284bdd98cbaa14e79b0b5a141218e507b3a823456" +dependencies = [ + "percent-encoding", +] + +[[package]] +name = "franklin-crypto" +version = "0.0.5" +source = "git+https://github.com/matter-labs/franklin-crypto?branch=dev#5695d07c7bc604c2c39a27712ffac171d39ee1ed" +dependencies = [ + "arr_macro", + "bellman_ce 0.3.2 (git+https://github.com/matter-labs/bellman?branch=dev)", + "bit-vec", + "blake2 0.9.2", + "blake2-rfc_bellman_edition", + "blake2s_simd", + "byteorder", + "digest 0.9.0", + "hex", + "indexmap 1.9.3", + "itertools 0.10.5", + "lazy_static", + "num-bigint 0.4.4", + "num-derive 0.2.5", + "num-integer", + "num-traits", + "rand 0.4.6", + "serde", + "sha2 0.9.9", + "sha3 0.9.1", + "smallvec", + "splitmut", + "tiny-keccak 1.5.0", +] + +[[package]] +name = "franklin-crypto" +version = "0.0.5" +source = "git+https://github.com/matter-labs/franklin-crypto?branch=snark_wrapper#a9e29acd73245bd3b670b62b4d481ece06d43803" +dependencies = [ + "arr_macro", + "bellman_ce 0.3.2 (git+https://github.com/matter-labs/bellman?branch=snark-wrapper)", + "bit-vec", + "blake2 0.9.2", + "blake2-rfc_bellman_edition", + "blake2s_simd", + "boojum", + "byteorder", + "derivative", + "digest 0.9.0", + "hex", + "indexmap 1.9.3", + "itertools 0.10.5", + "lazy_static", + "num-bigint 0.4.4", + "num-derive 0.2.5", + "num-integer", + "num-traits", + "rand 0.4.6", + "serde", + "sha2 0.9.9", + "sha3 0.9.1", + "smallvec", + "splitmut", + "tiny-keccak 1.5.0", +] + +[[package]] +name = "fs2" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9564fc758e15025b46aa6643b1b77d047d1a56a1aea6e01002ac0c7026876213" +dependencies = [ + "libc", + "winapi 0.3.9", +] + +[[package]] +name = "fuchsia-cprng" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a06f77d526c1a601b7c4cdd98f54b5eaabffc14d5f2f0296febdc7f357c6d3ba" + +[[package]] +name = "fuchsia-zircon" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82" +dependencies = [ + "bitflags 1.3.2", + "fuchsia-zircon-sys", +] + +[[package]] +name = "fuchsia-zircon-sys" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7" + +[[package]] +name = "funty" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fed34cd105917e91daa4da6b3728c47b068749d6a62c59811f06ed2ac71d9da7" + +[[package]] +name = "funty" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e6d5a32815ae3f33302d95fdcb2ce17862f8c65363dcfd29360480ba1001fc9c" + +[[package]] +name = "futures" +version = "0.1.31" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3a471a38ef8ed83cd6e40aa59c1ffe17db6855c18e3604d9c4ed8c08ebc28678" + +[[package]] +name = "futures" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "da0290714b38af9b4a7b094b8a37086d1b4e61f2df9122c3cad2577669145335" +dependencies = [ + "futures-channel", + "futures-core", + "futures-executor", + "futures-io", + "futures-sink", + "futures-task", + "futures-util", +] + +[[package]] +name = "futures-channel" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ff4dd66668b557604244583e3e1e1eada8c5c2e96a6d0d6653ede395b78bbacb" +dependencies = [ + "futures-core", + "futures-sink", +] + +[[package]] +name = "futures-core" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eb1d22c66e66d9d72e1758f0bd7d4fd0bee04cad842ee34587d68c07e45d088c" + +[[package]] +name = "futures-executor" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0f4fb8693db0cf099eadcca0efe2a5a22e4550f98ed16aba6c48700da29597bc" +dependencies = [ + "futures-core", + "futures-task", + "futures-util", + "num_cpus", +] + +[[package]] +name = "futures-intrusive" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a604f7a68fbf8103337523b1fadc8ade7361ee3f112f7c680ad179651616aed5" +dependencies = [ + "futures-core", + "lock_api", + "parking_lot 0.11.2", +] + +[[package]] +name = "futures-io" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8bf34a163b5c4c52d0478a4d757da8fb65cabef42ba90515efee0f6f9fa45aaa" + +[[package]] +name = "futures-locks" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "45ec6fe3675af967e67c5536c0b9d44e34e6c52f86bedc4ea49c5317b8e94d06" +dependencies = [ + "futures-channel", + "futures-task", +] + +[[package]] +name = "futures-macro" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "53b153fd91e4b0147f4aced87be237c98248656bb01050b96bf3ee89220a8ddb" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "futures-sink" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e36d3378ee38c2a36ad710c5d30c2911d752cb941c00c72dbabfb786a7970817" + +[[package]] +name = "futures-task" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "efd193069b0ddadc69c46389b740bbccdd97203899b48d09c5f7969591d6bae2" + +[[package]] +name = "futures-timer" +version = "3.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e64b03909df88034c26dc1547e8970b91f98bdb65165d6a4e9110d94263dbb2c" +dependencies = [ + "gloo-timers", + "send_wrapper 0.4.0", +] + +[[package]] +name = "futures-util" +version = "0.3.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a19526d624e703a3179b3d322efec918b6246ea0fa51d41124525f00f1cc8104" +dependencies = [ + "futures 0.1.31", + "futures-channel", + "futures-core", + "futures-io", + "futures-macro", + "futures-sink", + "futures-task", + "memchr", + "pin-project-lite", + "pin-utils", + "slab", +] + +[[package]] +name = "fxhash" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c31b6d751ae2c7f11320402d34e41349dd1016f8d5d45e48c4312bc8625af50c" +dependencies = [ + "byteorder", +] + +[[package]] +name = "generic-array" +version = "0.12.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ffdf9f34f1447443d37393cc6c2b8313aebddcd96906caf34e54c68d8e57d7bd" +dependencies = [ + "typenum", +] + +[[package]] +name = "generic-array" +version = "0.14.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "85649ca51fd72272d7821adaf274ad91c288277713d9c18820d8499a7ff69e9a" +dependencies = [ + "typenum", + "version_check", + "zeroize", +] + +[[package]] +name = "getrandom" +version = "0.1.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8fc3cb4d91f53b50155bdcfd23f6a4c39ae1969c2ae85982b135750cccaf5fce" +dependencies = [ + "cfg-if 1.0.0", + "libc", + "wasi 0.9.0+wasi-snapshot-preview1", +] + +[[package]] +name = "getrandom" +version = "0.2.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fe9006bed769170c11f845cf00c7c1e9092aeb3f268e007c3e760ac68008070f" +dependencies = [ + "cfg-if 1.0.0", + "libc", + "wasi 0.11.0+wasi-snapshot-preview1", +] + +[[package]] +name = "ghash" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d930750de5717d2dd0b8c0d42c076c0e884c81a73e6cab859bbd2339c71e3e40" +dependencies = [ + "opaque-debug 0.3.0", + "polyval", +] + +[[package]] +name = "gimli" +version = "0.28.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4271d37baee1b8c7e4b708028c57d816cf9d2434acb33a549475f78c181f6253" + +[[package]] +name = "glob" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d2fabcfbdc87f4758337ca535fb41a6d701b65693ce38287d856d1674551ec9b" + +[[package]] +name = "globset" +version = "0.4.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "57da3b9b5b85bd66f31093f8c408b90a74431672542466497dcbdfdc02034be1" +dependencies = [ + "aho-corasick", + "bstr 1.8.0", + "log", + "regex-automata 0.4.3", + "regex-syntax 0.8.2", +] + +[[package]] +name = "gloo-net" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a66b4e3c7d9ed8d315fd6b97c8b1f74a7c6ecbbc2320e65ae7ed38b7068cc620" +dependencies = [ + "futures-channel", + "futures-core", + "futures-sink", + "gloo-utils", + "http", + "js-sys", + "pin-project", + "serde", + "serde_json", + "thiserror", + "wasm-bindgen", + "wasm-bindgen-futures", + "web-sys", +] + +[[package]] +name = "gloo-timers" +version = "0.2.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9b995a66bb87bebce9a0f4a95aed01daca4872c050bfcb21653361c03bc35e5c" +dependencies = [ + "futures-channel", + "futures-core", + "js-sys", + "wasm-bindgen", +] + +[[package]] +name = "gloo-utils" +version = "0.1.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "037fcb07216cb3a30f7292bd0176b050b7b9a052ba830ef7d5d65f6dc64ba58e" +dependencies = [ + "js-sys", + "serde", + "serde_json", + "wasm-bindgen", + "web-sys", +] + +[[package]] +name = "google-cloud-auth" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "af1087f1fbd2dd3f58c17c7574ddd99cd61cbbbc2c4dc81114b8687209b196cb" +dependencies = [ + "async-trait", + "base64 0.21.5", + "google-cloud-metadata", + "google-cloud-token", + "home", + "jsonwebtoken", + "reqwest", + "serde", + "serde_json", + "thiserror", + "time", + "tokio", + "tracing", + "urlencoding", +] + +[[package]] +name = "google-cloud-metadata" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cc279bfb50487d7bcd900e8688406475fc750fe474a835b2ab9ade9eb1fc90e2" +dependencies = [ + "reqwest", + "thiserror", + "tokio", +] + +[[package]] +name = "google-cloud-storage" +version = "0.15.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac04b29849ebdeb9fb008988cc1c4d1f0c9d121b4c7f1ddeb8061df124580e93" +dependencies = [ + "async-stream", + "async-trait", + "base64 0.21.5", + "bytes 1.5.0", + "futures-util", + "google-cloud-auth", + "google-cloud-metadata", + "google-cloud-token", + "hex", + "once_cell", + "percent-encoding", + "pkcs8 0.10.2", + "regex", + "reqwest", + "ring 0.17.6", + "serde", + "serde_json", + "sha2 0.10.8", + "thiserror", + "time", + "tokio", + "tracing", + "url", +] + +[[package]] +name = "google-cloud-token" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f49c12ba8b21d128a2ce8585955246977fbce4415f680ebf9199b6f9d6d725f" +dependencies = [ + "async-trait", +] + +[[package]] +name = "governor" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "19775995ee20209163239355bc3ad2f33f83da35d9ef72dea26e5af753552c87" +dependencies = [ + "dashmap", + "futures 0.3.29", + "futures-timer", + "no-std-compat", + "nonzero_ext", + "parking_lot 0.12.1", + "quanta 0.9.3", + "rand 0.8.5", + "smallvec", +] + +[[package]] +name = "group" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5dfbfb3a6cfbd390d5c9564ab283a0349b9b9fcd46a706c1eb10e0db70bfbac7" +dependencies = [ + "ff 0.12.1", + "rand_core 0.6.4", + "subtle", +] + +[[package]] +name = "group" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f0f9ef7462f7c099f518d754361858f86d8a07af53ba9af0fe635bbccb151a63" +dependencies = [ + "ff 0.13.0", + "rand_core 0.6.4", + "subtle", +] + +[[package]] +name = "h2" +version = "0.3.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4d6250322ef6e60f93f9a2162799302cd6f68f79f6e5d85c8c16f14d1d958178" +dependencies = [ + "bytes 1.5.0", + "fnv", + "futures-core", + "futures-sink", + "futures-util", + "http", + "indexmap 2.1.0", + "slab", + "tokio", + "tokio-util 0.7.10", + "tracing", +] + +[[package]] +name = "handlebars" +version = "4.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "faa67bab9ff362228eb3d00bd024a4965d8231bbb7921167f0cfa66c6626b225" +dependencies = [ + "log", + "pest", + "pest_derive", + "serde", + "serde_json", + "thiserror", +] + +[[package]] +name = "hashbrown" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ab5ef0d4909ef3724cc8cce6ccc8572c5c817592e9285f5464f8e86f8bd3726e" +dependencies = [ + "ahash 0.7.7", +] + +[[package]] +name = "hashbrown" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" + +[[package]] +name = "hashbrown" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "33ff8ae62cd3a9102e5637afc8452c55acf3844001bd5374e0b0bd7b6616c038" +dependencies = [ + "ahash 0.8.6", +] + +[[package]] +name = "hashbrown" +version = "0.14.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "290f1a1d9242c78d09ce40a5e87e7554ee637af1351968159f4952f028f75604" + +[[package]] +name = "hashers" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b2bca93b15ea5a746f220e56587f71e73c6165eab783df9e26590069953e3c30" +dependencies = [ + "fxhash", +] + +[[package]] +name = "hashlink" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7249a3129cbc1ffccd74857f81464a323a152173cdb134e0fd81bc803b29facf" +dependencies = [ + "hashbrown 0.11.2", +] + +[[package]] +name = "hdrhistogram" +version = "7.5.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "765c9198f173dd59ce26ff9f95ef0aafd0a0fe01fb9d72841bc5066a4c06511d" +dependencies = [ + "byteorder", + "num-traits", +] + +[[package]] +name = "headers" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "06683b93020a07e3dbcf5f8c0f6d40080d725bea7936fc01ad345c01b97dc270" +dependencies = [ + "base64 0.21.5", + "bytes 1.5.0", + "headers-core", + "http", + "httpdate", + "mime", + "sha1", +] + +[[package]] +name = "headers-core" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e7f66481bfee273957b1f20485a4ff3362987f85b2c236580d81b4eb7a326429" +dependencies = [ + "http", +] + +[[package]] +name = "heck" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6d621efb26863f0e9924c6ac577e8275e5e6b77455db64ffa6c65c904e9e132c" +dependencies = [ + "unicode-segmentation", +] + +[[package]] +name = "heck" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8" +dependencies = [ + "unicode-segmentation", +] + +[[package]] +name = "hermit-abi" +version = "0.1.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62b467343b94ba476dcb2500d242dadbb39557df889310ac77c5d99100aaac33" +dependencies = [ + "libc", +] + +[[package]] +name = "hermit-abi" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d77f7ec81a6d05a3abb01ab6eb7590f6083d08449fe5a1c8b1e620283546ccb7" + +[[package]] +name = "hex" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f24254aa9a54b5c858eaee2f5bccdb46aaf0e486a595ed5fd8f86ba55232a70" + +[[package]] +name = "hkdf" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "791a029f6b9fc27657f6f188ec6e5e43f6911f6f878e0dc5501396e09809d437" +dependencies = [ + "hmac 0.12.1", +] + +[[package]] +name = "hmac" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1441c6b1e930e2817404b5046f1f989899143a12bf92de603b69f4e0aee1e15" +dependencies = [ + "crypto-mac 0.10.1", + "digest 0.9.0", +] + +[[package]] +name = "hmac" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c49c37c09c17a53d937dfbb742eb3a961d65a994e6bcdcf37e7399d0cc8ab5e" +dependencies = [ + "digest 0.10.7", +] + +[[package]] +name = "home" +version = "0.5.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5444c27eef6923071f7ebcc33e3444508466a76f7a2b93da00ed6e19f30c1ddb" +dependencies = [ + "windows-sys 0.48.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 0.3.9", +] + +[[package]] +name = "http" +version = "0.2.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8947b1a6fad4393052c7ba1f4cd97bed3e953a95c79c92ad9b051a04611d9fbb" +dependencies = [ + "bytes 1.5.0", + "fnv", + "itoa", +] + +[[package]] +name = "http-body" +version = "0.4.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d5f38f16d184e36f2408a55281cd658ecbd3ca05cce6d6510a176eca393e26d1" +dependencies = [ + "bytes 1.5.0", + "http", + "pin-project-lite", +] + +[[package]] +name = "http-range-header" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "add0ab9360ddbd88cfeb3bd9574a1d85cfdfa14db10b3e21d3700dbc4328758f" + +[[package]] +name = "httparse" +version = "1.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d897f394bad6a705d5f4104762e116a75639e470d80901eed05a860a95cb1904" + +[[package]] +name = "httpdate" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "df3b46402a9d5adb4c86a0cf463f42e19994e3ee891101b1841f30a545cb49a9" + +[[package]] +name = "httptest" +version = "0.15.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c8b44a11846bda8c9fe9194f9924db7132c34635c7ce020f180f6c5d46d2308f" +dependencies = [ + "bstr 0.2.17", + "bytes 1.5.0", + "crossbeam-channel 0.5.8", + "form_urlencoded", + "futures 0.3.29", + "http", + "hyper", + "log", + "once_cell", + "regex", + "serde", + "serde_json", + "serde_urlencoded", + "tokio", +] + +[[package]] +name = "humantime" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4" + +[[package]] +name = "hyper" +version = "0.14.27" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ffb1cfd654a8219eaef89881fdb3bb3b1cdc5fa75ded05d6933b2b382e395468" +dependencies = [ + "bytes 1.5.0", + "futures-channel", + "futures-core", + "futures-util", + "h2", + "http", + "http-body", + "httparse", + "httpdate", + "itoa", + "pin-project-lite", + "socket2 0.4.10", + "tokio", + "tower-service", + "tracing", + "want", +] + +[[package]] +name = "hyper-rustls" +version = "0.24.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ec3efd23720e2049821a693cbc7e65ea87c72f1c58ff2f9522ff332b1491e590" +dependencies = [ + "futures-util", + "http", + "hyper", + "log", + "rustls", + "rustls-native-certs", + "tokio", + "tokio-rustls", +] + +[[package]] +name = "hyper-tls" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d6183ddfa99b85da61a140bea0efc93fdf56ceaa041b37d553518030827f9905" +dependencies = [ + "bytes 1.5.0", + "hyper", + "native-tls", + "tokio", + "tokio-native-tls", +] + +[[package]] +name = "iana-time-zone" +version = "0.1.58" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8326b86b6cff230b97d0d312a6c40a60726df3332e721f72a1b035f451663b20" +dependencies = [ + "android_system_properties", + "core-foundation-sys", + "iana-time-zone-haiku", + "js-sys", + "wasm-bindgen", + "windows-core", +] + +[[package]] +name = "iana-time-zone-haiku" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f31827a206f56af32e590ba56d5d2d085f558508192593743f16b2306495269f" +dependencies = [ + "cc", +] + +[[package]] +name = "ident_case" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +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 = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "634d9b1461af396cad843f47fdba5597a4f9e6ddd4bfb6ff5d85028c25cb12f6" +dependencies = [ + "unicode-bidi", + "unicode-normalization", +] + +[[package]] +name = "im" +version = "15.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d0acd33ff0285af998aaf9b57342af478078f53492322fafc47450e09397e0e9" +dependencies = [ + "bitmaps", + "rand_core 0.6.4", + "rand_xoshiro", + "sized-chunks", + "typenum", + "version_check", +] + +[[package]] +name = "impl-codec" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "161ebdfec3c8e3b52bf61c4f3550a1eea4f9579d10dc1b936f3171ebdcd6c443" +dependencies = [ + "parity-scale-codec 2.3.1", +] + +[[package]] +name = "impl-codec" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ba6a270039626615617f3f36d15fc827041df3b78c439da2cadfa47455a77f2f" +dependencies = [ + "parity-scale-codec 3.6.9", +] + +[[package]] +name = "impl-rlp" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f28220f89297a075ddc7245cd538076ee98b01f2a9c23a53a4f1105d5a322808" +dependencies = [ + "rlp", +] + +[[package]] +name = "impl-serde" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4551f042f3438e64dbd6226b20527fc84a6e1fe65688b58746a2f53623f25f5c" +dependencies = [ + "serde", +] + +[[package]] +name = "impl-serde" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ebc88fc67028ae3db0c853baa36269d398d5f45b6982f95549ff5def78c935cd" +dependencies = [ + "serde", +] + +[[package]] +name = "impl-trait-for-tuples" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "11d7a9f6330b71fea57921c9b61c47ee6e84f72d394754eff6163ae67e7395eb" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "indenter" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ce23b50ad8242c51a442f3ff322d56b02f08852c77e4c0b4d3fd684abc89c683" + +[[package]] +name = "indexmap" +version = "1.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bd070e393353796e801d209ad339e89596eb4c8d430d18ede6a1cced8fafbd99" +dependencies = [ + "autocfg 1.1.0", + "hashbrown 0.12.3", +] + +[[package]] +name = "indexmap" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d530e1a18b1cb4c484e6e34556a0d948706958449fca0cab753d649f2bce3d1f" +dependencies = [ + "equivalent", + "hashbrown 0.14.3", +] + +[[package]] +name = "inout" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a0c10553d664a4d0bcff9f4215d0aac67a639cc68ef660840afe309b807bc9f5" +dependencies = [ + "generic-array 0.14.7", +] + +[[package]] +name = "instant" +version = "0.1.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a5bbe824c507c5da5956355e86a746d82e0e1464f65d862cc5e71da70e94b2c" +dependencies = [ + "cfg-if 1.0.0", +] + +[[package]] +name = "iovec" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b2b3ea6ff95e175473f8ffe6a7eb7c00d054240321b84c57051175fe3c1e075e" +dependencies = [ + "libc", +] + +[[package]] +name = "ipnet" +version = "2.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f518f335dce6725a761382244631d86cf0ccb2863413590b31338feb467f9c3" + +[[package]] +name = "ipnetwork" +version = "0.17.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "02c3eaab3ac0ede60ffa41add21970a7df7d91772c03383aac6c2c3d53cc716b" + +[[package]] +name = "iri-string" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "21859b667d66a4c1dacd9df0863b3efb65785474255face87f5bca39dd8407c0" +dependencies = [ + "memchr", + "serde", +] + +[[package]] +name = "is-terminal" +version = "0.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb0889898416213fab133e1d33a0e5858a48177452750691bde3666d0fdbaf8b" +dependencies = [ + "hermit-abi 0.3.3", + "rustix", + "windows-sys 0.48.0", +] + +[[package]] +name = "itertools" +version = "0.10.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b0fd2260e829bddf4cb6ea802289de2f86d6a7a690192fbe91b3f46e0f2c8473" +dependencies = [ + "either", +] + +[[package]] +name = "itertools" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b1c173a5686ce8bfa551b3563d0c2170bf24ca44da99c7ca4bfdab5418c3fe57" +dependencies = [ + "either", +] + +[[package]] +name = "itoa" +version = "1.0.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "af150ab688ff2122fcef229be89cb50dd66af9e01a4ff320cc137eecc9bacc38" + +[[package]] +name = "jobserver" +version = "0.1.27" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8c37f63953c4c63420ed5fd3d6d398c719489b9f872b9fa683262f8edd363c7d" +dependencies = [ + "libc", +] + +[[package]] +name = "js-sys" +version = "0.3.66" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cee9c64da59eae3b50095c18d3e74f8b73c0b86d2792824ff01bbce68ba229ca" +dependencies = [ + "wasm-bindgen", +] + +[[package]] +name = "jsonrpc-client-transports" +version = "18.0.0" +source = "git+https://github.com/matter-labs/jsonrpc.git?branch=master#12c53e3e20c09c2fb9966a4ef1b0ea63de172540" +dependencies = [ + "derive_more", + "futures 0.3.29", + "jsonrpc-core 18.0.0 (git+https://github.com/matter-labs/jsonrpc.git?branch=master)", + "jsonrpc-pubsub", + "log", + "serde", + "serde_json", +] + +[[package]] +name = "jsonrpc-core" +version = "18.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "14f7f76aef2d054868398427f6c54943cf3d1caa9a7ec7d0c38d69df97a965eb" +dependencies = [ + "futures 0.3.29", + "futures-executor", + "futures-util", + "log", + "serde", + "serde_derive", + "serde_json", +] + +[[package]] +name = "jsonrpc-core" +version = "18.0.0" +source = "git+https://github.com/matter-labs/jsonrpc.git?branch=master#12c53e3e20c09c2fb9966a4ef1b0ea63de172540" +dependencies = [ + "futures 0.3.29", + "futures-executor", + "futures-util", + "log", + "serde", + "serde_derive", + "serde_json", +] + +[[package]] +name = "jsonrpc-core-client" +version = "18.0.0" +source = "git+https://github.com/matter-labs/jsonrpc.git?branch=master#12c53e3e20c09c2fb9966a4ef1b0ea63de172540" +dependencies = [ + "futures 0.3.29", + "jsonrpc-client-transports", +] + +[[package]] +name = "jsonrpc-derive" +version = "18.0.0" +source = "git+https://github.com/matter-labs/jsonrpc.git?branch=master#12c53e3e20c09c2fb9966a4ef1b0ea63de172540" +dependencies = [ + "proc-macro-crate 0.1.5", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "jsonrpc-http-server" +version = "18.0.0" +source = "git+https://github.com/matter-labs/jsonrpc.git?branch=master#12c53e3e20c09c2fb9966a4ef1b0ea63de172540" +dependencies = [ + "futures 0.3.29", + "hyper", + "jsonrpc-core 18.0.0 (git+https://github.com/matter-labs/jsonrpc.git?branch=master)", + "jsonrpc-server-utils", + "log", + "net2", + "parking_lot 0.11.2", + "unicase", +] + +[[package]] +name = "jsonrpc-pubsub" +version = "18.0.0" +source = "git+https://github.com/matter-labs/jsonrpc.git?branch=master#12c53e3e20c09c2fb9966a4ef1b0ea63de172540" +dependencies = [ + "futures 0.3.29", + "jsonrpc-core 18.0.0 (git+https://github.com/matter-labs/jsonrpc.git?branch=master)", + "lazy_static", + "log", + "parking_lot 0.11.2", + "rand 0.7.3", + "serde", +] + +[[package]] +name = "jsonrpc-server-utils" +version = "18.0.0" +source = "git+https://github.com/matter-labs/jsonrpc.git?branch=master#12c53e3e20c09c2fb9966a4ef1b0ea63de172540" +dependencies = [ + "bytes 1.5.0", + "futures 0.3.29", + "globset", + "jsonrpc-core 18.0.0 (git+https://github.com/matter-labs/jsonrpc.git?branch=master)", + "lazy_static", + "log", + "tokio", + "tokio-stream", + "tokio-util 0.6.10", + "unicase", +] + +[[package]] +name = "jsonrpc-ws-server" +version = "18.0.0" +source = "git+https://github.com/matter-labs/jsonrpc.git?branch=master#12c53e3e20c09c2fb9966a4ef1b0ea63de172540" +dependencies = [ + "futures 0.3.29", + "jsonrpc-core 18.0.0 (git+https://github.com/matter-labs/jsonrpc.git?branch=master)", + "jsonrpc-server-utils", + "log", + "parity-ws", + "parking_lot 0.11.2", + "slab", +] + +[[package]] +name = "jsonrpsee" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e5f3783308bddc49d0218307f66a09330c106fbd792c58bac5c8dc294fdd0f98" +dependencies = [ + "jsonrpsee-client-transport", + "jsonrpsee-core", + "jsonrpsee-http-client", + "jsonrpsee-proc-macros", + "jsonrpsee-server", + "jsonrpsee-types", + "jsonrpsee-wasm-client", + "jsonrpsee-ws-client", + "tracing", +] + +[[package]] +name = "jsonrpsee-client-transport" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "abc5630e4fa0096f00ec7b44d520701fda4504170cb85e22dca603ae5d7ad0d7" +dependencies = [ + "futures-channel", + "futures-util", + "gloo-net", + "http", + "jsonrpsee-core", + "pin-project", + "rustls-native-certs", + "soketto", + "thiserror", + "tokio", + "tokio-rustls", + "tokio-util 0.7.10", + "tracing", + "webpki-roots 0.24.0", +] + +[[package]] +name = "jsonrpsee-core" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5aaa4c4d5fb801dcc316d81f76422db259809037a86b3194ae538dd026b05ed7" +dependencies = [ + "anyhow", + "async-lock", + "async-trait", + "beef", + "futures-timer", + "futures-util", + "globset", + "hyper", + "jsonrpsee-types", + "parking_lot 0.12.1", + "rand 0.8.5", + "rustc-hash", + "serde", + "serde_json", + "soketto", + "thiserror", + "tokio", + "tokio-stream", + "tracing", + "wasm-bindgen-futures", +] + +[[package]] +name = "jsonrpsee-http-client" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "aa7165efcbfbc951d180162ff28fe91b657ed81925e37a35e4a396ce12109f96" +dependencies = [ + "async-trait", + "hyper", + "hyper-rustls", + "jsonrpsee-core", + "jsonrpsee-types", + "serde", + "serde_json", + "thiserror", + "tokio", + "tower", + "tracing", +] + +[[package]] +name = "jsonrpsee-proc-macros" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "21dc12b1d4f16a86e8c522823c4fab219c88c03eb7c924ec0501a64bf12e058b" +dependencies = [ + "heck 0.4.1", + "proc-macro-crate 1.3.1", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "jsonrpsee-server" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6e79d78cfd5abd8394da10753723093c3ff64391602941c9c4b1d80a3414fd53" +dependencies = [ + "futures-util", + "hyper", + "jsonrpsee-core", + "jsonrpsee-types", + "serde", + "serde_json", + "soketto", + "tokio", + "tokio-stream", + "tokio-util 0.7.10", + "tower", + "tracing", +] + +[[package]] +name = "jsonrpsee-types" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "00aa7cc87bc42e04e26c8ac3e7186142f7fd2949c763d9b6a7e64a69672d8fb2" +dependencies = [ + "anyhow", + "beef", + "serde", + "serde_json", + "thiserror", + "tracing", +] + +[[package]] +name = "jsonrpsee-wasm-client" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0fe953c2801356f214d3f4051f786b3d11134512a46763ee8c39a9e3fa2cc1c0" +dependencies = [ + "jsonrpsee-client-transport", + "jsonrpsee-core", + "jsonrpsee-types", +] + +[[package]] +name = "jsonrpsee-ws-client" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c71b2597ec1c958c6d5bc94bb61b44d74eb28e69dc421731ab0035706f13882" +dependencies = [ + "http", + "jsonrpsee-client-transport", + "jsonrpsee-core", + "jsonrpsee-types", +] + +[[package]] +name = "jsonwebtoken" +version = "8.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6971da4d9c3aa03c3d8f3ff0f4155b534aad021292003895a469716b2a230378" +dependencies = [ + "base64 0.21.5", + "pem", + "ring 0.16.20", + "serde", + "serde_json", + "simple_asn1", +] + +[[package]] +name = "k256" +version = "0.11.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72c1e0b51e7ec0a97369623508396067a486bd0cbed95a2659a4b863d28cfc8b" +dependencies = [ + "cfg-if 1.0.0", + "ecdsa 0.14.8", + "elliptic-curve 0.12.3", + "sha2 0.10.8", +] + +[[package]] +name = "k256" +version = "0.13.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f01b677d82ef7a676aa37e099defd83a28e15687112cafdd112d60236b6115b" +dependencies = [ + "cfg-if 1.0.0", + "ecdsa 0.16.9", + "elliptic-curve 0.13.8", + "once_cell", + "sha2 0.10.8", + "signature 2.2.0", +] + +[[package]] +name = "keccak" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f6d5ed8676d904364de097082f4e7d240b571b67989ced0240f08b7f966f940" +dependencies = [ + "cpufeatures", +] + +[[package]] +name = "kernel32-sys" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7507624b29483431c0ba2d82aece8ca6cdba9382bff4ddd0f7490560c056098d" +dependencies = [ + "winapi 0.2.8", + "winapi-build", +] + +[[package]] +name = "lalrpop" +version = "0.20.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "da4081d44f4611b66c6dd725e6de3169f9f63905421e8626fcb86b6a898998b8" +dependencies = [ + "ascii-canvas", + "bit-set", + "diff", + "ena", + "is-terminal", + "itertools 0.10.5", + "lalrpop-util", + "petgraph", + "regex", + "regex-syntax 0.7.5", + "string_cache", + "term", + "tiny-keccak 2.0.2", + "unicode-xid 0.2.4", +] + +[[package]] +name = "lalrpop-util" +version = "0.20.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f35c735096c0293d313e8f2a641627472b83d01b937177fe76e5e2708d31e0d" + +[[package]] +name = "language-tags" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d4345964bb142484797b161f473a503a434de77149dd8c7427788c6e13379388" + +[[package]] +name = "lazy_static" +version = "1.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" + +[[package]] +name = "lazycell" +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 = "libc" +version = "0.2.150" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "89d92a4743f9a61002fae18374ed11e7973f530cb3a3255fb354818118b2203c" + +[[package]] +name = "libloading" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b67380fd3b2fbe7527a606e18729d21c6f3951633d0500574c4dc22d2d638b9f" +dependencies = [ + "cfg-if 1.0.0", + "winapi 0.3.9", +] + +[[package]] +name = "libm" +version = "0.2.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4ec2a862134d2a7d32d7983ddcdd1c4923530833c9f2ea1a44fc5fa473989058" + +[[package]] +name = "libredox" +version = "0.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "85c833ca1e66078851dba29046874e38f08b2c883700aa29a03ddd3b23814ee8" +dependencies = [ + "bitflags 2.4.1", + "libc", + "redox_syscall 0.4.1", +] + +[[package]] +name = "librocksdb-sys" +version = "0.11.0+8.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3386f101bcb4bd252d8e9d2fb41ec3b0862a15a62b478c355b2982efa469e3e" +dependencies = [ + "bindgen", + "bzip2-sys", + "cc", + "glob", + "libc", + "libz-sys", +] + +[[package]] +name = "libz-sys" +version = "1.1.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d97137b25e321a73eef1418d1d5d2eda4d77e12813f8e6dead84bc52c5870a7b" +dependencies = [ + "cc", + "pkg-config", + "vcpkg", +] + +[[package]] +name = "linkme" +version = "0.3.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "91ed2ee9464ff9707af8e9ad834cffa4802f072caad90639c583dd3c62e6e608" +dependencies = [ + "linkme-impl", +] + +[[package]] +name = "linkme-impl" +version = "0.3.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ba125974b109d512fccbc6c0244e7580143e460895dfd6ea7f8bbb692fd94396" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "linux-raw-sys" +version = "0.4.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "969488b55f8ac402214f3f5fd243ebb7206cf82de60d3172994707a4bcc2b829" + +[[package]] +name = "local-channel" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b6cbc85e69b8df4b8bb8b89ec634e7189099cea8927a276b7384ce5488e53ec8" +dependencies = [ + "futures-core", + "futures-sink", + "local-waker", +] + +[[package]] +name = "local-waker" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4d873d7c67ce09b42110d801813efbc9364414e356be9935700d368351657487" + +[[package]] +name = "lock_api" +version = "0.4.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3c168f8615b12bc01f9c17e2eb0cc07dcae1940121185446edc3744920e8ef45" +dependencies = [ + "autocfg 1.1.0", + "scopeguard", +] + +[[package]] +name = "log" +version = "0.4.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b5e6163cb8c49088c2c36f57875e58ccd8c87c7427f7fbd50ea6710b2f3f2e8f" + +[[package]] +name = "logos" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c000ca4d908ff18ac99b93a062cb8958d331c3220719c52e77cb19cc6ac5d2c1" +dependencies = [ + "logos-derive", +] + +[[package]] +name = "logos-codegen" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dc487311295e0002e452025d6b580b77bb17286de87b57138f3b5db711cded68" +dependencies = [ + "beef", + "fnv", + "proc-macro2 1.0.70", + "quote 1.0.33", + "regex-syntax 0.6.29", + "syn 2.0.39", +] + +[[package]] +name = "logos-derive" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dbfc0d229f1f42d790440136d941afd806bc9e949e2bcb8faa813b0f00d1267e" +dependencies = [ + "logos-codegen", +] + +[[package]] +name = "lru" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2994eeba8ed550fd9b47a0b38f0242bc3344e496483c6180b69139cc2fa5d1d7" + +[[package]] +name = "mach" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b823e83b2affd8f40a9ee8c29dbc56404c1e34cd2710921f2801e2cf29527afa" +dependencies = [ + "libc", +] + +[[package]] +name = "mach2" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6d0d1830bcd151a6fc4aea1369af235b36c1528fe976b8ff678683c9995eade8" +dependencies = [ + "libc", +] + +[[package]] +name = "maplit" +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" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8263075bb86c5a1b1427b5ae862e8889656f126e9f77c484496e8b47cf5c5558" +dependencies = [ + "regex-automata 0.1.10", +] + +[[package]] +name = "matchit" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0e7465ac9959cc2b1404e8e2367b43684a6d13790fe23056cc8c6c5a6b7bcb94" + +[[package]] +name = "maybe-uninit" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60302e4db3a61da70c0cb7991976248362f30319e88850c487b9b95bbf059e00" + +[[package]] +name = "md-5" +version = "0.10.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d89e7ee0cfbedfc4da3340218492196241d89eefb6dab27de5df917a6d2e78cf" +dependencies = [ + "cfg-if 1.0.0", + "digest 0.10.7", +] + +[[package]] +name = "memchr" +version = "2.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f665ee40bc4a3c5590afb1e9677db74a508659dfd71e126420da8274909a0167" + +[[package]] +name = "memoffset" +version = "0.5.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "043175f069eda7b85febe4a74abbaeff828d9f8b448515d3151a14a3542811aa" +dependencies = [ + "autocfg 1.1.0", +] + +[[package]] +name = "memoffset" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a634b1c61a95585bd15607c6ab0c4e5b226e695ff2800ba0cdccddf208c406c" +dependencies = [ + "autocfg 1.1.0", +] + +[[package]] +name = "metrics" +version = "0.21.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fde3af1a009ed76a778cb84fdef9e7dbbdf5775ae3e4cc1f434a6a307f6f76c5" +dependencies = [ + "ahash 0.8.6", + "metrics-macros", + "portable-atomic", +] + +[[package]] +name = "metrics-exporter-prometheus" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a4964177ddfdab1e3a2b37aec7cf320e14169abb0ed73999f558136409178d5" +dependencies = [ + "base64 0.21.5", + "hyper", + "indexmap 1.9.3", + "ipnet", + "metrics", + "metrics-util", + "quanta 0.11.1", + "thiserror", + "tokio", + "tracing", +] + +[[package]] +name = "metrics-macros" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ddece26afd34c31585c74a4db0630c376df271c285d682d1e55012197830b6df" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "metrics-util" +version = "0.15.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4de2ed6e491ed114b40b732e4d1659a9d53992ebd87490c44a6ffe23739d973e" +dependencies = [ + "crossbeam-epoch 0.9.15", + "crossbeam-utils 0.8.16", + "hashbrown 0.13.1", + "metrics", + "num_cpus", + "quanta 0.11.1", + "sketches-ddsketch", +] + +[[package]] +name = "miette" +version = "5.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "59bb584eaeeab6bd0226ccf3509a69d7936d148cf3d036ad350abe35e8c6856e" +dependencies = [ + "miette-derive", + "once_cell", + "thiserror", + "unicode-width", +] + +[[package]] +name = "miette-derive" +version = "5.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49e7bc1560b95a3c4a25d03de42fe76ca718ab92d1a22a55b9b4cf67b3ae635c" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "mime" +version = "0.3.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6877bb514081ee2a7ff5ef9de3281f14a4dd4bceac4c09388074a6b5df8a139a" + +[[package]] +name = "mime_guess" +version = "2.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4192263c238a5f0d0c6bfd21f336a313a4ce1c450542449ca191bb657b4642ef" +dependencies = [ + "mime", + "unicase", +] + +[[package]] +name = "mini-moka" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23e0b72e7c9042467008b10279fc732326bd605459ae03bda88825909dd19b56" +dependencies = [ + "crossbeam-channel 0.5.8", + "crossbeam-utils 0.8.16", + "dashmap", + "skeptic", + "smallvec", + "tagptr", + "triomphe", +] + +[[package]] +name = "minimal-lexical" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a" + +[[package]] +name = "miniz_oxide" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e7810e0be55b428ada41041c41f32c9f1a42817901b4ccf45fa3d4b6561e74c7" +dependencies = [ + "adler", +] + +[[package]] +name = "mio" +version = "0.6.23" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4afd66f5b91bf2a3bc13fad0e21caedac168ca4c707504e75585648ae80e4cc4" +dependencies = [ + "cfg-if 0.1.10", + "fuchsia-zircon", + "fuchsia-zircon-sys", + "iovec", + "kernel32-sys", + "libc", + "log", + "miow", + "net2", + "slab", + "winapi 0.2.8", +] + +[[package]] +name = "mio" +version = "0.8.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3dce281c5e46beae905d4de1870d8b1509a9142b62eedf18b443b011ca8343d0" +dependencies = [ + "libc", + "log", + "wasi 0.11.0+wasi-snapshot-preview1", + "windows-sys 0.48.0", +] + +[[package]] +name = "mio-extras" +version = "2.0.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "52403fe290012ce777c4626790c8951324a2b9e3316b3143779c72b029742f19" +dependencies = [ + "lazycell", + "log", + "mio 0.6.23", + "slab", +] + +[[package]] +name = "miow" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ebd808424166322d4a38da87083bfddd3ac4c131334ed55856112eb06d46944d" +dependencies = [ + "kernel32-sys", + "net2", + "winapi 0.2.8", + "ws2_32-sys", +] + +[[package]] +name = "multimap" +version = "0.8.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e5ce46fe64a9d73be07dcbe690a38ce1b293be448fd8ce1e6c1b8062c9f72c6a" + +[[package]] +name = "multivm" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "hex", + "itertools 0.10.5", + "once_cell", + "thiserror", + "tracing", + "vise", + "zk_evm 1.3.1", + "zk_evm 1.3.3 (git+https://github.com/matter-labs/era-zk_evm.git?tag=v1.3.3-rc2)", + "zk_evm 1.4.0", + "zksync_contracts", + "zksync_state", + "zksync_system_constants", + "zksync_types", + "zksync_utils", +] + +[[package]] +name = "native-tls" +version = "0.2.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "07226173c32f2926027b63cce4bcd8076c3552846cbe7925f3aaffeac0a3b92e" +dependencies = [ + "lazy_static", + "libc", + "log", + "openssl", + "openssl-probe", + "openssl-sys", + "schannel", + "security-framework", + "security-framework-sys", + "tempfile", +] + +[[package]] +name = "net2" +version = "0.2.39" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b13b648036a2339d06de780866fbdfda0dde886de7b3af2ddeba8b14f4ee34ac" +dependencies = [ + "cfg-if 0.1.10", + "libc", + "winapi 0.3.9", +] + +[[package]] +name = "new_debug_unreachable" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e4a24736216ec316047a1fc4252e27dabb04218aa4a3f37c6e7ddbf1f9782b54" + +[[package]] +name = "nix" +version = "0.27.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2eb04e9c688eff1c89d72b407f168cf79bb9e867a9d3323ed6c01519eb9cc053" +dependencies = [ + "bitflags 2.4.1", + "cfg-if 1.0.0", + "libc", +] + +[[package]] +name = "no-std-compat" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b93853da6d84c2e3c7d730d6473e8817692dd89be387eb01b94d7f108ecb5b8c" + +[[package]] +name = "nodrop" +version = "0.1.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72ef4a56884ca558e5ddb05a1d1e7e1bfd9a68d9ed024c21704cc98872dae1bb" + +[[package]] +name = "nom" +version = "7.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d273983c5a657a70a3e8f2a01329822f3b8c8172b73826411a55751e404a0a4a" +dependencies = [ + "memchr", + "minimal-lexical", +] + +[[package]] +name = "nonzero_ext" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "38bf9645c8b145698bb0b18a4637dcacbc421ea49bef2317e4fd8065a387cf21" + +[[package]] +name = "nu-ansi-term" +version = "0.46.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77a8165726e8236064dbb45459242600304b42a5ea24ee2948e18e023bf7ba84" +dependencies = [ + "overload", + "winapi 0.3.9", +] + +[[package]] +name = "num" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8b7a8e9be5e039e2ff869df49155f1c06bd01ade2117ec783e56ab0932b67a8f" +dependencies = [ + "num-bigint 0.3.3", + "num-complex 0.3.1", + "num-integer", + "num-iter", + "num-rational 0.3.2", + "num-traits", +] + +[[package]] +name = "num" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b05180d69e3da0e530ba2a1dae5110317e49e3b7f3d41be227dc5f92e49ee7af" +dependencies = [ + "num-bigint 0.4.4", + "num-complex 0.4.4", + "num-integer", + "num-iter", + "num-rational 0.4.1", + "num-traits", +] + +[[package]] +name = "num-bigint" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5f6f7833f2cbf2360a6cfd58cd41a53aa7a90bd4c202f5b1c7dd2ed73c57b2c3" +dependencies = [ + "autocfg 1.1.0", + "num-integer", + "num-traits", + "serde", +] + +[[package]] +name = "num-bigint" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "608e7659b5c3d7cba262d894801b9ec9d00de989e8a82bd4bef91d08da45cdc0" +dependencies = [ + "autocfg 1.1.0", + "num-integer", + "num-traits", + "serde", +] + +[[package]] +name = "num-complex" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "747d632c0c558b87dbabbe6a82f3b4ae03720d0646ac5b7b4dae89394be5f2c5" +dependencies = [ + "num-traits", + "serde", +] + +[[package]] +name = "num-complex" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1ba157ca0885411de85d6ca030ba7e2a83a28636056c7c699b07c8b6f7383214" +dependencies = [ + "num-traits", +] + +[[package]] +name = "num-derive" +version = "0.2.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eafd0b45c5537c3ba526f79d3e75120036502bebacbb3f3220914067ce39dbf2" +dependencies = [ + "proc-macro2 0.4.30", + "quote 0.6.13", + "syn 0.15.44", +] + +[[package]] +name = "num-derive" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "876a53fff98e03a936a674b29568b0e605f06b29372c2489ff4de23f1949743d" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "num-integer" +version = "0.1.45" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "225d3389fb3509a24c93f5c29eb6bde2586b98d9f016636dff58d7c6f7569cd9" +dependencies = [ + "autocfg 1.1.0", + "num-traits", +] + +[[package]] +name = "num-iter" +version = "0.1.43" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7d03e6c028c5dc5cac6e2dec0efda81fc887605bb3d884578bb6d6bf7514e252" +dependencies = [ + "autocfg 1.1.0", + "num-integer", + "num-traits", +] + +[[package]] +name = "num-modular" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "64a5fe11d4135c3bcdf3a95b18b194afa9608a5f6ff034f5d857bc9a27fb0119" +dependencies = [ + "num-integer", + "num-traits", +] + +[[package]] +name = "num-rational" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "12ac428b1cb17fce6f731001d307d351ec70a6d202fc2e60f7d4c5e42d8f4f07" +dependencies = [ + "autocfg 1.1.0", + "num-bigint 0.3.3", + "num-integer", + "num-traits", + "serde", +] + +[[package]] +name = "num-rational" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0638a1c9d0a3c0914158145bc76cff373a75a627e6ecbfb71cbe6f453a5a19b0" +dependencies = [ + "autocfg 1.1.0", + "num-bigint 0.4.4", + "num-integer", + "num-traits", +] + +[[package]] +name = "num-traits" +version = "0.2.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "39e3200413f237f41ab11ad6d161bc7239c84dcb631773ccd7de3dfe4b5c267c" +dependencies = [ + "autocfg 1.1.0", + "libm", +] + +[[package]] +name = "num_cpus" +version = "1.16.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43" +dependencies = [ + "hermit-abi 0.3.3", + "libc", +] + +[[package]] +name = "num_enum" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a015b430d3c108a207fd776d2e2196aaf8b1cf8cf93253e3a097ff3085076a1" +dependencies = [ + "num_enum_derive 0.6.1", +] + +[[package]] +name = "num_enum" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "683751d591e6d81200c39fb0d1032608b77724f34114db54f571ff1317b337c0" +dependencies = [ + "num_enum_derive 0.7.1", +] + +[[package]] +name = "num_enum_derive" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "96667db765a921f7b295ffee8b60472b686a51d4f21c2ee4ffdb94c7013b65a6" +dependencies = [ + "proc-macro-crate 1.3.1", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "num_enum_derive" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c11e44798ad209ccdd91fc192f0526a369a01234f7373e1b141c96d7cee4f0e" +dependencies = [ + "proc-macro-crate 2.0.0", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "num_threads" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2819ce041d2ee131036f4fc9d6ae7ae125a3a40e97ba64d04fe799ad9dabbb44" +dependencies = [ + "libc", +] + +[[package]] +name = "object" +version = "0.32.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9cf5f9dd3933bd50a9e1f149ec995f39ae2c496d31fd772c1fd45ebc27e902b0" +dependencies = [ + "memchr", +] + +[[package]] +name = "once_cell" +version = "1.18.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dd8b5dd2ae5ed71462c540258bedcb51965123ad7e7ccf4b9a8cafaa4a63576d" + +[[package]] +name = "opaque-debug" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2839e79665f131bdb5782e51f2c6c9599c133c6098982a54c794358bf432529c" + +[[package]] +name = "opaque-debug" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "624a8340c38c1b80fd549087862da4ba43e08858af025b236e509b6649fc13d5" + +[[package]] +name = "open-fastrlp" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "786393f80485445794f6043fd3138854dd109cc6c4bd1a6383db304c9ce9b9ce" +dependencies = [ + "arrayvec 0.7.4", + "auto_impl", + "bytes 1.5.0", + "ethereum-types 0.14.1", + "open-fastrlp-derive", +] + +[[package]] +name = "open-fastrlp-derive" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "003b2be5c6c53c1cfeb0a238b8a1c3915cd410feb684457a36c10038f764bb1c" +dependencies = [ + "bytes 1.5.0", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "openssl" +version = "0.10.60" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "79a4c6c3a2b158f7f8f2a2fc5a969fa3a068df6fc9dbb4a43845436e3af7c800" +dependencies = [ + "bitflags 2.4.1", + "cfg-if 1.0.0", + "foreign-types", + "libc", + "once_cell", + "openssl-macros", + "openssl-sys", +] + +[[package]] +name = "openssl-macros" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a948666b637a0f465e8564c73e89d4dde00d72d4d473cc972f390fc3dcee7d9c" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "openssl-probe" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ff011a302c396a5197692431fc1948019154afc178baf7d8e37367442a4601cf" + +[[package]] +name = "openssl-src" +version = "300.1.6+3.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "439fac53e092cd7442a3660c85dde4643ab3b5bd39040912388dcdabf6b88085" +dependencies = [ + "cc", +] + +[[package]] +name = "openssl-sys" +version = "0.9.96" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3812c071ba60da8b5677cc12bcb1d42989a65553772897a7e0355545a819838f" +dependencies = [ + "cc", + "libc", + "openssl-src", + "pkg-config", + "vcpkg", +] + +[[package]] +name = "option-ext" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "04744f49eae99ab78e0d5c0b603ab218f515ea8cfe5a456d7629ad883a3b6e7d" + +[[package]] +name = "ordered-float" +version = "2.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "68f19d67e5a2795c94e73e0bb1cc1a7edeb2e28efd39e2e1c9b7a40c1108b11c" +dependencies = [ + "num-traits", +] + +[[package]] +name = "os_info" +version = "3.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "006e42d5b888366f1880eda20371fedde764ed2213dc8496f49622fa0c99cd5e" +dependencies = [ + "log", + "serde", + "winapi 0.3.9", +] + +[[package]] +name = "overload" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b15813163c1d831bf4a13c3610c05c0d03b39feb07f7e09fa234dac9b15aaf39" + +[[package]] +name = "packed_simd" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f9f08af0c877571712e2e3e686ad79efad9657dbf0f7c3c8ba943ff6c38932d" +dependencies = [ + "cfg-if 1.0.0", + "num-traits", +] + +[[package]] +name = "pairing_ce" +version = "0.28.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "db007b21259660d025918e653508f03050bf23fb96a88601f9936329faadc597" +dependencies = [ + "byteorder", + "cfg-if 1.0.0", + "ff_ce", + "rand 0.4.6", + "serde", +] + +[[package]] +name = "pairing_ce" +version = "0.28.5" +source = "git+https://github.com/matter-labs/pairing.git?rev=f55393fd366596eac792d78525d26e9c4d6ed1ca#f55393fd366596eac792d78525d26e9c4d6ed1ca" +dependencies = [ + "byteorder", + "cfg-if 1.0.0", + "ff_ce", + "rand 0.4.6", + "serde", +] + +[[package]] +name = "pairing_ce" +version = "0.28.5" +source = "git+https://github.com/matter-labs/pairing.git#f55393fd366596eac792d78525d26e9c4d6ed1ca" +dependencies = [ + "byteorder", + "cfg-if 1.0.0", + "ff_ce", + "rand 0.4.6", + "serde", +] + +[[package]] +name = "parity-crypto" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4b92ea9ddac0d6e1db7c49991e7d397d34a9fd814b4c93cda53788e8eef94e35" +dependencies = [ + "aes 0.6.0", + "aes-ctr", + "block-modes", + "digest 0.9.0", + "ethereum-types 0.12.1", + "hmac 0.10.1", + "lazy_static", + "pbkdf2 0.7.5", + "ripemd160", + "rustc-hex", + "scrypt 0.5.0", + "secp256k1 0.20.3", + "sha2 0.9.9", + "subtle", + "tiny-keccak 2.0.2", + "zeroize", +] + +[[package]] +name = "parity-scale-codec" +version = "2.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "373b1a4c1338d9cd3d1fa53b3a11bdab5ab6bd80a20f7f7becd76953ae2be909" +dependencies = [ + "arrayvec 0.7.4", + "bitvec 0.20.4", + "byte-slice-cast", + "impl-trait-for-tuples", + "parity-scale-codec-derive 2.3.1", + "serde", +] + +[[package]] +name = "parity-scale-codec" +version = "3.6.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "881331e34fa842a2fb61cc2db9643a8fedc615e47cfcc52597d1af0db9a7e8fe" +dependencies = [ + "arrayvec 0.7.4", + "bitvec 1.0.1", + "byte-slice-cast", + "impl-trait-for-tuples", + "parity-scale-codec-derive 3.6.9", + "serde", +] + +[[package]] +name = "parity-scale-codec-derive" +version = "2.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1557010476e0595c9b568d16dcfb81b93cdeb157612726f5170d31aa707bed27" +dependencies = [ + "proc-macro-crate 1.3.1", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "parity-scale-codec-derive" +version = "3.6.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "be30eaf4b0a9fba5336683b38de57bb86d179a35862ba6bfcf57625d006bde5b" +dependencies = [ + "proc-macro-crate 2.0.0", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "parity-ws" +version = "0.11.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5983d3929ad50f12c3eb9a6743f19d691866ecd44da74c0a3308c3f8a56df0c6" +dependencies = [ + "byteorder", + "bytes 0.4.12", + "httparse", + "log", + "mio 0.6.23", + "mio-extras", + "rand 0.7.3", + "sha-1 0.8.2", + "slab", + "url", +] + +[[package]] +name = "parking_lot" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7d17b78036a60663b797adeaee46f5c9dfebb86948d1255007a1d6be0271ff99" +dependencies = [ + "instant", + "lock_api", + "parking_lot_core 0.8.6", +] + +[[package]] +name = "parking_lot" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f" +dependencies = [ + "lock_api", + "parking_lot_core 0.9.9", +] + +[[package]] +name = "parking_lot_core" +version = "0.8.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60a2cfe6f0ad2bfc16aefa463b497d5c7a5ecd44a23efa72aa342d90177356dc" +dependencies = [ + "cfg-if 1.0.0", + "instant", + "libc", + "redox_syscall 0.2.16", + "smallvec", + "winapi 0.3.9", +] + +[[package]] +name = "parking_lot_core" +version = "0.9.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4c42a9226546d68acdd9c0a280d17ce19bfe27a46bf68784e4066115788d008e" +dependencies = [ + "cfg-if 1.0.0", + "libc", + "redox_syscall 0.4.1", + "smallvec", + "windows-targets 0.48.5", +] + +[[package]] +name = "password-hash" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "54986aa4bfc9b98c6a5f40184223658d187159d7b3c6af33f2b2aa25ae1db0fa" +dependencies = [ + "base64ct", + "rand_core 0.6.4", +] + +[[package]] +name = "password-hash" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7676374caaee8a325c9e7a2ae557f216c5563a171d6997b0ef8a65af35147700" +dependencies = [ + "base64ct", + "rand_core 0.6.4", + "subtle", +] + +[[package]] +name = "paste" +version = "1.0.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "de3145af08024dea9fa9914f381a17b8fc6034dfb00f3a84013f7ff43f29ed4c" + +[[package]] +name = "path-slash" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1e91099d4268b0e11973f036e885d652fb0b21fedcf69738c627f94db6a44f42" + +[[package]] +name = "pbkdf2" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b3b8c0d71734018084da0c0354193a5edfb81b20d2d57a92c5b154aefc554a4a" +dependencies = [ + "crypto-mac 0.10.1", +] + +[[package]] +name = "pbkdf2" +version = "0.7.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bf916dd32dd26297907890d99dc2740e33f6bd9073965af4ccff2967962f5508" +dependencies = [ + "base64ct", + "crypto-mac 0.10.1", + "hmac 0.10.1", + "password-hash 0.1.4", + "sha2 0.9.9", +] + +[[package]] +name = "pbkdf2" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "83a0692ec44e4cf1ef28ca317f14f8f07da2d95ec3fa01f86e4467b725e60917" +dependencies = [ + "digest 0.10.7", + "hmac 0.12.1", + "password-hash 0.4.2", + "sha2 0.10.8", +] + +[[package]] +name = "pbkdf2" +version = "0.12.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f8ed6a7761f76e3b9f92dfb0a60a6a6477c61024b775147ff0973a02653abaf2" +dependencies = [ + "digest 0.10.7", + "hmac 0.12.1", +] + +[[package]] +name = "peeking_take_while" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "19b17cddbe7ec3f8bc800887bab5e717348c95ea2ca0b1bf0837fb964dc67099" + +[[package]] +name = "pem" +version = "1.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a8835c273a76a90455d7344889b0964598e3316e2a79ede8e36f16bdcf2228b8" +dependencies = [ + "base64 0.13.1", +] + +[[package]] +name = "pem-rfc7468" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "88b39c9bfcfc231068454382784bb460aae594343fb030d46e9f50a645418412" +dependencies = [ + "base64ct", +] + +[[package]] +name = "percent-encoding" +version = "2.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e" + +[[package]] +name = "pest" +version = "2.7.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ae9cee2a55a544be8b89dc6848072af97a20f2422603c10865be2a42b580fff5" +dependencies = [ + "memchr", + "thiserror", + "ucd-trie", +] + +[[package]] +name = "pest_derive" +version = "2.7.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "81d78524685f5ef2a3b3bd1cafbc9fcabb036253d9b1463e726a91cd16e2dfc2" +dependencies = [ + "pest", + "pest_generator", +] + +[[package]] +name = "pest_generator" +version = "2.7.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "68bd1206e71118b5356dae5ddc61c8b11e28b09ef6a31acbd15ea48a28e0c227" +dependencies = [ + "pest", + "pest_meta", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "pest_meta" +version = "2.7.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7c747191d4ad9e4a4ab9c8798f1e82a39affe7ef9648390b7e5548d18e099de6" +dependencies = [ + "once_cell", + "pest", + "sha2 0.10.8", +] + +[[package]] +name = "petgraph" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e1d3afd2628e69da2be385eb6f2fd57c8ac7977ceeff6dc166ff1657b0e386a9" +dependencies = [ + "fixedbitset", + "indexmap 2.1.0", +] + +[[package]] +name = "pharos" +version = "0.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e9567389417feee6ce15dd6527a8a1ecac205ef62c2932bcf3d9f6fc5b78b414" +dependencies = [ + "futures 0.3.29", + "rustc_version", +] + +[[package]] +name = "phf" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ade2d8b8f33c7333b51bcf0428d37e217e9f32192ae4772156f65063b8ce03dc" +dependencies = [ + "phf_macros", + "phf_shared 0.11.2", +] + +[[package]] +name = "phf_generator" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "48e4cc64c2ad9ebe670cb8fd69dd50ae301650392e81c05f9bfcb2d5bdbc24b0" +dependencies = [ + "phf_shared 0.11.2", + "rand 0.8.5", +] + +[[package]] +name = "phf_macros" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3444646e286606587e49f3bcf1679b8cef1dc2c5ecc29ddacaffc305180d464b" +dependencies = [ + "phf_generator", + "phf_shared 0.11.2", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "phf_shared" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b6796ad771acdc0123d2a88dc428b5e38ef24456743ddb1744ed628f9815c096" +dependencies = [ + "siphasher", +] + +[[package]] +name = "phf_shared" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "90fcb95eef784c2ac79119d1dd819e162b5da872ce6f3c3abe1e8ca1c082f72b" +dependencies = [ + "siphasher", +] + +[[package]] +name = "pin-project" +version = "1.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fda4ed1c6c173e3fc7a83629421152e01d7b1f9b7f65fb301e490e8cfc656422" +dependencies = [ + "pin-project-internal", +] + +[[package]] +name = "pin-project-internal" +version = "1.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4359fd9c9171ec6e8c62926d6faaf553a8dc3f64e1507e76da7911b4f6a04405" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "pin-project-lite" +version = "0.2.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8afb450f006bf6385ca15ef45d71d2288452bc3683ce2e2cacc0d18e4be60b58" + +[[package]] +name = "pin-utils" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184" + +[[package]] +name = "pkcs8" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9eca2c590a5f85da82668fa685c09ce2888b9430e83299debf1f34b65fd4a4ba" +dependencies = [ + "der 0.6.1", + "spki 0.6.0", +] + +[[package]] +name = "pkcs8" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f950b2377845cebe5cf8b5165cb3cc1a5e0fa5cfa3e1f7f55707d8fd82e0a7b7" +dependencies = [ + "der 0.7.8", + "spki 0.7.3", +] + +[[package]] +name = "pkg-config" +version = "0.3.27" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "26072860ba924cbfa98ea39c8c19b4dd6a4a25423dbdf219c1eca91aa0cf6964" + +[[package]] +name = "platforms" +version = "3.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "14e6ab3f592e6fb464fc9712d8d6e6912de6473954635fd76a589d832cffcbb0" + +[[package]] +name = "poly1305" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8159bd90725d2df49889a078b54f4f79e87f1f8a8444194cdca81d38f5393abf" +dependencies = [ + "cpufeatures", + "opaque-debug 0.3.0", + "universal-hash", +] + +[[package]] +name = "polyval" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d52cff9d1d4dee5fe6d03729099f4a310a41179e0a10dbf542039873f2e826fb" +dependencies = [ + "cfg-if 1.0.0", + "cpufeatures", + "opaque-debug 0.3.0", + "universal-hash", +] + +[[package]] +name = "portable-atomic" +version = "1.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3bccab0e7fd7cc19f820a1c8c91720af652d0c88dc9664dd72aef2614f04af3b" + +[[package]] +name = "powerfmt" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "439ee305def115ba05938db6eb1644ff94165c5ab5e9420d1c1bcedbba909391" + +[[package]] +name = "ppv-lite86" +version = "0.2.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b40af805b3121feab8a3c29f04d8ad262fa8e0561883e7653e024ae4479e6de" + +[[package]] +name = "precomputed-hash" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "925383efa346730478fb4838dbe9137d2a47675ad789c546d150a6e1dd4ab31c" + +[[package]] +name = "prettyplease" +version = "0.2.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ae005bd773ab59b4725093fd7df83fd7892f7d8eafb48dbd7de6e024e4215f9d" +dependencies = [ + "proc-macro2 1.0.70", + "syn 2.0.39", +] + +[[package]] +name = "primitive-types" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "05e4722c697a58a99d5d06a08c30821d7c082a4632198de1eaa5a6c22ef42373" +dependencies = [ + "fixed-hash 0.7.0", + "impl-codec 0.5.1", + "impl-rlp", + "impl-serde 0.3.2", + "uint", +] + +[[package]] +name = "primitive-types" +version = "0.12.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b34d9fd68ae0b74a41b21c03c2f62847aa0ffea044eee893b4c140b37e244e2" +dependencies = [ + "fixed-hash 0.8.0", + "impl-codec 0.6.0", + "impl-rlp", + "impl-serde 0.4.0", + "scale-info", + "uint", +] + +[[package]] +name = "proc-macro-crate" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1d6ea3c4595b96363c13943497db34af4460fb474a95c43f4446ad341b8c9785" +dependencies = [ + "toml 0.5.11", +] + +[[package]] +name = "proc-macro-crate" +version = "1.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f4c021e1093a56626774e81216a4ce732a735e5bad4868a03f3ed65ca0c3919" +dependencies = [ + "once_cell", + "toml_edit 0.19.15", +] + +[[package]] +name = "proc-macro-crate" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7e8366a6159044a37876a2b9817124296703c586a5c92e2c53751fa06d8d43e8" +dependencies = [ + "toml_edit 0.20.7", +] + +[[package]] +name = "proc-macro-error" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "da25490ff9892aab3fcf7c36f08cfb902dd3e71ca0f9f9517bea02a73a5ce38c" +dependencies = [ + "proc-macro-error-attr", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", + "version_check", +] + +[[package]] +name = "proc-macro-error-attr" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a1be40180e52ecc98ad80b184934baf3d0d29f979574e439af5a55274b35f869" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "version_check", +] + +[[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-macro2" +version = "0.4.30" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cf3d2011ab5c909338f7887f4fc896d35932e29146c12c8d01da6b22a80ba759" +dependencies = [ + "unicode-xid 0.1.0", +] + +[[package]] +name = "proc-macro2" +version = "1.0.70" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "39278fbbf5fb4f646ce651690877f89d1c5811a3d4acb27700c1cb3cdb78fd3b" +dependencies = [ + "unicode-ident", +] + +[[package]] +name = "prometheus-client" +version = "0.21.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3c99afa9a01501019ac3a14d71d9f94050346f55ca471ce90c799a15c58f61e2" +dependencies = [ + "dtoa", + "itoa", + "parking_lot 0.12.1", + "prometheus-client-derive-encode", +] + +[[package]] +name = "prometheus-client-derive-encode" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "440f724eba9f6996b75d63681b0a92b06947f1457076d503a4d2e2c8f56442b8" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "prometheus_exporter" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "metrics", + "metrics-exporter-prometheus", + "tokio", + "vise", + "vise-exporter", +] + +[[package]] +name = "proptest" +version = "1.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "31b476131c3c86cb68032fdc5cb6d5a1045e3e42d96b69fa599fd77701e1f5bf" +dependencies = [ + "bitflags 2.4.1", + "lazy_static", + "num-traits", + "rand 0.8.5", + "rand_chacha 0.3.1", + "rand_xorshift 0.3.0", + "regex-syntax 0.8.2", + "unarray", +] + +[[package]] +name = "prost" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "146c289cda302b98a28d40c8b3b90498d6e526dd24ac2ecea73e4e491685b94a" +dependencies = [ + "bytes 1.5.0", + "prost-derive", +] + +[[package]] +name = "prost-build" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c55e02e35260070b6f716a2423c2ff1c3bb1642ddca6f99e1f26d06268a0e2d2" +dependencies = [ + "bytes 1.5.0", + "heck 0.4.1", + "itertools 0.11.0", + "log", + "multimap", + "once_cell", + "petgraph", + "prettyplease", + "prost", + "prost-types", + "regex", + "syn 2.0.39", + "tempfile", + "which", +] + +[[package]] +name = "prost-derive" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "efb6c9a1dd1def8e2124d17e83a20af56f1570d6c2d2bd9e266ccb768df3840e" +dependencies = [ + "anyhow", + "itertools 0.11.0", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "prost-reflect" +version = "0.12.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "057237efdb71cf4b3f9396302a3d6599a92fa94063ba537b66130980ea9909f3" +dependencies = [ + "base64 0.21.5", + "logos", + "miette", + "once_cell", + "prost", + "prost-types", + "serde", + "serde-value", +] + +[[package]] +name = "prost-types" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "193898f59edcf43c26227dcd4c8427f00d99d61e95dcde58dabd49fa291d470e" +dependencies = [ + "prost", +] + +[[package]] +name = "protox" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "00bb76c5f6221de491fe2c8f39b106330bbd9762c6511119c07940e10eb9ff11" +dependencies = [ + "bytes 1.5.0", + "miette", + "prost", + "prost-reflect", + "prost-types", + "protox-parse", + "thiserror", +] + +[[package]] +name = "protox-parse" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b4581f441c58863525a3e6bec7b8de98188cf75239a56c725a3e7288450a33f" +dependencies = [ + "logos", + "miette", + "prost-types", + "thiserror", +] + +[[package]] +name = "pulldown-cmark" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77a1a2f1f0a7ecff9c31abbe177637be0e97a0aef46cf8738ece09327985d998" +dependencies = [ + "bitflags 1.3.2", + "memchr", + "unicase", +] + +[[package]] +name = "quanta" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "20afe714292d5e879d8b12740aa223c6a88f118af41870e8b6196e39a02238a8" +dependencies = [ + "crossbeam-utils 0.8.16", + "libc", + "mach", + "once_cell", + "raw-cpuid", + "wasi 0.10.2+wasi-snapshot-preview1", + "web-sys", + "winapi 0.3.9", +] + +[[package]] +name = "quanta" +version = "0.11.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a17e662a7a8291a865152364c20c7abc5e60486ab2001e8ec10b24862de0b9ab" +dependencies = [ + "crossbeam-utils 0.8.16", + "libc", + "mach2", + "once_cell", + "raw-cpuid", + "wasi 0.11.0+wasi-snapshot-preview1", + "web-sys", + "winapi 0.3.9", +] + +[[package]] +name = "quick-protobuf" +version = "0.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9d6da84cc204722a989e01ba2f6e1e276e190f22263d0cb6ce8526fcdb0d2e1f" +dependencies = [ + "byteorder", +] + +[[package]] +name = "quote" +version = "0.6.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6ce23b6b870e8f94f81fb0a363d65d86675884b34a09043c81e5562f11c1f8e1" +dependencies = [ + "proc-macro2 0.4.30", +] + +[[package]] +name = "quote" +version = "1.0.33" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5267fca4496028628a95160fc423a33e8b2e6af8a5302579e322e4b520293cae" +dependencies = [ + "proc-macro2 1.0.70", +] + +[[package]] +name = "radium" +version = "0.6.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "643f8f41a8ebc4c5dc4515c82bb8abd397b527fc20fd681b7c011c2aee5d44fb" + +[[package]] +name = "radium" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dc33ff2d4973d518d823d61aa239014831e521c75da58e3df4840d3f47749d09" + +[[package]] +name = "rand" +version = "0.4.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "552840b97013b1a26992c11eac34bdd778e464601a4c2054b5f0bff7c6761293" +dependencies = [ + "fuchsia-cprng", + "libc", + "rand_core 0.3.1", + "rdrand", + "winapi 0.3.9", +] + +[[package]] +name = "rand" +version = "0.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6d71dacdc3c88c1fde3885a3be3fbab9f35724e6ce99467f7d9c5026132184ca" +dependencies = [ + "autocfg 0.1.8", + "libc", + "rand_chacha 0.1.1", + "rand_core 0.4.2", + "rand_hc 0.1.0", + "rand_isaac", + "rand_jitter", + "rand_os", + "rand_pcg", + "rand_xorshift 0.1.1", + "winapi 0.3.9", +] + +[[package]] +name = "rand" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6a6b1679d49b24bbfe0c803429aa1874472f50d9b363131f0e89fc356b544d03" +dependencies = [ + "getrandom 0.1.16", + "libc", + "rand_chacha 0.2.2", + "rand_core 0.5.1", + "rand_hc 0.2.0", +] + +[[package]] +name = "rand" +version = "0.8.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404" +dependencies = [ + "libc", + "rand_chacha 0.3.1", + "rand_core 0.6.4", +] + +[[package]] +name = "rand_chacha" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "556d3a1ca6600bfcbab7c7c91ccb085ac7fbbcd70e008a98742e7847f4f7bcef" +dependencies = [ + "autocfg 0.1.8", + "rand_core 0.3.1", +] + +[[package]] +name = "rand_chacha" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f4c8ed856279c9737206bf725bf36935d8666ead7aa69b52be55af369d193402" +dependencies = [ + "ppv-lite86", + "rand_core 0.5.1", +] + +[[package]] +name = "rand_chacha" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e6c10a63a0fa32252be49d21e7709d4d4baf8d231c2dbce1eaa8141b9b127d88" +dependencies = [ + "ppv-lite86", + "rand_core 0.6.4", +] + +[[package]] +name = "rand_core" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a6fdeb83b075e8266dcc8762c22776f6877a63111121f5f8c7411e5be7eed4b" +dependencies = [ + "rand_core 0.4.2", +] + +[[package]] +name = "rand_core" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c33a3c44ca05fa6f1807d8e6743f3824e8509beca625669633be0acbdf509dc" + +[[package]] +name = "rand_core" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "90bde5296fc891b0cef12a6d03ddccc162ce7b2aff54160af9338f8d40df6d19" +dependencies = [ + "getrandom 0.1.16", +] + +[[package]] +name = "rand_core" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c" +dependencies = [ + "getrandom 0.2.11", +] + +[[package]] +name = "rand_hc" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b40677c7be09ae76218dc623efbf7b18e34bced3f38883af07bb75630a21bc4" +dependencies = [ + "rand_core 0.3.1", +] + +[[package]] +name = "rand_hc" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ca3129af7b92a17112d59ad498c6f81eaf463253766b90396d39ea7a39d6613c" +dependencies = [ + "rand_core 0.5.1", +] + +[[package]] +name = "rand_isaac" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ded997c9d5f13925be2a6fd7e66bf1872597f759fd9dd93513dd7e92e5a5ee08" +dependencies = [ + "rand_core 0.3.1", +] + +[[package]] +name = "rand_jitter" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1166d5c91dc97b88d1decc3285bb0a99ed84b05cfd0bc2341bdf2d43fc41e39b" +dependencies = [ + "libc", + "rand_core 0.4.2", + "winapi 0.3.9", +] + +[[package]] +name = "rand_os" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b75f676a1e053fc562eafbb47838d67c84801e38fc1ba459e8f180deabd5071" +dependencies = [ + "cloudabi", + "fuchsia-cprng", + "libc", + "rand_core 0.4.2", + "rdrand", + "winapi 0.3.9", +] + +[[package]] +name = "rand_pcg" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "abf9b09b01790cfe0364f52bf32995ea3c39f4d2dd011eac241d2914146d0b44" +dependencies = [ + "autocfg 0.1.8", + "rand_core 0.4.2", +] + +[[package]] +name = "rand_xorshift" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cbf7e9e623549b0e21f6e97cf8ecf247c1a8fd2e8a992ae265314300b2455d5c" +dependencies = [ + "rand_core 0.3.1", +] + +[[package]] +name = "rand_xorshift" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d25bf25ec5ae4a3f1b92f929810509a2f53d7dca2f50b794ff57e3face536c8f" +dependencies = [ + "rand_core 0.6.4", +] + +[[package]] +name = "rand_xoshiro" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6f97cdb2a36ed4183de61b2f824cc45c9f1037f28afe0a322e9fff4c108b5aaa" +dependencies = [ + "rand_core 0.6.4", +] + +[[package]] +name = "raw-cpuid" +version = "10.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c297679cb867470fa8c9f67dbba74a78d78e3e98d7cf2b08d6d71540f797332" +dependencies = [ + "bitflags 1.3.2", +] + +[[package]] +name = "rayon" +version = "1.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c27db03db7734835b3f53954b534c91069375ce6ccaa2e065441e07d9b6cdb1" +dependencies = [ + "either", + "rayon-core", +] + +[[package]] +name = "rayon-core" +version = "1.12.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5ce3fb6ad83f861aac485e76e1985cd109d9a3713802152be56c3b1f0e0658ed" +dependencies = [ + "crossbeam-deque 0.8.3", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "rdrand" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "678054eb77286b51581ba43620cc911abf02758c91f93f479767aed0f90458b2" +dependencies = [ + "rand_core 0.3.1", +] + +[[package]] +name = "redox_syscall" +version = "0.2.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb5a58c1855b4b6819d59012155603f0b22ad30cad752600aadfcb695265519a" +dependencies = [ + "bitflags 1.3.2", +] + +[[package]] +name = "redox_syscall" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4722d768eff46b75989dd134e5c353f0d6296e5aaa3132e776cbdb56be7731aa" +dependencies = [ + "bitflags 1.3.2", +] + +[[package]] +name = "redox_users" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a18479200779601e498ada4e8c1e1f50e3ee19deb0259c25825a98b5603b2cb4" +dependencies = [ + "getrandom 0.2.11", + "libredox", + "thiserror", +] + +[[package]] +name = "regex" +version = "1.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "380b951a9c5e80ddfd6136919eef32310721aa4aacd4889a8d39124b026ab343" +dependencies = [ + "aho-corasick", + "memchr", + "regex-automata 0.4.3", + "regex-syntax 0.8.2", +] + +[[package]] +name = "regex-automata" +version = "0.1.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c230d73fb8d8c1b9c0b3135c5142a8acee3a0558fb8db5cf1cb65f8d7862132" +dependencies = [ + "regex-syntax 0.6.29", +] + +[[package]] +name = "regex-automata" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5f804c7828047e88b2d32e2d7fe5a105da8ee3264f01902f796c8e067dc2483f" +dependencies = [ + "aho-corasick", + "memchr", + "regex-syntax 0.8.2", +] + +[[package]] +name = "regex-syntax" +version = "0.6.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f162c6dd7b008981e4d40210aca20b4bd0f9b60ca9271061b07f78537722f2e1" + +[[package]] +name = "regex-syntax" +version = "0.7.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dbb5fb1acd8a1a18b3dd5be62d25485eb770e05afb408a9627d14d451bae12da" + +[[package]] +name = "regex-syntax" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c08c74e62047bb2de4ff487b251e4a92e24f48745648451635cec7d591162d9f" + +[[package]] +name = "remove_dir_all" +version = "0.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3acd125665422973a33ac9d3dd2df85edad0f4ae9b00dafb1a05e43a9f5ef8e7" +dependencies = [ + "winapi 0.3.9", +] + +[[package]] +name = "reqwest" +version = "0.11.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "046cd98826c46c2ac8ddecae268eb5c2e58628688a5fc7a2643704a73faba95b" +dependencies = [ + "base64 0.21.5", + "bytes 1.5.0", + "encoding_rs", + "futures-core", + "futures-util", + "h2", + "http", + "http-body", + "hyper", + "hyper-rustls", + "hyper-tls", + "ipnet", + "js-sys", + "log", + "mime", + "mime_guess", + "native-tls", + "once_cell", + "percent-encoding", + "pin-project-lite", + "rustls", + "rustls-pemfile", + "serde", + "serde_json", + "serde_urlencoded", + "system-configuration", + "tokio", + "tokio-native-tls", + "tokio-rustls", + "tokio-util 0.7.10", + "tower-service", + "url", + "wasm-bindgen", + "wasm-bindgen-futures", + "wasm-streams", + "web-sys", + "webpki-roots 0.25.3", + "winreg", +] + +[[package]] +name = "rescue_poseidon" +version = "0.4.1" +source = "git+https://github.com/matter-labs/rescue-poseidon.git?branch=poseidon2#c4a788471710bdb7aa0f59e8756b45ef93cdd2b2" +dependencies = [ + "addchain", + "arrayvec 0.7.4", + "blake2 0.10.6 (registry+https://github.com/rust-lang/crates.io-index)", + "byteorder", + "derivative", + "franklin-crypto 0.0.5 (git+https://github.com/matter-labs/franklin-crypto?branch=snark_wrapper)", + "log", + "num-bigint 0.3.3", + "num-integer", + "num-iter", + "num-traits", + "rand 0.4.6", + "serde", + "sha3 0.9.1", + "smallvec", +] + +[[package]] +name = "rescue_poseidon" +version = "0.4.1" +source = "git+https://github.com/matter-labs/rescue-poseidon#d059b5042df5ed80e151f05751410b524a54d16c" +dependencies = [ + "addchain", + "arrayvec 0.7.4", + "blake2 0.10.6 (registry+https://github.com/rust-lang/crates.io-index)", + "byteorder", + "franklin-crypto 0.0.5 (git+https://github.com/matter-labs/franklin-crypto?branch=dev)", + "num-bigint 0.3.3", + "num-integer", + "num-iter", + "num-traits", + "rand 0.4.6", + "serde", + "sha3 0.9.1", + "smallvec", +] + +[[package]] +name = "rfc6979" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7743f17af12fa0b03b803ba12cd6a8d9483a587e89c69445e3909655c0b9fabb" +dependencies = [ + "crypto-bigint 0.4.9", + "hmac 0.12.1", + "zeroize", +] + +[[package]] +name = "rfc6979" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f8dd2a808d456c4a54e300a23e9f5a67e122c3024119acbfd73e3bf664491cb2" +dependencies = [ + "hmac 0.12.1", + "subtle", +] + +[[package]] +name = "ring" +version = "0.16.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3053cf52e236a3ed746dfc745aa9cacf1b791d846bdaf412f60a8d7d6e17c8fc" +dependencies = [ + "cc", + "libc", + "once_cell", + "spin 0.5.2", + "untrusted 0.7.1", + "web-sys", + "winapi 0.3.9", +] + +[[package]] +name = "ring" +version = "0.17.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "684d5e6e18f669ccebf64a92236bb7db9a34f07be010e3627368182027180866" +dependencies = [ + "cc", + "getrandom 0.2.11", + "libc", + "spin 0.9.8", + "untrusted 0.9.0", + "windows-sys 0.48.0", +] + +[[package]] +name = "ripemd" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bd124222d17ad93a644ed9d011a40f4fb64aa54275c08cc216524a9ea82fb09f" +dependencies = [ + "digest 0.10.7", +] + +[[package]] +name = "ripemd160" +version = "0.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2eca4ecc81b7f313189bf73ce724400a07da2a6dac19588b03c8bd76a2dcc251" +dependencies = [ + "block-buffer 0.9.0", + "digest 0.9.0", + "opaque-debug 0.3.0", +] + +[[package]] +name = "rlp" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bb919243f34364b6bd2fc10ef797edbfa75f33c252e7998527479c6d6b47e1ec" +dependencies = [ + "bytes 1.5.0", + "rlp-derive", + "rustc-hex", +] + +[[package]] +name = "rlp-derive" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e33d7b2abe0c340d8797fe2907d3f20d3b5ea5908683618bfe80df7f621f672a" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "rocksdb" +version = "0.21.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bb6f170a4041d50a0ce04b0d2e14916d6ca863ea2e422689a5b694395d299ffe" +dependencies = [ + "libc", + "librocksdb-sys", +] + +[[package]] +name = "rustc-demangle" +version = "0.1.23" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76" + +[[package]] +name = "rustc-hash" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "08d43f7aa6b08d49f382cde6a7982047c3426db949b1424bc4b7ec9ae12c6ce2" + +[[package]] +name = "rustc-hex" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3e75f6a532d0fd9f7f13144f392b6ad56a32696bfcd9c78f797f16bbb6f072d6" + +[[package]] +name = "rustc_version" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366" +dependencies = [ + "semver", +] + +[[package]] +name = "rustix" +version = "0.38.25" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dc99bc2d4f1fed22595588a013687477aedf3cdcfb26558c559edb67b4d9b22e" +dependencies = [ + "bitflags 2.4.1", + "errno", + "libc", + "linux-raw-sys", + "windows-sys 0.48.0", +] + +[[package]] +name = "rustls" +version = "0.21.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "629648aced5775d558af50b2b4c7b02983a04b312126d45eeead26e7caa498b9" +dependencies = [ + "log", + "ring 0.17.6", + "rustls-webpki", + "sct", +] + +[[package]] +name = "rustls-native-certs" +version = "0.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a9aace74cb666635c918e9c12bc0d348266037aa8eb599b5cba565709a8dff00" +dependencies = [ + "openssl-probe", + "rustls-pemfile", + "schannel", + "security-framework", +] + +[[package]] +name = "rustls-pemfile" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1c74cae0a4cf6ccbbf5f359f08efdf8ee7e1dc532573bf0db71968cb56b1448c" +dependencies = [ + "base64 0.21.5", +] + +[[package]] +name = "rustls-webpki" +version = "0.101.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8b6275d1ee7a1cd780b64aca7726599a1dbc893b1e64144529e55c3c2f745765" +dependencies = [ + "ring 0.17.6", + "untrusted 0.9.0", +] + +[[package]] +name = "rustversion" +version = "1.0.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7ffc183a10b4478d04cbbbfc96d0873219d962dd5accaff2ffbd4ceb7df837f4" + +[[package]] +name = "ryu" +version = "1.0.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1ad4cc8da4ef723ed60bced201181d83791ad433213d8c24efffda1eec85d741" + +[[package]] +name = "salsa20" +version = "0.7.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "399f290ffc409596022fce5ea5d4138184be4784f2b28c62c59f0d8389059a15" +dependencies = [ + "cipher 0.2.5", +] + +[[package]] +name = "salsa20" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "97a22f5af31f73a954c10289c93e8a50cc23d971e80ee446f1f6f7137a088213" +dependencies = [ + "cipher 0.4.4", +] + +[[package]] +name = "same-file" +version = "1.0.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "93fc1dc3aaa9bfed95e02e6eadabb4baf7e3078b0bd1b4d7b6b0b68378900502" +dependencies = [ + "winapi-util", +] + +[[package]] +name = "scale-info" +version = "2.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f7d66a1128282b7ef025a8ead62a4a9fcf017382ec53b8ffbf4d7bf77bd3c60" +dependencies = [ + "cfg-if 1.0.0", + "derive_more", + "parity-scale-codec 3.6.9", + "scale-info-derive", +] + +[[package]] +name = "scale-info-derive" +version = "2.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "abf2c68b89cafb3b8d918dd07b42be0da66ff202cf1155c5739a4e0c1ea0dc19" +dependencies = [ + "proc-macro-crate 1.3.1", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "schannel" +version = "0.1.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0c3733bf4cf7ea0880754e19cb5a462007c4a8c1914bff372ccc95b464f1df88" +dependencies = [ + "windows-sys 0.48.0", +] + +[[package]] +name = "scopeguard" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49" + +[[package]] +name = "scrypt" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8da492dab03f925d977776a0b7233d7b934d6dc2b94faead48928e2e9bacedb9" +dependencies = [ + "base64 0.13.1", + "hmac 0.10.1", + "pbkdf2 0.6.0", + "rand 0.7.3", + "rand_core 0.5.1", + "salsa20 0.7.2", + "sha2 0.9.9", + "subtle", +] + +[[package]] +name = "scrypt" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9f9e24d2b632954ded8ab2ef9fea0a0c769ea56ea98bddbafbad22caeeadf45d" +dependencies = [ + "hmac 0.12.1", + "pbkdf2 0.11.0", + "salsa20 0.10.2", + "sha2 0.10.8", +] + +[[package]] +name = "sct" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "da046153aa2352493d6cb7da4b6e5c0c057d8a1d0a9aa8560baffdd945acd414" +dependencies = [ + "ring 0.17.6", + "untrusted 0.9.0", +] + +[[package]] +name = "sec1" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3be24c1842290c45df0a7bf069e0c268a747ad05a192f2fd7dcfdbc1cba40928" +dependencies = [ + "base16ct 0.1.1", + "der 0.6.1", + "generic-array 0.14.7", + "pkcs8 0.9.0", + "subtle", + "zeroize", +] + +[[package]] +name = "sec1" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3e97a565f76233a6003f9f5c54be1d9c5bdfa3eccfb189469f11ec4901c47dc" +dependencies = [ + "base16ct 0.2.0", + "der 0.7.8", + "generic-array 0.14.7", + "pkcs8 0.10.2", + "subtle", + "zeroize", +] + +[[package]] +name = "secp256k1" +version = "0.20.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "97d03ceae636d0fed5bae6a7f4f664354c5f4fcedf6eef053fef17e49f837d0a" +dependencies = [ + "rand 0.6.5", + "secp256k1-sys 0.4.2", +] + +[[package]] +name = "secp256k1" +version = "0.27.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "25996b82292a7a57ed3508f052cfff8640d38d32018784acd714758b43da9c8f" +dependencies = [ + "secp256k1-sys 0.8.1", +] + +[[package]] +name = "secp256k1-sys" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "957da2573cde917463ece3570eab4a0b3f19de6f1646cde62e6fd3868f566036" +dependencies = [ + "cc", +] + +[[package]] +name = "secp256k1-sys" +version = "0.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "70a129b9e9efbfb223753b9163c4ab3b13cff7fd9c7f010fbac25ab4099fa07e" +dependencies = [ + "cc", +] + +[[package]] +name = "security-framework" +version = "2.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "05b64fb303737d99b81884b2c63433e9ae28abebe5eb5045dcdd175dc2ecf4de" +dependencies = [ + "bitflags 1.3.2", + "core-foundation", + "core-foundation-sys", + "libc", + "security-framework-sys", +] + +[[package]] +name = "security-framework-sys" +version = "2.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e932934257d3b408ed8f30db49d85ea163bfe74961f017f405b025af298f0c7a" +dependencies = [ + "core-foundation-sys", + "libc", +] + +[[package]] +name = "semver" +version = "1.0.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "836fa6a3e1e547f9a2c4040802ec865b5d85f4014efe00555d7090a3dcaa1090" +dependencies = [ + "serde", +] + +[[package]] +name = "send_wrapper" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f638d531eccd6e23b980caf34876660d38e265409d8e99b397ab71eb3612fad0" + +[[package]] +name = "send_wrapper" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cd0b0ec5f1c1ca621c432a25813d8d60c88abe6d3e08a3eb9cf37d97a0fe3d73" + +[[package]] +name = "sentry" +version = "0.31.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6ce4b57f1b521f674df7a1d200be8ff5d74e3712020ee25b553146657b5377d5" +dependencies = [ + "httpdate", + "native-tls", + "reqwest", + "sentry-backtrace", + "sentry-contexts", + "sentry-core", + "sentry-debug-images", + "sentry-panic", + "sentry-tracing", + "tokio", + "ureq", +] + +[[package]] +name = "sentry-backtrace" +version = "0.31.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "58cc8d4e04a73de8f718dc703943666d03f25d3e9e4d0fb271ca0b8c76dfa00e" +dependencies = [ + "backtrace", + "once_cell", + "regex", + "sentry-core", +] + +[[package]] +name = "sentry-contexts" +version = "0.31.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6436c1bad22cdeb02179ea8ef116ffc217797c028927def303bc593d9320c0d1" +dependencies = [ + "hostname", + "libc", + "os_info", + "rustc_version", + "sentry-core", + "uname", +] + +[[package]] +name = "sentry-core" +version = "0.31.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "901f761681f97db3db836ef9e094acdd8756c40215326c194201941947164ef1" +dependencies = [ + "once_cell", + "rand 0.8.5", + "sentry-types", + "serde", + "serde_json", +] + +[[package]] +name = "sentry-debug-images" +version = "0.31.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "afdb263e73d22f39946f6022ed455b7561b22ff5553aca9be3c6a047fa39c328" +dependencies = [ + "findshlibs", + "once_cell", + "sentry-core", +] + +[[package]] +name = "sentry-panic" +version = "0.31.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74fbf1c163f8b6a9d05912e1b272afa27c652e8b47ea60cb9a57ad5e481eea99" +dependencies = [ + "sentry-backtrace", + "sentry-core", +] + +[[package]] +name = "sentry-tracing" +version = "0.31.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "82eabcab0a047040befd44599a1da73d3adb228ff53b5ed9795ae04535577704" +dependencies = [ + "sentry-backtrace", + "sentry-core", + "tracing-core", + "tracing-subscriber", +] + +[[package]] +name = "sentry-types" +version = "0.31.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "da956cca56e0101998c8688bc65ce1a96f00673a0e58e663664023d4c7911e82" +dependencies = [ + "debugid", + "hex", + "rand 0.8.5", + "serde", + "serde_json", + "thiserror", + "time", + "url", + "uuid 1.6.1", +] + +[[package]] +name = "seq-macro" +version = "0.3.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a3f0bf26fd526d2a95683cd0f87bf103b8539e2ca1ef48ce002d67aad59aa0b4" + +[[package]] +name = "serde" +version = "1.0.193" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "25dd9975e68d0cb5aa1120c288333fc98731bd1dd12f561e468ea4728c042b89" +dependencies = [ + "serde_derive", +] + +[[package]] +name = "serde-value" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f3a1a3341211875ef120e117ea7fd5228530ae7e7036a779fdc9117be6b3282c" +dependencies = [ + "ordered-float", + "serde", +] + +[[package]] +name = "serde_derive" +version = "1.0.193" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "43576ca501357b9b071ac53cdc7da8ef0cbd9493d8df094cd821777ea6e894d3" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "serde_json" +version = "1.0.108" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3d1c7e3eac408d115102c4c24ad393e0821bb3a5df4d506a80f85f7a742a526b" +dependencies = [ + "itoa", + "ryu", + "serde", +] + +[[package]] +name = "serde_path_to_error" +version = "0.1.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4beec8bce849d58d06238cb50db2e1c417cfeafa4c63f692b15c82b7c80f8335" +dependencies = [ + "itoa", + "serde", +] + +[[package]] +name = "serde_spanned" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "12022b835073e5b11e90a14f86838ceb1c8fb0325b72416845c487ac0fa95e80" +dependencies = [ + "serde", +] + +[[package]] +name = "serde_urlencoded" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3491c14715ca2294c4d6a88f15e84739788c1d030eed8c110436aafdaa2f3fd" +dependencies = [ + "form_urlencoded", + "itoa", + "ryu", + "serde", +] + +[[package]] +name = "serde_with" +version = "1.14.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "678b5a069e50bf00ecd22d0cd8ddf7c236f68581b03db652061ed5eb13a312ff" +dependencies = [ + "base64 0.13.1", + "serde", + "serde_with_macros", +] + +[[package]] +name = "serde_with_macros" +version = "1.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e182d6ec6f05393cc0e5ed1bf81ad6db3a8feedf8ee515ecdd369809bcce8082" +dependencies = [ + "darling", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "sha-1" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f7d94d0bede923b3cea61f3f1ff57ff8cdfd77b400fb8f9998949e0cf04163df" +dependencies = [ + "block-buffer 0.7.3", + "digest 0.8.1", + "fake-simd", + "opaque-debug 0.2.3", +] + +[[package]] +name = "sha-1" +version = "0.9.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "99cd6713db3cf16b6c84e06321e049a9b9f699826e16096d23bbcc44d15d51a6" +dependencies = [ + "block-buffer 0.9.0", + "cfg-if 1.0.0", + "cpufeatures", + "digest 0.9.0", + "opaque-debug 0.3.0", +] + +[[package]] +name = "sha-1" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f5058ada175748e33390e40e872bd0fe59a19f265d0158daa551c5a88a76009c" +dependencies = [ + "cfg-if 1.0.0", + "cpufeatures", + "digest 0.10.7", +] + +[[package]] +name = "sha1" +version = "0.10.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3bf829a2d51ab4a5ddf1352d8470c140cadc8301b2ae1789db023f01cedd6ba" +dependencies = [ + "cfg-if 1.0.0", + "cpufeatures", + "digest 0.10.7", +] + +[[package]] +name = "sha2" +version = "0.9.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4d58a1e1bf39749807d89cf2d98ac2dfa0ff1cb3faa38fbb64dd88ac8013d800" +dependencies = [ + "block-buffer 0.9.0", + "cfg-if 1.0.0", + "cpufeatures", + "digest 0.9.0", + "opaque-debug 0.3.0", +] + +[[package]] +name = "sha2" +version = "0.10.6" +source = "git+https://github.com/RustCrypto/hashes.git?rev=1731ced4a116d61ba9dc6ee6d0f38fb8102e357a#1731ced4a116d61ba9dc6ee6d0f38fb8102e357a" +dependencies = [ + "cfg-if 1.0.0", + "cpufeatures", + "digest 0.10.7", +] + +[[package]] +name = "sha2" +version = "0.10.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "793db75ad2bcafc3ffa7c68b215fee268f537982cd901d132f89c6343f3a3dc8" +dependencies = [ + "cfg-if 1.0.0", + "cpufeatures", + "digest 0.10.7", +] + +[[package]] +name = "sha3" +version = "0.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f81199417d4e5de3f04b1e871023acea7389672c4135918f05aa9cbf2f2fa809" +dependencies = [ + "block-buffer 0.9.0", + "digest 0.9.0", + "keccak", + "opaque-debug 0.3.0", +] + +[[package]] +name = "sha3" +version = "0.10.6" +source = "git+https://github.com/RustCrypto/hashes.git?rev=7a187e934c1f6c68e4b4e5cf37541b7a0d64d303#7a187e934c1f6c68e4b4e5cf37541b7a0d64d303" +dependencies = [ + "digest 0.10.7", + "keccak", +] + +[[package]] +name = "sha3" +version = "0.10.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "75872d278a8f37ef87fa0ddbda7802605cb18344497949862c0d4dcb291eba60" +dependencies = [ + "digest 0.10.7", + "keccak", +] + +[[package]] +name = "sharded-slab" +version = "0.1.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f40ca3c46823713e0d4209592e8d6e826aa57e928f09752619fc696c499637f6" +dependencies = [ + "lazy_static", +] + +[[package]] +name = "shlex" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a7cee0529a6d40f580e7a5e6c495c8fbfe21b7b52795ed4bb5e62cdf92bc6380" + +[[package]] +name = "signal-hook-registry" +version = "1.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d8229b473baa5980ac72ef434c4415e70c4b5e71b423043adb4ba059f89c99a1" +dependencies = [ + "libc", +] + +[[package]] +name = "signature" +version = "1.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74233d3b3b2f6d4b006dc19dee745e73e2a6bfb6f93607cd3b02bd5b00797d7c" +dependencies = [ + "digest 0.10.7", + "rand_core 0.6.4", +] + +[[package]] +name = "signature" +version = "2.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77549399552de45a898a580c1b41d445bf730df867cc44e6c0233bbc4b8329de" +dependencies = [ + "digest 0.10.7", + "rand_core 0.6.4", +] + +[[package]] +name = "simple_asn1" +version = "0.6.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "adc4e5204eb1910f40f9cfa375f6f05b68c3abac4b6fd879c8ff5e7ae8a0a085" +dependencies = [ + "num-bigint 0.4.4", + "num-traits", + "thiserror", + "time", +] + +[[package]] +name = "siphasher" +version = "0.3.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "38b58827f4464d87d377d175e90bf58eb00fd8716ff0a62f80356b5e61555d0d" + +[[package]] +name = "sized-chunks" +version = "0.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "16d69225bde7a69b235da73377861095455d298f2b970996eec25ddbb42b3d1e" +dependencies = [ + "bitmaps", + "typenum", +] + +[[package]] +name = "skeptic" +version = "0.13.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "16d23b015676c90a0f01c197bfdc786c20342c73a0afdda9025adb0bc42940a8" +dependencies = [ + "bytecount", + "cargo_metadata 0.14.2", + "error-chain", + "glob", + "pulldown-cmark", + "tempfile", + "walkdir", +] + +[[package]] +name = "sketches-ddsketch" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "68a406c1882ed7f29cd5e248c9848a80e7cb6ae0fea82346d2746f2f941c07e1" + +[[package]] +name = "slab" +version = "0.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f92a496fb766b417c996b9c5e57daf2f7ad3b0bebe1ccfca4856390e3d3bb67" +dependencies = [ + "autocfg 1.1.0", +] + +[[package]] +name = "smallvec" +version = "1.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4dccd0940a2dcdf68d092b8cbab7dc0ad8fa938bf95787e1b916b0e3d0e8e970" +dependencies = [ + "serde", +] + +[[package]] +name = "snark_wrapper" +version = "0.1.0" +source = "git+https://github.com/matter-labs/snark-wrapper.git?branch=main#42661a9ff9d00853441589679c101f71e3785f55" +dependencies = [ + "derivative", + "rand 0.4.6", + "rescue_poseidon 0.4.1 (git+https://github.com/matter-labs/rescue-poseidon.git?branch=poseidon2)", +] + +[[package]] +name = "snow" +version = "0.9.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "58021967fd0a5eeeb23b08df6cc244a4d4a5b4aec1d27c9e02fad1a58b4cd74e" +dependencies = [ + "aes-gcm", + "blake2 0.10.6 (registry+https://github.com/rust-lang/crates.io-index)", + "chacha20poly1305", + "curve25519-dalek", + "rand_core 0.6.4", + "rustc_version", + "sha2 0.10.8", + "subtle", +] + +[[package]] +name = "socket2" +version = "0.4.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9f7916fc008ca5542385b89a3d3ce689953c143e9304a9bf8beec1de48994c0d" +dependencies = [ + "libc", + "winapi 0.3.9", +] + +[[package]] +name = "socket2" +version = "0.5.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b5fac59a5cb5dd637972e5fca70daf0523c9067fcdc4842f053dae04a18f8e9" +dependencies = [ + "libc", + "windows-sys 0.48.0", +] + +[[package]] +name = "soketto" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "41d1c5305e39e09653383c2c7244f2f78b3bcae37cf50c64cb4789c9f5096ec2" +dependencies = [ + "base64 0.13.1", + "bytes 1.5.0", + "futures 0.3.29", + "http", + "httparse", + "log", + "rand 0.8.5", + "sha-1 0.9.8", +] + +[[package]] +name = "solang-parser" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c425ce1c59f4b154717592f0bdf4715c3a1d55058883622d3157e1f0908a5b26" +dependencies = [ + "itertools 0.11.0", + "lalrpop", + "lalrpop-util", + "phf", + "thiserror", + "unicode-xid 0.2.4", +] + +[[package]] +name = "spin" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6e63cff320ae2c57904679ba7cb63280a3dc4613885beafb148ee7bf9aa9042d" + +[[package]] +name = "spin" +version = "0.9.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67" + +[[package]] +name = "spki" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "67cf02bbac7a337dc36e4f5a693db6c21e7863f45070f7064577eb4367a3212b" +dependencies = [ + "base64ct", + "der 0.6.1", +] + +[[package]] +name = "spki" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d91ed6c858b01f942cd56b37a94b3e0a1798290327d1236e4d9cf4eaca44d29d" +dependencies = [ + "base64ct", + "der 0.7.8", +] + +[[package]] +name = "splitmut" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c85070f382340e8b23a75808e83573ddf65f9ad9143df9573ca37c1ed2ee956a" + +[[package]] +name = "sqlformat" +version = "0.1.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4b7922be017ee70900be125523f38bdd644f4f06a1b16e8fa5a8ee8c34bffd4" +dependencies = [ + "itertools 0.10.5", + "nom", + "unicode_categories", +] + +[[package]] +name = "sqlx" +version = "0.5.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "551873805652ba0d912fec5bbb0f8b4cdd96baf8e2ebf5970e5671092966019b" +dependencies = [ + "sqlx-core", + "sqlx-macros", +] + +[[package]] +name = "sqlx-core" +version = "0.5.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e48c61941ccf5ddcada342cd59e3e5173b007c509e1e8e990dafc830294d9dc5" +dependencies = [ + "ahash 0.7.7", + "atoi", + "base64 0.13.1", + "bigdecimal", + "bitflags 1.3.2", + "byteorder", + "bytes 1.5.0", + "chrono", + "crc", + "crossbeam-queue 0.3.8", + "dirs 4.0.0", + "either", + "event-listener", + "futures-channel", + "futures-core", + "futures-intrusive", + "futures-util", + "hashlink", + "hex", + "hkdf", + "hmac 0.12.1", + "indexmap 1.9.3", + "ipnetwork", + "itoa", + "libc", + "log", + "md-5", + "memchr", + "num-bigint 0.3.3", + "once_cell", + "paste", + "percent-encoding", + "rand 0.8.5", + "serde", + "serde_json", + "sha-1 0.10.1", + "sha2 0.10.8", + "smallvec", + "sqlformat", + "sqlx-rt", + "stringprep", + "thiserror", + "tokio-stream", + "url", + "whoami", +] + +[[package]] +name = "sqlx-macros" +version = "0.5.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bc0fba2b0cae21fc00fe6046f8baa4c7fcb49e379f0f592b04696607f69ed2e1" +dependencies = [ + "dotenv", + "either", + "heck 0.4.1", + "hex", + "once_cell", + "proc-macro2 1.0.70", + "quote 1.0.33", + "serde", + "serde_json", + "sha2 0.10.8", + "sqlx-core", + "sqlx-rt", + "syn 1.0.109", + "url", +] + +[[package]] +name = "sqlx-rt" +version = "0.5.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4db708cd3e459078f85f39f96a00960bd841f66ee2a669e90bf36907f5a79aae" +dependencies = [ + "native-tls", + "once_cell", + "tokio", + "tokio-native-tls", +] + +[[package]] +name = "stable_deref_trait" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3" + +[[package]] +name = "static_assertions" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a2eb9349b6444b326872e140eb1cf5e7c522154d69e7a0ffb0fb81c06b37543f" + +[[package]] +name = "string_cache" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f91138e76242f575eb1d3b38b4f1362f10d3a43f47d182a5b359af488a02293b" +dependencies = [ + "new_debug_unreachable", + "once_cell", + "parking_lot 0.12.1", + "phf_shared 0.10.0", + "precomputed-hash", +] + +[[package]] +name = "stringprep" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bb41d74e231a107a1b4ee36bd1214b11285b77768d2e3824aedafa988fd36ee6" +dependencies = [ + "finl_unicode", + "unicode-bidi", + "unicode-normalization", +] + +[[package]] +name = "strsim" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8ea5119cdb4c55b55d432abb513a0429384878c15dde60cc77b1c99de1a95a6a" + +[[package]] +name = "strsim" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623" + +[[package]] +name = "structopt" +version = "0.3.26" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0c6b5c64445ba8094a6ab0c3cd2ad323e07171012d9c98b0b15651daf1787a10" +dependencies = [ + "clap 2.34.0", + "lazy_static", + "structopt-derive", +] + +[[package]] +name = "structopt-derive" +version = "0.4.18" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dcb5ae327f9cc13b68763b5749770cb9e048a99bd9dfdfa58d0cf05d5f64afe0" +dependencies = [ + "heck 0.3.3", + "proc-macro-error", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "strum" +version = "0.24.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "063e6045c0e62079840579a7e47a355ae92f60eb74daaf156fb1e84ba164e63f" +dependencies = [ + "strum_macros 0.24.3", +] + +[[package]] +name = "strum" +version = "0.25.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "290d54ea6f91c969195bdbcd7442c8c2a2ba87da8bf60a7ee86a235d4bc1e125" +dependencies = [ + "strum_macros 0.25.3", +] + +[[package]] +name = "strum_macros" +version = "0.24.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1e385be0d24f186b4ce2f9982191e7101bb737312ad61c1f2f984f34bcf85d59" +dependencies = [ + "heck 0.4.1", + "proc-macro2 1.0.70", + "quote 1.0.33", + "rustversion", + "syn 1.0.109", +] + +[[package]] +name = "strum_macros" +version = "0.25.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23dc1fa9ac9c169a78ba62f0b841814b7abae11bdd047b9c58f893439e309ea0" +dependencies = [ + "heck 0.4.1", + "proc-macro2 1.0.70", + "quote 1.0.33", + "rustversion", + "syn 2.0.39", +] + +[[package]] +name = "subtle" +version = "2.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6bdef32e8150c2a081110b42772ffe7d7c9032b606bc226c8260fd97e0976601" + +[[package]] +name = "svm-rs" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "20689c7d03b6461b502d0b95d6c24874c7d24dea2688af80486a130a06af3b07" +dependencies = [ + "dirs 5.0.1", + "fs2", + "hex", + "once_cell", + "reqwest", + "semver", + "serde", + "serde_json", + "sha2 0.10.8", + "thiserror", + "url", + "zip", +] + +[[package]] +name = "syn" +version = "0.15.44" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9ca4b3b69a77cbe1ffc9e198781b7acb0c7365a883670e8f1c1bc66fba79a5c5" +dependencies = [ + "proc-macro2 0.4.30", + "quote 0.6.13", + "unicode-xid 0.1.0", +] + +[[package]] +name = "syn" +version = "1.0.109" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "unicode-ident", +] + +[[package]] +name = "syn" +version = "2.0.39" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23e78b90f2fcf45d3e842032ce32e3f2d1545ba6636271dcbf24fa306d87be7a" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "unicode-ident", +] + +[[package]] +name = "sync_vm" +version = "1.3.3" +source = "git+https://github.com/matter-labs/era-sync_vm.git?branch=v1.3.3#ed8ab8984cae05d00d9d62196753c8d40df47c7d" +dependencies = [ + "arrayvec 0.7.4", + "cs_derive 0.1.0 (git+https://github.com/matter-labs/era-sync_vm.git?branch=v1.3.3)", + "derivative", + "franklin-crypto 0.0.5 (git+https://github.com/matter-labs/franklin-crypto?branch=dev)", + "hex", + "itertools 0.10.5", + "num-bigint 0.4.4", + "num-derive 0.3.3", + "num-integer", + "num-traits", + "once_cell", + "rand 0.4.6", + "rescue_poseidon 0.4.1 (git+https://github.com/matter-labs/rescue-poseidon)", + "serde", + "smallvec", + "zk_evm 1.3.3 (git+https://github.com/matter-labs/era-zk_evm.git?branch=v1.3.3)", +] + +[[package]] +name = "sync_wrapper" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2047c6ded9c721764247e62cd3b03c09ffc529b2ba5b10ec482ae507a4a70160" + +[[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", +] + +[[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", +] + +[[package]] +name = "tagptr" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b2093cf4c8eb1e67749a6762251bc9cd836b6fc171623bd0a9d324d37af2417" + +[[package]] +name = "tap" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "55937e1799185b12863d447f42597ed69d9928686b8d88a1df17376a097d8369" + +[[package]] +name = "tempdir" +version = "0.3.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "15f2b5fb00ccdf689e0149d1b1b3c03fead81c2b37735d812fa8bddbbf41b6d8" +dependencies = [ + "rand 0.4.6", + "remove_dir_all", +] + +[[package]] +name = "tempfile" +version = "3.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7ef1adac450ad7f4b3c28589471ade84f25f731a7a0fe30d71dfa9f60fd808e5" +dependencies = [ + "cfg-if 1.0.0", + "fastrand 2.0.1", + "redox_syscall 0.4.1", + "rustix", + "windows-sys 0.48.0", +] + +[[package]] +name = "term" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c59df8ac95d96ff9bede18eb7300b0fda5e5d8d90960e76f8e14ae765eedbf1f" +dependencies = [ + "dirs-next", + "rustversion", + "winapi 0.3.9", +] + +[[package]] +name = "termcolor" +version = "1.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ff1bc3d3f05aff0403e8ac0d92ced918ec05b666a43f83297ccef5bea8a3d449" +dependencies = [ + "winapi-util", +] + +[[package]] +name = "test-log" +version = "0.2.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f66edd6b6cd810743c0c71e1d085e92b01ce6a72782032e3f794c8284fe4bcdd" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "textwrap" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d326610f408c7a4eb6f51c37c330e496b08506c9457c9d34287ecc38809fb060" +dependencies = [ + "unicode-width", +] + +[[package]] +name = "thiserror" +version = "1.0.50" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f9a7210f5c9a7156bb50aa36aed4c95afb51df0df00713949448cf9e97d382d2" +dependencies = [ + "thiserror-impl", +] + +[[package]] +name = "thiserror-impl" +version = "1.0.50" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "266b2e40bc00e5a6c09c3584011e08b06f123c00362c92b975ba9843aaaa14b8" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "thread_local" +version = "1.1.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3fdd6f064ccff2d6567adcb3873ca630700f00b5ad3f060c25b5dcfd9a4ce152" +dependencies = [ + "cfg-if 1.0.0", + "once_cell", +] + +[[package]] +name = "threadpool" +version = "1.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d050e60b33d41c19108b32cea32164033a9013fe3b46cbd4457559bfbf77afaa" +dependencies = [ + "num_cpus", +] + +[[package]] +name = "time" +version = "0.3.30" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c4a34ab300f2dee6e562c10a046fc05e358b29f9bf92277f30c3c8d82275f6f5" +dependencies = [ + "deranged", + "itoa", + "libc", + "num_threads", + "powerfmt", + "serde", + "time-core", + "time-macros", +] + +[[package]] +name = "time-core" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ef927ca75afb808a4d64dd374f00a2adf8d0fcff8e7b184af886c3c87ec4a3f3" + +[[package]] +name = "time-macros" +version = "0.2.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4ad70d68dba9e1f8aceda7aa6711965dfec1cac869f311a51bd08b3a2ccbce20" +dependencies = [ + "time-core", +] + +[[package]] +name = "tiny-keccak" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1d8a021c69bb74a44ccedb824a046447e2c84a01df9e5c20779750acb38e11b2" +dependencies = [ + "crunchy", +] + +[[package]] +name = "tiny-keccak" +version = "2.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2c9d3793400a45f954c52e73d068316d76b6f4e36977e3fcebb13a2721e80237" +dependencies = [ + "crunchy", +] + +[[package]] +name = "tinyvec" +version = "1.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "87cc5ceb3875bb20c2890005a4e226a4651264a5c75edb2421b52861a0a0cb50" +dependencies = [ + "tinyvec_macros", +] + +[[package]] +name = "tinyvec_macros" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" + +[[package]] +name = "tokio" +version = "1.34.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d0c014766411e834f7af5b8f4cf46257aab4036ca95e9d2c144a10f59ad6f5b9" +dependencies = [ + "backtrace", + "bytes 1.5.0", + "libc", + "mio 0.8.9", + "num_cpus", + "parking_lot 0.12.1", + "pin-project-lite", + "signal-hook-registry", + "socket2 0.5.5", + "tokio-macros", + "windows-sys 0.48.0", +] + +[[package]] +name = "tokio-macros" +version = "2.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b8a1e28f2deaa14e508979454cb3a223b10b938b45af148bc0986de36f1923b" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "tokio-native-tls" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bbae76ab933c85776efabc971569dd6119c580d8f5d448769dec1764bf796ef2" +dependencies = [ + "native-tls", + "tokio", +] + +[[package]] +name = "tokio-rustls" +version = "0.24.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c28327cf380ac148141087fbfb9de9d7bd4e84ab5d2c28fbc911d753de8a7081" +dependencies = [ + "rustls", + "tokio", +] + +[[package]] +name = "tokio-stream" +version = "0.1.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "397c988d37662c7dda6d2208364a706264bf3d6138b11d436cbac0ad38832842" +dependencies = [ + "futures-core", + "pin-project-lite", + "tokio", +] + +[[package]] +name = "tokio-tungstenite" +version = "0.20.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "212d5dcb2a1ce06d81107c3d0ffa3121fe974b73f068c8282cb1c32328113b6c" +dependencies = [ + "futures-util", + "log", + "rustls", + "tokio", + "tokio-rustls", + "tungstenite", + "webpki-roots 0.25.3", +] + +[[package]] +name = "tokio-util" +version = "0.6.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "36943ee01a6d67977dd3f84a5a1d2efeb4ada3a1ae771cadfaa535d9d9fc6507" +dependencies = [ + "bytes 1.5.0", + "futures-core", + "futures-sink", + "log", + "pin-project-lite", + "tokio", +] + +[[package]] +name = "tokio-util" +version = "0.7.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5419f34732d9eb6ee4c3578b7989078579b7f039cbbb9ca2c4da015749371e15" +dependencies = [ + "bytes 1.5.0", + "futures-core", + "futures-io", + "futures-sink", + "pin-project-lite", + "tokio", + "tracing", +] + +[[package]] +name = "toml" +version = "0.5.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f4f7f0dd8d50a853a531c426359045b1998f04219d88799810762cd4ad314234" +dependencies = [ + "serde", +] + +[[package]] +name = "toml" +version = "0.8.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a1a195ec8c9da26928f773888e0742ca3ca1040c6cd859c919c9f59c1954ab35" +dependencies = [ + "serde", + "serde_spanned", + "toml_datetime", + "toml_edit 0.21.0", +] + +[[package]] +name = "toml_datetime" +version = "0.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3550f4e9685620ac18a50ed434eb3aec30db8ba93b0287467bca5826ea25baf1" +dependencies = [ + "serde", +] + +[[package]] +name = "toml_edit" +version = "0.14.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5376256e44f2443f8896ac012507c19a012df0fe8758b55246ae51a2279db51f" +dependencies = [ + "combine", + "indexmap 1.9.3", + "itertools 0.10.5", +] + +[[package]] +name = "toml_edit" +version = "0.19.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1b5bb770da30e5cbfde35a2d7b9b8a2c4b8ef89548a7a6aeab5c9a576e3e7421" +dependencies = [ + "indexmap 2.1.0", + "toml_datetime", + "winnow", +] + +[[package]] +name = "toml_edit" +version = "0.20.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "70f427fce4d84c72b5b732388bf4a9f4531b53f74e2887e3ecb2481f68f66d81" +dependencies = [ + "indexmap 2.1.0", + "toml_datetime", + "winnow", +] + +[[package]] +name = "toml_edit" +version = "0.21.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d34d383cd00a163b4a5b85053df514d45bc330f6de7737edfe0a93311d1eaa03" +dependencies = [ + "indexmap 2.1.0", + "serde", + "serde_spanned", + "toml_datetime", + "winnow", +] + +[[package]] +name = "tower" +version = "0.4.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b8fa9be0de6cf49e536ce1851f987bd21a43b771b09473c3549a6c853db37c1c" +dependencies = [ + "futures-core", + "futures-util", + "hdrhistogram", + "indexmap 1.9.3", + "pin-project", + "pin-project-lite", + "rand 0.8.5", + "slab", + "tokio", + "tokio-util 0.7.10", + "tower-layer", + "tower-service", + "tracing", +] + +[[package]] +name = "tower-http" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "61c5bb1d698276a2443e5ecfabc1008bf15a36c12e6a7176e7bf089ea9131140" +dependencies = [ + "async-compression", + "base64 0.21.5", + "bitflags 2.4.1", + "bytes 1.5.0", + "futures-core", + "futures-util", + "http", + "http-body", + "http-range-header", + "httpdate", + "iri-string", + "mime", + "mime_guess", + "percent-encoding", + "pin-project-lite", + "tokio", + "tokio-util 0.7.10", + "tower", + "tower-layer", + "tower-service", + "tracing", + "uuid 1.6.1", +] + +[[package]] +name = "tower-layer" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c20c8dbed6283a09604c3e69b4b7eeb54e298b8a600d4d5ecb5ad39de609f1d0" + +[[package]] +name = "tower-service" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b6bc1c9ce2b5135ac7f93c72918fc37feb872bdc6a5533a8b85eb4b86bfdae52" + +[[package]] +name = "tracing" +version = "0.1.40" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c3523ab5a71916ccf420eebdf5521fcef02141234bbc0b8a49f2fdc4544364ef" +dependencies = [ + "log", + "pin-project-lite", + "tracing-attributes", + "tracing-core", +] + +[[package]] +name = "tracing-attributes" +version = "0.1.27" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "34704c8d6ebcbc939824180af020566b01a7c01f80641264eba0999f6c2b6be7" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "tracing-core" +version = "0.1.32" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c06d3da6113f116aaee68e4d601191614c9053067f9ab7f6edbcb161237daa54" +dependencies = [ + "once_cell", + "valuable", +] + +[[package]] +name = "tracing-futures" +version = "0.2.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "97d095ae15e245a057c8e8451bab9b3ee1e1f68e9ba2b4fbc18d0ac5237835f2" +dependencies = [ + "pin-project", + "tracing", +] + +[[package]] +name = "tracing-log" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ee855f1f400bd0e5c02d150ae5de3840039a3f54b025156404e34c23c03f47c3" +dependencies = [ + "log", + "once_cell", + "tracing-core", +] + +[[package]] +name = "tracing-serde" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bc6b213177105856957181934e4920de57730fc69bf42c37ee5bb664d406d9e1" +dependencies = [ + "serde", + "tracing-core", +] + +[[package]] +name = "tracing-subscriber" +version = "0.3.18" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ad0f048c97dbd9faa9b7df56362b8ebcaa52adb06b498c050d2f4e32f90a7a8b" +dependencies = [ + "matchers", + "nu-ansi-term", + "once_cell", + "regex", + "serde", + "serde_json", + "sharded-slab", + "smallvec", + "thread_local", + "time", + "tracing", + "tracing-core", + "tracing-log", + "tracing-serde", +] + +[[package]] +name = "triomphe" +version = "0.1.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "859eb650cfee7434994602c3a68b25d77ad9e68c8a6cd491616ef86661382eb3" + +[[package]] +name = "try-lock" +version = "0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3528ecfd12c466c6f163363caf2d02a71161dd5e1cc6ae7b34207ea2d42d81ed" + +[[package]] +name = "tungstenite" +version = "0.20.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9e3dac10fd62eaf6617d3a904ae222845979aec67c615d1c842b4002c7666fb9" +dependencies = [ + "byteorder", + "bytes 1.5.0", + "data-encoding", + "http", + "httparse", + "log", + "rand 0.8.5", + "rustls", + "sha1", + "thiserror", + "url", + "utf-8", +] + +[[package]] +name = "typenum" +version = "1.17.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "42ff0bf0c66b8238c6f3b578df37d0b7848e55df8577b3f74f92a69acceeb825" + +[[package]] +name = "ucd-trie" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ed646292ffc8188ef8ea4d1e0e0150fb15a5c2e12ad9b8fc191ae7a8a7f3c4b9" + +[[package]] +name = "uint" +version = "0.9.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "76f64bba2c53b04fcab63c01a7d7427eadc821e3bc48c34dc9ba29c501164b52" +dependencies = [ + "byteorder", + "crunchy", + "hex", + "static_assertions", +] + +[[package]] +name = "uname" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b72f89f0ca32e4db1c04e2a72f5345d59796d4866a1ee0609084569f73683dc8" +dependencies = [ + "libc", +] + +[[package]] +name = "unarray" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eaea85b334db583fe3274d12b4cd1880032beab409c0d774be044d4480ab9a94" + +[[package]] +name = "unicase" +version = "2.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f7d2d4dafb69621809a81864c9c1b864479e1235c0dd4e199924b9742439ed89" +dependencies = [ + "version_check", +] + +[[package]] +name = "unicode-bidi" +version = "0.3.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "92888ba5573ff080736b3648696b70cafad7d250551175acbaa4e0385b3e1460" + +[[package]] +name = "unicode-ident" +version = "1.0.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b" + +[[package]] +name = "unicode-normalization" +version = "0.1.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c5713f0fc4b5db668a2ac63cdb7bb4469d8c9fed047b1d0292cc7b0ce2ba921" +dependencies = [ + "tinyvec", +] + +[[package]] +name = "unicode-segmentation" +version = "1.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1dd624098567895118886609431a7c3b8f516e41d30e0643f03d94592a147e36" + +[[package]] +name = "unicode-width" +version = "0.1.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e51733f11c9c4f72aa0c160008246859e340b00807569a0da0e7a1079b27ba85" + +[[package]] +name = "unicode-xid" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +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" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "39ec24b3121d976906ece63c9daad25b85969647682eee313cb5779fdd69e14e" + +[[package]] +name = "universal-hash" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fc1de2c688dc15305988b563c3854064043356019f97a4b46276fe734c4f07ea" +dependencies = [ + "crypto-common", + "subtle", +] + +[[package]] +name = "unroll" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5ad948c1cb799b1a70f836077721a92a35ac177d4daddf4c20a633786d4cf618" +dependencies = [ + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "untrusted" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a156c684c91ea7d62626509bce3cb4e1d9ed5c4d978f7b4352658f96a4c26b4a" + +[[package]] +name = "untrusted" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8ecb6da28b8a351d773b68d5825ac39017e680750f980f3a1a85cd8dd28a47c1" + +[[package]] +name = "ureq" +version = "2.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f8cdd25c339e200129fe4de81451814e5228c9b771d57378817d6117cc2b3f97" +dependencies = [ + "base64 0.21.5", + "log", + "native-tls", + "once_cell", + "url", +] + +[[package]] +name = "url" +version = "2.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "31e6302e3bb753d46e83516cae55ae196fc0c309407cf11ab35cc51a4c2a4633" +dependencies = [ + "form_urlencoded", + "idna 0.5.0", + "percent-encoding", + "serde", +] + +[[package]] +name = "urlencoding" +version = "2.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "daf8dba3b7eb870caf1ddeed7bc9d2a049f3cfdfae7cb521b087cc33ae4c49da" + +[[package]] +name = "utf-8" +version = "0.7.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "09cc8ee72d2a9becf2f2febe0205bbed8fc6615b7cb429ad062dc7b7ddd036a9" + +[[package]] +name = "utf8parse" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a" + +[[package]] +name = "uuid" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bc5cf98d8186244414c848017f0e2676b3fcb46807f6668a97dfe67359a3c4b7" +dependencies = [ + "getrandom 0.2.11", + "serde", +] + +[[package]] +name = "uuid" +version = "1.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5e395fcf16a7a3d8127ec99782007af141946b4795001f876d54fb0d55978560" +dependencies = [ + "getrandom 0.2.11", + "serde", +] + +[[package]] +name = "valuable" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "830b7e5d4d90034032940e4ace0d9a9a057e7a45cd94e6c007832e39edb82f6d" + +[[package]] +name = "vcpkg" +version = "0.2.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426" + +[[package]] +name = "vec_map" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1bddf1187be692e79c5ffeab891132dfb0f236ed36a43c7ed39f1165ee20191" + +[[package]] +name = "version_check" +version = "0.9.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" + +[[package]] +name = "vise" +version = "0.1.0" +source = "git+https://github.com/matter-labs/vise.git?rev=dd05139b76ab0843443ab3ff730174942c825dae#dd05139b76ab0843443ab3ff730174942c825dae" +dependencies = [ + "elsa", + "linkme", + "once_cell", + "prometheus-client", + "vise-macros", +] + +[[package]] +name = "vise-exporter" +version = "0.1.0" +source = "git+https://github.com/matter-labs/vise.git?rev=dd05139b76ab0843443ab3ff730174942c825dae#dd05139b76ab0843443ab3ff730174942c825dae" +dependencies = [ + "hyper", + "metrics-exporter-prometheus", + "once_cell", + "tokio", + "tracing", + "vise", +] + +[[package]] +name = "vise-macros" +version = "0.1.0" +source = "git+https://github.com/matter-labs/vise.git?rev=dd05139b76ab0843443ab3ff730174942c825dae#dd05139b76ab0843443ab3ff730174942c825dae" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "vlog" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "chrono", + "sentry", + "serde_json", + "tracing", + "tracing-subscriber", +] + +[[package]] +name = "walkdir" +version = "2.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d71d857dc86794ca4c280d616f7da00d2dbfd8cd788846559a6813e6aa4b54ee" +dependencies = [ + "same-file", + "winapi-util", +] + +[[package]] +name = "want" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfa7760aed19e106de2c7c0b581b509f2f25d3dacaf737cb82ac61bc6d760b0e" +dependencies = [ + "try-lock", +] + +[[package]] +name = "wasi" +version = "0.9.0+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cccddf32554fecc6acb585f82a32a72e28b48f8c4c1883ddfeeeaa96f7d8e519" + +[[package]] +name = "wasi" +version = "0.10.2+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fd6fbd9a79829dd1ad0cc20627bf1ed606756a7f77edff7b66b7064f9cb327c6" + +[[package]] +name = "wasi" +version = "0.11.0+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" + +[[package]] +name = "wasm-bindgen" +version = "0.2.89" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0ed0d4f68a3015cc185aff4db9506a015f4b96f95303897bfa23f846db54064e" +dependencies = [ + "cfg-if 1.0.0", + "wasm-bindgen-macro", +] + +[[package]] +name = "wasm-bindgen-backend" +version = "0.2.89" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1b56f625e64f3a1084ded111c4d5f477df9f8c92df113852fa5a374dbda78826" +dependencies = [ + "bumpalo", + "log", + "once_cell", + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", + "wasm-bindgen-shared", +] + +[[package]] +name = "wasm-bindgen-futures" +version = "0.4.39" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac36a15a220124ac510204aec1c3e5db8a22ab06fd6706d881dc6149f8ed9a12" +dependencies = [ + "cfg-if 1.0.0", + "js-sys", + "wasm-bindgen", + "web-sys", +] + +[[package]] +name = "wasm-bindgen-macro" +version = "0.2.89" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0162dbf37223cd2afce98f3d0785506dcb8d266223983e4b5b525859e6e182b2" +dependencies = [ + "quote 1.0.33", + "wasm-bindgen-macro-support", +] + +[[package]] +name = "wasm-bindgen-macro-support" +version = "0.2.89" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f0eb82fcb7930ae6219a7ecfd55b217f5f0893484b7a13022ebb2b2bf20b5283" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", + "wasm-bindgen-backend", + "wasm-bindgen-shared", +] + +[[package]] +name = "wasm-bindgen-shared" +version = "0.2.89" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7ab9b36309365056cd639da3134bf87fa8f3d86008abf99e612384a6eecd459f" + +[[package]] +name = "wasm-streams" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4609d447824375f43e1ffbc051b50ad8f4b3ae8219680c94452ea05eb240ac7" +dependencies = [ + "futures-util", + "js-sys", + "wasm-bindgen", + "wasm-bindgen-futures", + "web-sys", +] + +[[package]] +name = "web-sys" +version = "0.3.66" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "50c24a44ec86bb68fbecd1b3efed7e85ea5621b39b35ef2766b66cd984f8010f" +dependencies = [ + "js-sys", + "wasm-bindgen", +] + +[[package]] +name = "web3" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5388522c899d1e1c96a4c307e3797e0f697ba7c77dd8e0e625ecba9dd0342937" +dependencies = [ + "arrayvec 0.7.4", + "base64 0.21.5", + "bytes 1.5.0", + "derive_more", + "ethabi 18.0.0", + "ethereum-types 0.14.1", + "futures 0.3.29", + "futures-timer", + "headers", + "hex", + "idna 0.4.0", + "jsonrpc-core 18.0.0 (registry+https://github.com/rust-lang/crates.io-index)", + "log", + "once_cell", + "parking_lot 0.12.1", + "pin-project", + "reqwest", + "rlp", + "secp256k1 0.27.0", + "serde", + "serde_json", + "tiny-keccak 2.0.2", + "url", +] + +[[package]] +name = "webpki-roots" +version = "0.24.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b291546d5d9d1eab74f069c77749f2cb8504a12caa20f0f2de93ddbf6f411888" +dependencies = [ + "rustls-webpki", +] + +[[package]] +name = "webpki-roots" +version = "0.25.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1778a42e8b3b90bff8d0f5032bf22250792889a5cdc752aa0020c84abe3aaf10" + +[[package]] +name = "which" +version = "4.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "87ba24419a2078cd2b0f2ede2691b6c66d8e47836da3b6db8265ebad47afbfc7" +dependencies = [ + "either", + "home", + "once_cell", + "rustix", +] + +[[package]] +name = "whoami" +version = "1.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "22fc3756b8a9133049b26c7f61ab35416c130e8c09b660f5b3958b446f52cc50" +dependencies = [ + "wasm-bindgen", + "web-sys", +] + +[[package]] +name = "winapi" +version = "0.2.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a" + +[[package]] +name = "winapi" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" +dependencies = [ + "winapi-i686-pc-windows-gnu", + "winapi-x86_64-pc-windows-gnu", +] + +[[package]] +name = "winapi-build" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc" + +[[package]] +name = "winapi-i686-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" + +[[package]] +name = "winapi-util" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f29e6f9198ba0d26b4c9f07dbe6f9ed633e1f3d5b8b414090084349e46a52596" +dependencies = [ + "winapi 0.3.9", +] + +[[package]] +name = "winapi-x86_64-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" + +[[package]] +name = "windows-core" +version = "0.51.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1f8cf84f35d2db49a46868f947758c7a1138116f7fac3bc844f43ade1292e64" +dependencies = [ + "windows-targets 0.48.5", +] + +[[package]] +name = "windows-sys" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9" +dependencies = [ + "windows-targets 0.48.5", +] + +[[package]] +name = "windows-sys" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "282be5f36a8ce781fad8c8ae18fa3f9beff57ec1b52cb3de0789201425d9a33d" +dependencies = [ + "windows-targets 0.52.0", +] + +[[package]] +name = "windows-targets" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9a2fa6e2155d7247be68c096456083145c183cbbbc2764150dda45a87197940c" +dependencies = [ + "windows_aarch64_gnullvm 0.48.5", + "windows_aarch64_msvc 0.48.5", + "windows_i686_gnu 0.48.5", + "windows_i686_msvc 0.48.5", + "windows_x86_64_gnu 0.48.5", + "windows_x86_64_gnullvm 0.48.5", + "windows_x86_64_msvc 0.48.5", +] + +[[package]] +name = "windows-targets" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a18201040b24831fbb9e4eb208f8892e1f50a37feb53cc7ff887feb8f50e7cd" +dependencies = [ + "windows_aarch64_gnullvm 0.52.0", + "windows_aarch64_msvc 0.52.0", + "windows_i686_gnu 0.52.0", + "windows_i686_msvc 0.52.0", + "windows_x86_64_gnu 0.52.0", + "windows_x86_64_gnullvm 0.52.0", + "windows_x86_64_msvc 0.52.0", +] + +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8" + +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb7764e35d4db8a7921e09562a0304bf2f93e0a51bfccee0bd0bb0b666b015ea" + +[[package]] +name = "windows_aarch64_msvc" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dc35310971f3b2dbbf3f0690a219f40e2d9afcf64f9ab7cc1be722937c26b4bc" + +[[package]] +name = "windows_aarch64_msvc" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bbaa0368d4f1d2aaefc55b6fcfee13f41544ddf36801e793edbbfd7d7df075ef" + +[[package]] +name = "windows_i686_gnu" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a75915e7def60c94dcef72200b9a8e58e5091744960da64ec734a6c6e9b3743e" + +[[package]] +name = "windows_i686_gnu" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a28637cb1fa3560a16915793afb20081aba2c92ee8af57b4d5f28e4b3e7df313" + +[[package]] +name = "windows_i686_msvc" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f55c233f70c4b27f66c523580f78f1004e8b5a8b659e05a4eb49d4166cca406" + +[[package]] +name = "windows_i686_msvc" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ffe5e8e31046ce6230cc7215707b816e339ff4d4d67c65dffa206fd0f7aa7b9a" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "53d40abd2583d23e4718fddf1ebec84dbff8381c07cae67ff7768bbf19c6718e" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3d6fa32db2bc4a2f5abeacf2b69f7992cd09dca97498da74a151a3132c26befd" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b7b52767868a23d5bab768e390dc5f5c55825b6d30b86c844ff2dc7414044cc" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a657e1e9d3f514745a572a6846d3c7aa7dbe1658c056ed9c3344c4109a6949e" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dff9641d1cd4be8d1a070daf9e3773c5f67e78b4d9d42263020c057706765c04" + +[[package]] +name = "winnow" +version = "0.5.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "829846f3e3db426d4cee4510841b71a8e58aa2a76b1132579487ae430ccd9c7b" +dependencies = [ + "memchr", +] + +[[package]] +name = "winreg" +version = "0.50.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "524e57b2c537c0f9b1e69f1965311ec12182b4122e45035b1508cd24d2adadb1" +dependencies = [ + "cfg-if 1.0.0", + "windows-sys 0.48.0", +] + +[[package]] +name = "ws2_32-sys" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d59cefebd0c892fa2dd6de581e937301d8552cb44489cdff035c6187cb63fa5e" +dependencies = [ + "winapi 0.2.8", + "winapi-build", +] + +[[package]] +name = "ws_stream_wasm" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7999f5f4217fe3818726b66257a4475f71e74ffd190776ad053fa159e50737f5" +dependencies = [ + "async_io_stream", + "futures 0.3.29", + "js-sys", + "log", + "pharos", + "rustc_version", + "send_wrapper 0.6.0", + "thiserror", + "wasm-bindgen", + "wasm-bindgen-futures", + "web-sys", +] + +[[package]] +name = "wyz" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "85e60b0d1b5f99db2556934e21937020776a5d31520bf169e851ac44e6420214" + +[[package]] +name = "wyz" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "05f360fc0b24296329c78fda852a1e9ae82de9cf7b27dae4b7f62f118f77b9ed" +dependencies = [ + "tap", +] + +[[package]] +name = "yansi" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "09041cd90cf85f7f8b2df60c646f853b7f535ce68f85244eb6731cf89fa498ec" + +[[package]] +name = "zerocopy" +version = "0.7.27" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f43de342578a3a14a9314a2dab1942cbfcbe5686e1f91acdc513058063eafe18" +dependencies = [ + "zerocopy-derive", +] + +[[package]] +name = "zerocopy-derive" +version = "0.7.27" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e1012d89e3acb79fad7a799ce96866cfb8098b74638465ea1b1533d35900ca90" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "zeroize" +version = "1.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "525b4ec142c6b68a2d10f01f7bbf6755599ca3f81ea53b8431b7dd348f5fdb2d" +dependencies = [ + "zeroize_derive", +] + +[[package]] +name = "zeroize_derive" +version = "1.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ce36e65b0d2999d2aafac989fb249189a141aee1f53c612c1f37d72631959f69" +dependencies = [ + "proc-macro2 1.0.70", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "zip" +version = "0.6.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "760394e246e4c28189f19d488c058bf16f564016aefac5d32bb1f3b51d5e9261" +dependencies = [ + "aes 0.8.3", + "byteorder", + "bzip2", + "constant_time_eq", + "crc32fast", + "crossbeam-utils 0.8.16", + "flate2", + "hmac 0.12.1", + "pbkdf2 0.11.0", + "sha1", + "time", + "zstd 0.11.2+zstd.1.5.2", +] + +[[package]] +name = "zk_evm" +version = "1.3.1" +source = "git+https://github.com/matter-labs/era-zk_evm.git?tag=v1.3.1-rc2#0a7c775932db4839ff6b7fb0db9bdb3583ab54c0" +dependencies = [ + "blake2 0.10.6 (git+https://github.com/RustCrypto/hashes.git?rev=1f727ce37ff40fa0cce84eb8543a45bdd3ca4a4e)", + "k256 0.11.6", + "lazy_static", + "num 0.4.1", + "serde", + "serde_json", + "sha2 0.10.6", + "sha3 0.10.6", + "static_assertions", + "zkevm_opcode_defs 1.3.1", +] + +[[package]] +name = "zk_evm" +version = "1.3.3" +source = "git+https://github.com/matter-labs/era-zk_evm.git?tag=v1.3.3-rc2#fbee20f5bac7d6ca3e22ae69b2077c510a07de4e" +dependencies = [ + "anyhow", + "lazy_static", + "num 0.4.1", + "serde", + "serde_json", + "static_assertions", + "zk_evm_abstractions", + "zkevm_opcode_defs 1.3.2", +] + +[[package]] +name = "zk_evm" +version = "1.3.3" +source = "git+https://github.com/matter-labs/era-zk_evm.git?branch=v1.3.3#fbee20f5bac7d6ca3e22ae69b2077c510a07de4e" +dependencies = [ + "anyhow", + "lazy_static", + "num 0.4.1", + "serde", + "serde_json", + "static_assertions", + "zk_evm_abstractions", + "zkevm_opcode_defs 1.3.2", +] + +[[package]] +name = "zk_evm" +version = "1.4.0" +source = "git+https://github.com/matter-labs/era-zk_evm.git?branch=v1.4.0#dd76fc5badf2c05278a21b38015a7798fe2fe358" +dependencies = [ + "anyhow", + "lazy_static", + "num 0.4.1", + "serde", + "serde_json", + "static_assertions", + "zk_evm_abstractions", + "zkevm_opcode_defs 1.3.2", +] + +[[package]] +name = "zk_evm_abstractions" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-zk_evm_abstractions.git#15a2af404902d5f10352e3d1fac693cc395fcff9" +dependencies = [ + "anyhow", + "serde", + "static_assertions", + "zkevm_opcode_defs 1.3.2", +] + +[[package]] +name = "zkevm-assembly" +version = "1.3.2" +source = "git+https://github.com/matter-labs/era-zkEVM-assembly.git?branch=v1.3.2#3c61d450cbe6548068be8f313ed02f1bd229a865" +dependencies = [ + "env_logger 0.9.3", + "hex", + "lazy_static", + "log", + "nom", + "num-bigint 0.4.4", + "num-traits", + "sha3 0.10.8", + "smallvec", + "structopt", + "thiserror", + "zkevm_opcode_defs 1.3.2", +] + +[[package]] +name = "zkevm_circuits" +version = "1.4.0" +source = "git+https://github.com/matter-labs/era-zkevm_circuits.git?branch=main#fb3e2574b5c890342518fc930c145443f039a105" +dependencies = [ + "arrayvec 0.7.4", + "bincode", + "boojum", + "cs_derive 0.1.0 (git+https://github.com/matter-labs/era-boojum.git?branch=main)", + "derivative", + "hex", + "itertools 0.10.5", + "rand 0.4.6", + "rand 0.8.5", + "seq-macro", + "serde", + "serde_json", + "smallvec", + "zkevm_opcode_defs 1.3.2", +] + +[[package]] +name = "zkevm_opcode_defs" +version = "1.3.1" +source = "git+https://github.com/matter-labs/era-zkevm_opcode_defs.git?branch=v1.3.1#00d4ad2292bd55374a0fa10fe11686d7a109d8a0" +dependencies = [ + "bitflags 1.3.2", + "ethereum-types 0.14.1", + "lazy_static", + "sha2 0.10.8", +] + +[[package]] +name = "zkevm_opcode_defs" +version = "1.3.2" +source = "git+https://github.com/matter-labs/era-zkevm_opcode_defs.git?branch=v1.3.2#dffacadeccdfdbff4bc124d44c595c4a6eae5013" +dependencies = [ + "bitflags 2.4.1", + "blake2 0.10.6 (git+https://github.com/RustCrypto/hashes.git?rev=1f727ce37ff40fa0cce84eb8543a45bdd3ca4a4e)", + "ethereum-types 0.14.1", + "k256 0.11.6", + "lazy_static", + "sha2 0.10.6", + "sha3 0.10.6", +] + +[[package]] +name = "zkevm_test_harness" +version = "1.3.3" +source = "git+https://github.com/matter-labs/era-zkevm_test_harness.git?branch=v1.3.3#d52b56d6ba8196c8a3c74c4933654469e6f27a5a" +dependencies = [ + "bincode", + "circuit_testing", + "codegen 0.2.0", + "crossbeam 0.8.2", + "derivative", + "env_logger 0.10.1", + "hex", + "num-bigint 0.4.4", + "num-integer", + "num-traits", + "rayon", + "serde", + "serde_json", + "smallvec", + "structopt", + "sync_vm", + "test-log", + "tracing", + "zk_evm 1.3.3 (git+https://github.com/matter-labs/era-zk_evm.git?branch=v1.3.3)", + "zkevm-assembly", +] + +[[package]] +name = "zkevm_test_harness" +version = "1.4.0" +source = "git+https://github.com/matter-labs/era-zkevm_test_harness.git?branch=v1.4.0#d2e3670e0c5115b7cc7cc24e6d3dbdd17a214aad" +dependencies = [ + "bincode", + "circuit_definitions", + "codegen 0.2.0", + "crossbeam 0.8.2", + "derivative", + "env_logger 0.10.1", + "hex", + "rand 0.4.6", + "rayon", + "serde", + "serde_json", + "smallvec", + "structopt", + "test-log", + "tracing", + "zkevm-assembly", +] + +[[package]] +name = "zksync-web3-rs" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "15bc9b106393359ac013c2527db318ced4ca838d26ef03488233af557ebe5da8" +dependencies = [ + "async-trait", + "clap 4.4.10", + "env_logger 0.10.1", + "ethers", + "ethers-contract", + "hex", + "lazy_static", + "log", + "serde", + "serde_json", + "sha2 0.9.9", + "thiserror", + "tokio", +] + +[[package]] +name = "zksync_basic_types" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "serde", + "serde_json", + "web3", +] + +[[package]] +name = "zksync_circuit_breaker" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "async-trait", + "backon", + "convert_case 0.6.0", + "futures 0.3.29", + "hex", + "metrics", + "serde_json", + "thiserror", + "tokio", + "tracing", + "zksync_config", + "zksync_contracts", + "zksync_dal", + "zksync_eth_client", + "zksync_types", +] + +[[package]] +name = "zksync_commitment_utils" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "zkevm_test_harness 1.4.0", + "zksync_types", + "zksync_utils", +] + +[[package]] +name = "zksync_concurrency" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "anyhow", + "once_cell", + "pin-project", + "rand 0.8.5", + "sha3 0.10.8", + "thiserror", + "time", + "tokio", + "tracing", + "tracing-subscriber", + "vise", +] + +[[package]] +name = "zksync_config" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "serde", + "zksync_basic_types", +] + +[[package]] +name = "zksync_consensus_bft" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "anyhow", + "async-trait", + "once_cell", + "rand 0.8.5", + "thiserror", + "tracing", + "vise", + "zksync_concurrency", + "zksync_consensus_crypto", + "zksync_consensus_network", + "zksync_consensus_roles", + "zksync_consensus_storage", + "zksync_consensus_utils", + "zksync_protobuf", +] + +[[package]] +name = "zksync_consensus_crypto" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "anyhow", + "blst", + "ed25519-dalek", + "ff_ce", + "hex", + "pairing_ce 0.28.5 (git+https://github.com/matter-labs/pairing.git?rev=f55393fd366596eac792d78525d26e9c4d6ed1ca)", + "rand 0.4.6", + "rand 0.8.5", + "sha3 0.10.8", + "thiserror", + "tracing", +] + +[[package]] +name = "zksync_consensus_executor" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "anyhow", + "prost", + "rand 0.8.5", + "tracing", + "vise", + "zksync_concurrency", + "zksync_consensus_bft", + "zksync_consensus_crypto", + "zksync_consensus_network", + "zksync_consensus_roles", + "zksync_consensus_storage", + "zksync_consensus_sync_blocks", + "zksync_consensus_utils", + "zksync_protobuf", + "zksync_protobuf_build", +] + +[[package]] +name = "zksync_consensus_network" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "anyhow", + "async-trait", + "im", + "once_cell", + "pin-project", + "prost", + "rand 0.8.5", + "snow", + "thiserror", + "tracing", + "vise", + "zksync_concurrency", + "zksync_consensus_crypto", + "zksync_consensus_roles", + "zksync_consensus_utils", + "zksync_protobuf", + "zksync_protobuf_build", +] + +[[package]] +name = "zksync_consensus_roles" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "anyhow", + "bit-vec", + "hex", + "prost", + "rand 0.8.5", + "serde", + "thiserror", + "tracing", + "zksync_concurrency", + "zksync_consensus_crypto", + "zksync_consensus_utils", + "zksync_protobuf", + "zksync_protobuf_build", +] + +[[package]] +name = "zksync_consensus_storage" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "anyhow", + "async-trait", + "prost", + "rand 0.8.5", + "thiserror", + "tracing", + "zksync_concurrency", + "zksync_consensus_roles", + "zksync_protobuf", + "zksync_protobuf_build", +] + +[[package]] +name = "zksync_consensus_sync_blocks" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "anyhow", + "thiserror", + "tracing", + "zksync_concurrency", + "zksync_consensus_network", + "zksync_consensus_roles", + "zksync_consensus_storage", + "zksync_consensus_utils", +] + +[[package]] +name = "zksync_consensus_utils" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "thiserror", + "zksync_concurrency", +] + +[[package]] +name = "zksync_contracts" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "envy", + "ethabi 18.0.0", + "hex", + "once_cell", + "serde", + "serde_json", + "zksync_utils", +] + +[[package]] +name = "zksync_core" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "actix-cors", + "actix-rt", + "actix-web", + "anyhow", + "async-trait", + "axum", + "bigdecimal", + "bitflags 1.3.2", + "chrono", + "ctrlc", + "futures 0.3.29", + "governor", + "hex", + "itertools 0.10.5", + "jsonrpc-core 18.0.0 (git+https://github.com/matter-labs/jsonrpc.git?branch=master)", + "jsonrpc-core-client", + "jsonrpc-derive", + "jsonrpc-http-server", + "jsonrpc-pubsub", + "jsonrpc-ws-server", + "lru", + "metrics", + "multivm", + "num 0.3.1", + "once_cell", + "prometheus_exporter", + "prost", + "rand 0.8.5", + "reqwest", + "serde", + "serde_json", + "thiserror", + "tokio", + "tower", + "tower-http", + "tracing", + "vise", + "vlog", + "zksync_circuit_breaker", + "zksync_commitment_utils", + "zksync_concurrency", + "zksync_config", + "zksync_consensus_bft", + "zksync_consensus_executor", + "zksync_consensus_roles", + "zksync_consensus_storage", + "zksync_contracts", + "zksync_dal", + "zksync_eth_client", + "zksync_eth_signer", + "zksync_health_check", + "zksync_mempool", + "zksync_merkle_tree", + "zksync_mini_merkle_tree", + "zksync_object_store", + "zksync_protobuf", + "zksync_protobuf_build", + "zksync_prover_utils", + "zksync_queued_job_processor", + "zksync_state", + "zksync_storage", + "zksync_system_constants", + "zksync_types", + "zksync_utils", + "zksync_verification_key_generator_and_server", + "zksync_web3_decl", +] + +[[package]] +name = "zksync_crypto" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "base64 0.13.1", + "blake2 0.10.6 (registry+https://github.com/rust-lang/crates.io-index)", + "hex", + "once_cell", + "serde", + "sha2 0.9.9", + "thiserror", + "zksync_basic_types", +] + +[[package]] +name = "zksync_dal" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "bigdecimal", + "bincode", + "hex", + "itertools 0.10.5", + "num 0.3.1", + "once_cell", + "prost", + "rand 0.8.5", + "serde", + "serde_json", + "sqlx", + "strum 0.24.1", + "thiserror", + "tokio", + "tracing", + "url", + "vise", + "zksync_consensus_roles", + "zksync_consensus_storage", + "zksync_contracts", + "zksync_health_check", + "zksync_protobuf", + "zksync_protobuf_build", + "zksync_system_constants", + "zksync_types", + "zksync_utils", +] + +[[package]] +name = "zksync_eth_client" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "async-trait", + "hex", + "jsonrpc-core 18.0.0 (registry+https://github.com/rust-lang/crates.io-index)", + "serde", + "thiserror", + "tokio", + "tracing", + "vise", + "zksync_config", + "zksync_contracts", + "zksync_eth_signer", + "zksync_types", +] + +[[package]] +name = "zksync_eth_signer" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "async-trait", + "hex", + "jsonrpc-core 18.0.0 (registry+https://github.com/rust-lang/crates.io-index)", + "parity-crypto", + "reqwest", + "rlp", + "secp256k1 0.27.0", + "serde", + "serde_derive", + "serde_json", + "thiserror", + "zksync_types", +] + +[[package]] +name = "zksync_health_check" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "async-trait", + "futures 0.3.29", + "serde", + "serde_json", + "tokio", + "tracing", +] + +[[package]] +name = "zksync_mempool" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "tracing", + "zksync_types", +] + +[[package]] +name = "zksync_merkle_tree" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "leb128", + "once_cell", + "rayon", + "thiserror", + "tracing", + "vise", + "zksync_crypto", + "zksync_storage", + "zksync_types", + "zksync_utils", +] + +[[package]] +name = "zksync_mini_merkle_tree" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "once_cell", + "zksync_basic_types", + "zksync_crypto", +] + +[[package]] +name = "zksync_object_store" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "async-trait", + "bincode", + "flate2", + "google-cloud-auth", + "google-cloud-storage", + "http", + "serde_json", + "tokio", + "tracing", + "vise", + "zksync_config", + "zksync_types", +] + +[[package]] +name = "zksync_protobuf" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "anyhow", + "bit-vec", + "once_cell", + "prost", + "prost-reflect", + "quick-protobuf", + "rand 0.8.5", + "serde", + "serde_json", + "zksync_concurrency", + "zksync_protobuf_build", +] + +[[package]] +name = "zksync_protobuf_build" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-consensus.git?rev=49b1a98f80d0e9f74fdceadece4283e745c71599#49b1a98f80d0e9f74fdceadece4283e745c71599" +dependencies = [ + "anyhow", + "heck 0.4.1", + "prettyplease", + "proc-macro2 1.0.70", + "prost-build", + "prost-reflect", + "protox", + "quote 1.0.33", + "syn 2.0.39", +] + +[[package]] +name = "zksync_prover_utils" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "async-trait", + "ctrlc", + "futures 0.3.29", + "regex", + "reqwest", + "tokio", + "toml_edit 0.14.4", + "tracing", + "zksync_config", + "zksync_object_store", + "zksync_types", + "zksync_utils", +] + +[[package]] +name = "zksync_queued_job_processor" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "async-trait", + "tokio", + "tracing", + "vise", + "zksync_utils", +] + +[[package]] +name = "zksync_state" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "itertools 0.10.5", + "mini-moka", + "tokio", + "tracing", + "vise", + "zksync_dal", + "zksync_storage", + "zksync_types", + "zksync_utils", +] + +[[package]] +name = "zksync_storage" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "num_cpus", + "once_cell", + "rocksdb", + "tracing", + "vise", +] + +[[package]] +name = "zksync_system_constants" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "bigdecimal", + "hex", + "num 0.3.1", + "once_cell", + "serde", + "serde_json", + "url", + "zksync_basic_types", + "zksync_contracts", + "zksync_utils", +] + +[[package]] +name = "zksync_types" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "blake2 0.10.6 (registry+https://github.com/rust-lang/crates.io-index)", + "chrono", + "codegen 0.1.0", + "ethereum-types 0.12.1", + "hex", + "num 0.3.1", + "num_enum 0.6.1", + "once_cell", + "parity-crypto", + "rlp", + "serde", + "serde_json", + "serde_with", + "strum 0.24.1", + "thiserror", + "zk_evm 1.3.3 (git+https://github.com/matter-labs/era-zk_evm.git?tag=v1.3.3-rc2)", + "zk_evm 1.4.0", + "zkevm_test_harness 1.3.3", + "zksync_basic_types", + "zksync_consensus_roles", + "zksync_contracts", + "zksync_mini_merkle_tree", + "zksync_protobuf", + "zksync_protobuf_build", + "zksync_system_constants", + "zksync_utils", +] + +[[package]] +name = "zksync_utils" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "bigdecimal", + "futures 0.3.29", + "hex", + "itertools 0.10.5", + "metrics", + "num 0.3.1", + "reqwest", + "serde", + "thiserror", + "tokio", + "tracing", + "vlog", + "zk_evm 1.3.3 (git+https://github.com/matter-labs/era-zk_evm.git?tag=v1.3.3-rc2)", + "zksync_basic_types", +] + +[[package]] +name = "zksync_verification_key_generator_and_server" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "anyhow", + "bincode", + "circuit_testing", + "ff_ce", + "hex", + "itertools 0.10.5", + "once_cell", + "serde_json", + "structopt", + "tracing", + "vlog", + "zksync_prover_utils", + "zksync_types", +] + +[[package]] +name = "zksync_web3_decl" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?rev=3c669e7b0caf6515ad865f4cba5ea6fb36c33811#3c669e7b0caf6515ad865f4cba5ea6fb36c33811" +dependencies = [ + "bigdecimal", + "chrono", + "itertools 0.10.5", + "jsonrpsee", + "rlp", + "serde", + "serde_json", + "thiserror", + "zksync_types", +] + +[[package]] +name = "zstd" +version = "0.11.2+zstd.1.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "20cc960326ece64f010d2d2107537f26dc589a6573a316bd5b1dba685fa5fde4" +dependencies = [ + "zstd-safe 5.0.2+zstd.1.5.2", +] + +[[package]] +name = "zstd" +version = "0.12.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a27595e173641171fc74a1232b7b1c7a7cb6e18222c11e9dfb9888fa424c53c" +dependencies = [ + "zstd-safe 6.0.6", +] + +[[package]] +name = "zstd" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bffb3309596d527cfcba7dfc6ed6052f1d39dfbd7c867aa2e865e4a449c10110" +dependencies = [ + "zstd-safe 7.0.0", +] + +[[package]] +name = "zstd-safe" +version = "5.0.2+zstd.1.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1d2a5585e04f9eea4b2a3d1eca508c4dee9592a89ef6f450c11719da0726f4db" +dependencies = [ + "libc", + "zstd-sys", +] + +[[package]] +name = "zstd-safe" +version = "6.0.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ee98ffd0b48ee95e6c5168188e44a54550b1564d9d530ee21d5f0eaed1069581" +dependencies = [ + "libc", + "zstd-sys", +] + +[[package]] +name = "zstd-safe" +version = "7.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "43747c7422e2924c11144d5229878b98180ef8b06cca4ab5af37afc8a8d8ea3e" +dependencies = [ + "zstd-sys", +] + +[[package]] +name = "zstd-sys" +version = "2.0.9+zstd.1.5.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9e16efa8a874a0481a574084d34cc26fdb3b99627480f785888deb6386506656" +dependencies = [ + "cc", + "pkg-config", +] + +[[patch.unused]] +name = "sha3" +version = "0.10.6" +source = "git+https://github.com/RustCrypto/hashes?tag=sha3-v0.10.6#7a187e934c1f6c68e4b4e5cf37541b7a0d64d303" diff --git a/.test-node-subtree/Cargo.toml b/.test-node-subtree/Cargo.toml new file mode 100644 index 00000000..48203b0c --- /dev/null +++ b/.test-node-subtree/Cargo.toml @@ -0,0 +1,66 @@ +[package] +name = "era_test_node" +version = "0.1.0-alpha.14" +edition = "2018" +authors = ["The Matter Labs Team "] +homepage = "https://zksync.io/" +repository = "https://github.com/matter-labs/zksync-era" +license = "MIT OR Apache-2.0" +keywords = ["blockchain", "zksync"] +categories = ["cryptography"] +publish = false # We don't want to publish our binaries. + +[dependencies] +zksync_basic_types = { git = "https://github.com/matter-labs/zksync-era.git", rev = "3c669e7b0caf6515ad865f4cba5ea6fb36c33811" } +zksync_core = { git = "https://github.com/matter-labs/zksync-era.git", rev = "3c669e7b0caf6515ad865f4cba5ea6fb36c33811" } +multivm = { git = "https://github.com/matter-labs/zksync-era.git", rev = "3c669e7b0caf6515ad865f4cba5ea6fb36c33811" } +zksync_contracts = { git = "https://github.com/matter-labs/zksync-era.git", rev = "3c669e7b0caf6515ad865f4cba5ea6fb36c33811" } +zksync_types = { git = "https://github.com/matter-labs/zksync-era.git", rev = "3c669e7b0caf6515ad865f4cba5ea6fb36c33811" } +zksync_utils = { git = "https://github.com/matter-labs/zksync-era.git", rev = "3c669e7b0caf6515ad865f4cba5ea6fb36c33811" } +zksync_state = { git = "https://github.com/matter-labs/zksync-era.git", rev = "3c669e7b0caf6515ad865f4cba5ea6fb36c33811" } +zksync_web3_decl = { git = "https://github.com/matter-labs/zksync-era.git", rev = "3c669e7b0caf6515ad865f4cba5ea6fb36c33811" } +sha3 = "0.10.6" + + +openssl-sys = { version = "0.9", features = ["vendored"] } + +anyhow = "1.0" +tokio = { version = "1", features = ["time", "rt"] } +futures = { version = "0.3", features = ["compat"] } +once_cell = "1.7" + +jsonrpc-http-server = { git = "https://github.com/matter-labs/jsonrpc.git", branch = "master" } +jsonrpc-core = { git = "https://github.com/matter-labs/jsonrpc.git", branch = "master" } +jsonrpc-core-client = { git = "https://github.com/matter-labs/jsonrpc.git", branch = "master" } +jsonrpc-derive = { git = "https://github.com/matter-labs/jsonrpc.git", branch = "master" } + +clap = { version = "4.2.4", features = ["derive"] } +reqwest = { version = "0.11", features = ["blocking"] } +serde = { version = "1.0", features = ["derive"] } +tracing = { version = "0.1.26", features = ["log"] } +tracing-subscriber = { version = "0.3", features = ["fmt", "env-filter", "time", "json", "local-time"] } +colored = "2.0" +lazy_static = "1.4" +eyre = "0.6" +serde_json = "1.0.67" +bigdecimal = { version = "0.2.0" } +hex = "0.4" +ethabi = "16.0.0" +itertools = "0.10.5" +rustc-hash = "1.1.0" +indexmap = "2.0.1" +chrono = { version = "0.4.31", default-features = false } +time = "0.3.30" + +[dev-dependencies] +httptest = "0.15.4" +tempdir = "0.3.7" +maplit = "1.0.2" +zksync-web3-rs = "0.1.1" +ethers = { version = "2.0.4", features = ["rustls"] } + +[patch.crates-io] +sha3 = { git = "https://github.com/RustCrypto/hashes", tag = "sha3-v0.10.6" } + +[profile.dev] +debug = 0 \ No newline at end of file diff --git a/.test-node-subtree/Cross.toml b/.test-node-subtree/Cross.toml new file mode 100644 index 00000000..085fc4ee --- /dev/null +++ b/.test-node-subtree/Cross.toml @@ -0,0 +1,9 @@ +# Cross.toml + +[target.x86_64-unknown-linux-gnu] +pre-build = [ + "export DEBIAN_FRONTEND=noninteractive", + "export TZ=Etc/UTC", + "dpkg --add-architecture $CROSS_DEB_ARCH", + "apt update -q && apt upgrade -yq && apt install --assume-yes --no-install-recommends libclang-10-dev clang-10 cmake build-essential pkg-config libssl-dev:$CROSS_DEB_ARCH libsasl2-dev llvm-dev gnutls-bin" +] \ No newline at end of file diff --git a/.test-node-subtree/LICENSE-APACHE b/.test-node-subtree/LICENSE-APACHE new file mode 100644 index 00000000..d9a10c0d --- /dev/null +++ b/.test-node-subtree/LICENSE-APACHE @@ -0,0 +1,176 @@ + Apache License + Version 2.0, January 2004 + http://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS diff --git a/.test-node-subtree/LICENSE-MIT b/.test-node-subtree/LICENSE-MIT new file mode 100644 index 00000000..2739ea6e --- /dev/null +++ b/.test-node-subtree/LICENSE-MIT @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2019 Matter Labs + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/.test-node-subtree/Makefile b/.test-node-subtree/Makefile new file mode 100644 index 00000000..51efd64e --- /dev/null +++ b/.test-node-subtree/Makefile @@ -0,0 +1,70 @@ +# Build the system contracts +build-contracts: + cd etc/system-contracts && yarn; yarn install; yarn build + ./scripts/refresh_contracts.sh + +# Clean the system contracts +clean-contracts: + cd etc/system-contracts && yarn clean + rm -rf src/deps/contracts + +# Rebuild the system contracts +rebuild-contracts: + cd etc/system-contracts && yarn build + ./scripts/refresh_contracts.sh + ./scripts/refresh_test_contracts.sh + +# Build the Rust project +rust-build: + cargo build --release + +# Run local +run: rust-build + ./target/release/era_test_node run + +# Build the Rust project for a specific target. Primarily used for CI. +build-%: + cross build --bin era_test_node --target $* --release + +# Build the Rust documentation +rust-doc: + cargo doc --no-deps --open + +# Lint checks for Rust code +lint: + cd e2e-tests && yarn && yarn lint && yarn fmt && yarn typecheck + cargo fmt --all -- --check + cargo clippy -p era_test_node -Zunstable-options -- -D warnings --allow clippy::unwrap_used + +# Fix lint errors for Rust code +lint-fix: + cd e2e-tests && yarn && yarn lint:fix && yarn fmt:fix + cargo clippy --fix + cargo fmt + +# Run unit tests for Rust code +test: + cargo test + +# Run e2e tests against running era_test_node +test-e2e: + ./scripts/execute-e2e-tests.sh + +# Build everything +all: build-contracts rust-build + +# Clean everything +clean: clean-contracts + +# Create new draft release based on Cargo.toml version +new-release-tag: + @VERSION_NUMBER=$$(grep '^version =' Cargo.toml | awk -F '"' '{print $$2}') && \ + git tag -a v$$VERSION_NUMBER -m "Release v$$VERSION_NUMBER" && \ + echo "\n\033[0;32mGit tag creation SUCCESSFUL! Use the following command to push the tag:\033[0m" && \ + echo "git push origin v$$VERSION_NUMBER" + +# Create the rust book +book: + mdbook build docs/rustbook + +.PHONY: build-contracts clean-contracts rebuild-contracts rust-build lint test test-e2e all clean build-% new-release-tag book diff --git a/.test-node-subtree/README.md b/.test-node-subtree/README.md new file mode 100644 index 00000000..07579b22 --- /dev/null +++ b/.test-node-subtree/README.md @@ -0,0 +1,250 @@ +
+ + +![era-test-node](./.github/assets/era_test_node_banner_light.png#gh-light-mode-only) +![era-test-node](./.github/assets/era_test_node_banner_dark.png#gh-dark-mode-only) + + +
+ +# 🚀 zkSync Era In-Memory Node 🚀 + +This crate provides an in-memory node that supports forking the state from other networks. + +The goal of this crate is to offer a fast solution for integration testing, bootloader and system contract testing, and prototyping. + +🔗 For a detailed walkthrough, refer to the [official documentation](https://era.zksync.io/docs/tools/testing/era-test-node.html). + +## 📌 Overview + +The In-Memory Node is designed for local testing and uses an in-memory database for storing state information. It also employs simplified hashmaps for tracking blocks and transactions. When in fork mode, it fetches missing storage data from a remote source if not available locally. Additionally, it uses the remote server (openchain) to resolve the ABI and topics to human-readable names. + +## ⚠️ Caution + +Please note that `era-test-node` is still in its **alpha** stage. Some features might not be fully supported yet and may not work as intended. However, it is open-sourced, and contributions are welcome! + +## 📊 Limitations & Features + +| 🚫 Limitations | ✅ Features | +| ----------------------------------------------- | ----------------------------------------------------------- | +| No communication between Layer 1 and Layer 2. | Can fork the state of mainnet, testnet, or custom network. | +| Many APIs are not yet implemented. | Can replay existing mainnet or testnet transactions. | +| No support for accessing historical data. | Uses local bootloader and system contracts. | +| Only one transaction allowed per Layer 1 batch. | Operates deterministically in non-fork mode. | +| Fixed values returned for zk Gas estimation. | Starts up quickly with pre-configured 'rich' accounts. | +| Redeploy requires MetaMask cache reset. | Supports hardhat's console.log debugging. | +| | Resolves names of ABI functions and Events using openchain. | + +## 🛠 Prerequisites + +1. **Rust**: `era-test-node` is written in Rust. Ensure you have Rust installed on your machine. [Download Rust here](https://www.rust-lang.org/tools/install). + +2. **Other Dependencies**: This crate relies on rocksDB. If you face any compile errors due to rocksDB, install the necessary dependencies with: + ```bash + apt-get install -y cmake pkg-config libssl-dev clang + ``` + +## 📥 Installation & Setup + +1. Download `era-test-node` from latest [Release](https://github.com/matter-labs/era-test-node/releases/latest) + +2. Extract the binary and mark as executable: + ```bash + tar xz -f era_test_node.tar.gz -C /usr/local/bin/ + chmod +x /usr/local/bin/era_test_node + ``` + +3. Start the node: + ```bash + era_test_node run + ``` + +## 🧑‍💻 Running Locally + +1. Compile Rust project and start the node: + ```bash + make run + ``` + +## 📄 System Contracts + +The system contract within the node can be specified via the `--dev-system-contracts` option. +It can take one of the following options: + * `built-in`: Use the compiled built-in contracts + * `built-in-no-verify`: Use the compiled built-in contracts, but without signature verification + * `local`: Load contracts from `ZKSYNC_HOME` + +## 📃 Logging + +The node may be started in either of `debug`, `info`, `warn` or `error` logging levels via the `--log` option: +```bash +era_test_node --log=error run +``` + +Additionally, the file path can be provided via the `--log-file-path` option (defaults to `./era_test_node.log`): +```bash +era_test_node --log=error --log-file-path=run.log run +``` + +The logging can be configured during runtime via the [`config_setLogLevel`](./SUPPORTED_APIS.md#config_setloglevel) and [`config_setLogging`](./SUPPORTED_APIS.md#config_setlogging) methods. + +## 📃 Caching + +The node will cache certain network request by default to disk in the `.cache` directory. Alternatively the caching can be disabled or set to in-memory only +via the `--cache=none|memory|disk` parameter. + +```bash +era_test_node --cache=none run +``` + +```bash +era_test_node --cache=memory run +``` + +Additionally when using `--cache=disk`, the cache directory may be specified via `--cache-dir` and the cache may +be reset on startup via `--reset-cache` parameters. +```bash +era_test_node --cache=disk --cache-dir=/tmp/foo --reset-cache run +``` + +## 🌐 Network Details + +- L2 RPC: http://localhost:8011 +- Network Id: 260 + +> Note: The existing implementation does not support communication with Layer 1. As a result, an L1 RPC is not available. + +## 🍴 Forking Networks + +To fork the mainnet: + +```bash +era_test_node fork mainnet +``` + +> Tip: You can also fork the zkSync Sepolia testnet with `era_test_node fork sepolia-testnet`. + +## 🔄 Replay Remote Transactions Locally + +If you wish to replay a remote transaction locally for deep debugging, use the following command: + +```bash +era_test_node replay_tx +``` + +## 📞 Sending Network Calls + +You can send network calls against a running `era-test-node`. For example, to check the testnet LINK balance or mainnet USDT, use `curl` or `foundry-zksync`. + +```bash +curl -X POST -H "Content-Type: application/json" --data '{"jsonrpc":"2.0","method":"eth_call","params":[{"to":"0x40609141Db628BeEE3BfAB8034Fc2D8278D0Cc78", "data":"0x06fdde03"}, "latest"],"id":1}' http://localhost:8011 +``` + +## 🔍 Seeing more details of the transactions + +By default, the tool is just printing the basic information about the executed transactions (like status, gas used etc). + +But with --show-calls flag, it can print more detailed call traces, and with --resolve-hashes, it will ask openchain for ABI names. + +```bash +era_test_node --show-calls=user --resolve-hashes replay_tx sepolia-testnet 0x7119045573862797257e4441ff48bf5a3bc4d133a00d167c18dc955eda12cfac + +Executing 0x7119045573862797257e4441ff48bf5a3bc4d133a00d167c18dc955eda12cfac +┌─────────────────────────┐ +│ TRANSACTION SUMMARY │ +└─────────────────────────┘ +Transaction: SUCCESS +Initiator: 0x4eaf936c172b5e5511959167e8ab4f7031113ca3 +Payer: 0x4eaf936c172b5e5511959167e8ab4f7031113ca3 +Gas - Limit: 2_487_330 | Used: 969_330 | Refunded: 1_518_000 +Use --show-gas-details flag or call config_setShowGasDetails to display more info + +==== Console logs: + +==== 22 call traces. Use --show-calls flag or call config_setShowCalls to display more info. + Call(Normal) 0x4eaf936c172b5e5511959167e8ab4f7031113ca3 validateTransaction(bytes32, bytes32, tuple) 1830339 + Call(Normal) 0x0000000000000000000000000000000000000001 0x89c19e9b 1766835 + Call(Normal) 0x4eaf936c172b5e5511959167e8ab4f7031113ca3 payForTransaction(bytes32, bytes32, tuple) 1789767 + Call(Normal) 0x4eaf936c172b5e5511959167e8ab4f7031113ca3 executeTransaction(bytes32, bytes32, tuple) 1671012 + Call(Mimic) 0x5d4fb5385ed95b65d1cd6a10ed9549613481ab2f 0x 1443393 +``` + +You can use the following options to get more granular information during transaction processing: + +- `--show-storage-logs `: Show storage log information. + [default: none] + [possible values: none, read, paid, write, all] + +- `--show-vm-details `: Show VM details information. + [default: none] + [possible values: none, all] + +- `--show-gas-details `: Show Gas details information. + [default: none] + [possible values: none, all] + +Example: + +```bash +era_test_node --show-storage-logs=all --show-vm-details=all --show-gas-details=all run +``` + +## 💰 Using Rich Wallets + +For testing and development purposes, the `era-test-node` comes pre-configured with a set of 'rich' wallets. These wallets are loaded with test funds, allowing you to simulate transactions and interactions without the need for real assets. + +Here's a list of the available rich wallets: + +| Account Address | Private Key | +| -------------------------------------------- | -------------------------------------------------------------------- | +| `0x36615Cf349d7F6344891B1e7CA7C72883F5dc049` | `0x7726827caac94a7f9e1b160f7ea819f172f7b6f9d2a97f992c38edeab82d4110` | +| `0xa61464658AfeAf65CccaaFD3a512b69A83B77618` | `0xac1e735be8536c6534bb4f17f06f6afc73b2b5ba84ac2cfb12f7461b20c0bbe3` | +| `0x0D43eB5B8a47bA8900d84AA36656c92024e9772e` | `0xd293c684d884d56f8d6abd64fc76757d3664904e309a0645baf8522ab6366d9e` | +| `0xA13c10C0D5bd6f79041B9835c63f91de35A15883` | `0x850683b40d4a740aa6e745f889a6fdc8327be76e122f5aba645a5b02d0248db8` | +| `0x8002cD98Cfb563492A6fB3E7C8243b7B9Ad4cc92` | `0xf12e28c0eb1ef4ff90478f6805b68d63737b7f33abfa091601140805da450d93` | +| `0x4F9133D1d3F50011A6859807C837bdCB31Aaab13` | `0xe667e57a9b8aaa6709e51ff7d093f1c5b73b63f9987e4ab4aa9a5c699e024ee8` | +| `0xbd29A1B981925B94eEc5c4F1125AF02a2Ec4d1cA` | `0x28a574ab2de8a00364d5dd4b07c4f2f574ef7fcc2a86a197f65abaec836d1959` | +| `0xedB6F5B4aab3dD95C7806Af42881FF12BE7e9daa` | `0x74d8b3a188f7260f67698eb44da07397a298df5427df681ef68c45b34b61f998` | +| `0xe706e60ab5Dc512C36A4646D719b889F398cbBcB` | `0xbe79721778b48bcc679b78edac0ce48306a8578186ffcb9f2ee455ae6efeace1` | +| `0xE90E12261CCb0F3F7976Ae611A29e84a6A85f424` | `0x3eb15da85647edd9a1159a4a13b9e7c56877c4eb33f614546d4db06a51868b1c` | + +Feel free to use these wallets in your tests, but remember, they are for development purposes only and should not be used in production or with real assets. + +## 🔧 Supported APIs + +See our list of [Supported APIs here](SUPPORTED_APIS.md). + +## 🤖 CI/CD Testing with GitHub Actions + +A GitHub Action is available for integrating `era-test-node` into your CI/CD environments. This action offers high configurability and streamlines the process of testing your applications in an automated way. + +You can find this GitHub Action in the marketplace [here](https://github.com/marketplace/actions/era-test-node-action). + +### 📝 Example Usage + +Below is an example `yaml` configuration to use the `era-test-node` GitHub Action in your workflow: + +```yml +name: Run Era Test Node Action + +on: + push: + branches: [ main ] + +jobs: + build: + runs-on: ubuntu-latest + + steps: + - name: Checkout code + uses: actions/checkout@v2 + + - name: Run Era Test Node + uses: dutterbutter/era-test-node-action@latest +``` + +## 🤝 Contributing + +We welcome contributions from the community! If you're interested in contributing to the zkSync Era In-Memory Node, please take a look at our [CONTRIBUTING.md](./.github/CONTRIBUTING.md) for guidelines and details on the process. + +Thank you for making zkSync Era In-Memory Node better! 🙌 diff --git a/.test-node-subtree/SUPPORTED_APIS.md b/.test-node-subtree/SUPPORTED_APIS.md new file mode 100644 index 00000000..e560c0fb --- /dev/null +++ b/.test-node-subtree/SUPPORTED_APIS.md @@ -0,0 +1,1981 @@ +# 🔧 Supported APIs for In-Memory Node 🔧 + +> ⚠️ **WORK IN PROGRESS**: This list is non-comprehensive and being updated. If there is an API that requires additional support, please start by [creating a GitHub Issue](https://github.com/matter-labs/era-test-node/issues/new/choose). + +## Key + +The `status` options are: + ++ `SUPPORTED` - Basic support is complete ++ `PARTIALLY` - Partial support and a description including more specific details ++ `NOT IMPLEMENTED` - Currently not supported/implemented + +## Supported APIs Table + +| Namespace | API |
Status
| Description | +| --- | --- | --- | --- | +| [`CONFIG`](#config-namespace) | [`config_getShowCalls`](#config_getshowcalls) | `SUPPORTED` | Gets the current value of `show_calls` that's originally set with `--show-calls` option | +| [`CONFIG`](#config-namespace) | [`config_getCurrentTimestamp`](#config_getcurrenttimestamp) | `SUPPORTED` | Gets the value of `current_timestamp` for the node | +| [`CONFIG`](#config-namespace) | [`config_setResolveHashes`](#config_setresolvehashes) | `SUPPORTED` | Updates `resolve-hashes` to call OpenChain for human-readable ABI names in call traces | +| [`CONFIG`](#config-namespace) | [`config_setShowCalls`](#config_setshowcalls) | `SUPPORTED` | Updates `show_calls` to print more detailed call traces | +| [`CONFIG`](#config-namespace) | [`config_setShowStorageLogs`](#config_setshowstoragelogs) | `SUPPORTED` | Updates `show_storage_logs` to print storage log reads/writes | +| [`CONFIG`](#config-namespace) | [`config_setShowVmDetails`](#config_setshowvmdetails) | `SUPPORTED` | Updates `show_vm_details` to print more detailed results from vm execution | +| [`CONFIG`](#config-namespace) | [`config_setShowGasDetails`](#config_setshowgasdetails) | `SUPPORTED` | Updates `show_gas_details` to print more details about gas estimation and usage | +| [`CONFIG`](#config-namespace) | [`config_setLogLevel`](#config_setloglevel) | `SUPPORTED` | Sets the logging level for the node and only displays the node logs. | +| [`CONFIG`](#config-namespace) | [`config_setLogging`](#config_setlogging) | `SUPPORTED` | Sets the fine-tuned logging levels for the node and any of its dependencies | +| [`DEBUG`](#debug-namespace) | [`debug_traceCall`](#debug_tracecall) | `SUPPORTED` | Performs a call and returns structured traces of the execution | +| [`DEBUG`](#debug-namespace) | [`debug_traceBlockByHash`](#debug_traceblockbyhash) | `SUPPORTED` | Returns structured traces for operations within the block of the specified block hash | +| [`DEBUG`](#debug-namespace) | [`debug_traceBlockByNumber`](#debug_traceblockbynumber) | `SUPPORTED` | Returns structured traces for operations within the block of the specified block number | +| [`DEBUG`](#debug-namespace) | [`debug_traceTransaction`](#debug_tracetransaction) | `SUPPORTED` | Returns a structured trace of the execution of the specified transaction | +| `ETH` | `eth_accounts` | `SUPPORTED` | Returns a list of addresses owned by client | +| [`ETH`](#eth-namespace) | [`eth_chainId`](#eth_chainid) | `SUPPORTED` | Returns the currently configured chain id
_(default is `260`)_ | +| `ETH` | `eth_coinbase` | `NOT IMPLEMENTED` | Returns the client coinbase address | +| [`ETH`](#eth-namespace) | [`eth_estimateGas`](#eth_estimategas) | `SUPPORTED` | Generates and returns an estimate of how much gas is necessary for the transaction to complete | +| [`ETH`](#eth-namespace) | [`eth_feeHistory`](#eth_feehistory) | `SUPPORTED` | Returns a collection of historical block gas data
_(hardcoded with gas price of `250_000_000`)_ | +| [`ETH`](#eth-namespace) | [`eth_gasPrice`](#eth_gasprice) | `SUPPORTED` | Returns the current price per gas in wei
_(hardcoded to `250_000_000`)_ | +| [`ETH`](#eth-namespace) | [`eth_getBalance`](#eth_getbalance) | `SUPPORTED` | Returns the balance of the account of given address | +| [`ETH`](#eth-namespace) | [`eth_getBlockByHash`](#eth_getblockbyhash) | `SUPPORTED` | Returns information about a block by block hash | +| [`ETH`](#eth-namespace) | [`eth_getBlockByNumber`](#eth_getblockbynumber) | `SUPPORTED` | Returns information about a block by block number | +| [`ETH`](#eth-namespace) | [`eth_getBlockTransactionCountByHash`](#eth_getblocktransactioncountbyhash) | `SUPPORTED` | Number of transactions in a block from a block matching the given block hash | +| [`ETH`](#eth-namespace) | [`eth_getBlockTransactionCountByNumber`](#eth_getblocktransactioncountbynumber) | `SUPPORTED` | Number of transactions in a block from a block matching the given block number | +| `ETH` | `eth_getCompilers` | `NOT IMPLEMENTED` | Returns a list of available compilers | +| [`ETH`](#eth-namespace) | [`eth_getTransactionByHash`](#eth_gettransactionbyhash) | `SUPPORTED` | Returns the information about a transaction requested by transaction hash | +| [`ETH`](#eth-namespace) | [`eth_getTransactionCount`](#eth_gettransactioncount) | `SUPPORTED` | Returns the number of transactions sent from an address | +| [`ETH`](#eth-namespace) | [`eth_blockNumber`](#eth_blocknumber) | `SUPPORTED` | Returns the number of the most recent block | +| [`ETH`](#eth-namespace) | [`eth_call`](#eth_call) | `SUPPORTED` | Executes a new message call immediately without creating a transaction on the block chain | +| [`ETH`](#eth-namespace) | [`eth_sendRawTransaction`](#eth_sendrawtransaction) | `SUPPORTED` | Creates new message call transaction or a contract creation for signed transactions | +| [`ETH`](#eth-namespace) | [`eth_getCode`](#eth_getcode) | `SUPPORTED` | Returns code at a given address | +| [`ETH`](#eth-namespace) | [`eth_getFilterChanges`](#`eth_getfilterchanges) | `SUPPORTED` | Polling method for a filter, which returns an array of logs, block hashes, or transaction hashes, depending on the filter type, which occurred since last poll | +| [`ETH`](#eth-namespace) | [`eth_getFilterLogs`](#eth_getfilterlogs) | `SUPPORTED` | Returns an array of all logs matching filter with given id | +| [`ETH`](#eth-namespace) | [`eth_getLogs`](#eth_getlogs) | `SUPPORTED` | Returns an array of all logs matching a given filter object | +| `ETH` | `eth_getProof` | `NOT IMPLEMENTED` | Returns the details for the account at the specified address and block number, the account's Merkle proof, and the storage values for the specified storage keys with their Merkle-proofs | +| [`ETH`](#eth-namespace) | [`eth_getStorageAt`](#eth_getstorageat) | `SUPPORTED` | Returns the value from a storage position at a given address | +| [`ETH`](#eth-namespace) | [`eth_getTransactionByBlockHashAndIndex`](#eth_gettransactionbyblockhashandindex) | `SUPPORTED` | Returns information about a transaction by block hash and transaction index position | +| [`ETH`](#eth-namespace) | [`eth_getTransactionByBlockNumberAndIndex`](#eth_gettransactionbyblocknumberandindex) | `SUPPORTED` | Returns information about a transaction by block number and transaction index position | +| [`ETH`](#eth-namespace) | [`eth_getTransactionReceipt`](#eth_gettransactionreceipt) | `SUPPORTED` | Returns the receipt of a transaction by transaction hash | +| `ETH` | `eth_getUncleByBlockHashAndIndex` | `NOT IMPLEMENTED` | Returns information about a uncle of a block by hash and uncle index position | +| `ETH` | `eth_getUncleByBlockNumberAndIndex` | `NOT IMPLEMENTED` | Returns information about a uncle of a block by hash and uncle index position | +| `ETH` | `eth_getUncleCountByBlockHash` | `NOT IMPLEMENTED` | Returns the number of uncles in a block from a block matching the given block hash | +| `ETH` | `eth_getUncleCountByBlockNumber` | `NOT IMPLEMENTED` | Returns the number of uncles in a block from a block matching the given block hash | +| `ETH` | `eth_getWork` | `NOT IMPLEMENTED` | Returns: An Array with the following elements
1: DATA, 32 Bytes - current block header pow-hash
2: DATA, 32 Bytes - the seed hash used for the DAG.
3: DATA, 32 Bytes - the boundary condition ("target"), 2^256 / difficulty | +| `ETH` | `eth_hashrate` | `NOT IMPLEMENTED` | Returns the number of hashes per second that the node is mining with | +| `ETH` | `eth_maxPriorityFeePerGas` | `NOT IMPLEMENTED` | Returns a `maxPriorityFeePerGas` value suitable for quick transaction inclusion | +| `ETH` | `eth_mining` | `NOT IMPLEMENTED` | Returns `true` if client is actively mining new blocks | +| [`ETH`](#eth-namespace) | [`eth_newBlockFilter`](#`eth_newblockfilter) | `SUPPORTED` | Creates a filter in the node, to notify when a new block arrives | +| [`ETH`](#eth-namespace) | [`eth_newFilter`](#`eth_newfilter) | `SUPPORTED` | Creates a filter object, based on filter options, to notify when the state changes (logs) | +| [`ETH`](#eth-namespace) | [`eth_newPendingTransactionFilter`](#`eth_newpendingtransactionfilter) | `SUPPORTED` | Creates a filter in the node, to notify when new pending transactions arrive | +| [`ETH`](#eth-namespace) | [`eth_protocolVersion`](#eth_protocolversion) | `SUPPORTED` | Returns the current ethereum protocol version | +| [`ETH`](#eth-namespace) | [`eth_sendTransaction`](#eth_sendtransaction) | `SUPPORTED` | Creates new message call transaction or a contract creation, if the data field contains code | +| `ETH` | `eth_sign` | `NOT IMPLEMENTED` | The sign method calculates an Ethereum specific signature with: `sign(keccak256("\x19Ethereum Signed Message:\n" + message.length + message)))` | +| `ETH` | `eth_signTransaction` | `NOT IMPLEMENTED` | Signs a transaction that can be submitted to the network at a later time using `eth_sendRawTransaction` | +| `ETH` | `eth_signTypedData` | `NOT IMPLEMENTED` | Identical to `eth_signTypedData_v4` | +| `ETH` | `eth_signTypedData_v4` | `NOT IMPLEMENTED` | Returns `Promise: Signature`. As in `eth_sign`, it is a hex encoded 129 byte array starting with `0x`. | +| `ETH` | `eth_submitHashrate` | `NOT IMPLEMENTED` | Used for submitting mining hashrate | +| `ETH` | `eth_submitWork` | `NOT IMPLEMENTED` | Used for submitting a proof-of-work solution | +| `ETH` | `eth_subscribe` | `NOT IMPLEMENTED` | Starts a subscription to a particular event | +| [`ETH`](#eth-namespace) | [`eth_syncing`](#eth_syncing) | `SUPPORTED` | Returns an object containing data about the sync status or `false` when not syncing | +| [`ETH`](#eth-namespace) | [`eth_uninstallFilter`](#`eth_uninstallfilter) | `SUPPORTED` | Uninstalls a filter with given id | +| `ETH` | `eth_unsubscribe` | `NOT IMPLEMENTED` | Cancel a subscription to a particular event | +| `EVM` | `evm_addAccount` | `NOT IMPLEMENTED` | Adds any arbitrary account | +| [`EVM`](#evm-namespace) | [`evm_increaseTime`](#evm_increasetime) | `SUPPORTED` | Jump forward in time by the given amount of time, in seconds | +| [`EVM`](#evm-namespace) | [`evm_mine`](#evm_mine) | `SUPPORTED` | Force a single block to be mined | +| `EVM` | `evm_removeAccount` | `NOT IMPLEMENTED` | Removes an account | +| [`EVM`](#evm-namespace) | [`evm_revert`](#evm_revert) | `SUPPORTED` | Revert the state of the blockchain to a previous snapshot | +| `EVM` | `evm_setAccountBalance` | `NOT IMPLEMENTED` | Sets the given account's balance to the specified WEI value | +| `EVM` | `evm_setAccountCode` | `NOT IMPLEMENTED` | Sets the given account's code to the specified data | +| `EVM` | `evm_setAccountNonce` | `NOT IMPLEMENTED` | Sets the given account's nonce to the specified value | +| `EVM` | `evm_setAccountStorageAt` | `NOT IMPLEMENTED` | Sets the given account's storage slot to the specified data | +| `EVM` | `evm_setAutomine` | `NOT IMPLEMENTED` | Enables or disables the automatic mining of new blocks with each new transaction submitted to the network | +| `EVM` | `evm_setBlockGasLimit` | `NOT IMPLEMENTED` | Sets the Block Gas Limit of the network | +| `EVM` | `evm_setIntervalMining` | `NOT IMPLEMENTED` | Enables (with a numeric argument greater than 0) or disables (with a numeric argument equal to 0), the automatic mining of blocks at a regular interval of milliseconds, each of which will include all pending transactions | +| [`EVM`](#evm-namespace) | [`evm_setNextBlockTimestamp`](#evm_setnextblocktimestamp) | `SUPPORTED` | Works like `evm_increaseTime`, but takes the exact timestamp that you want in the next block, and increases the time accordingly | +| [`EVM`](#evm-namespace) | [`evm_setTime`](#evm_settime) | `SUPPORTED` | Sets the internal clock time to the given timestamp | +| [`EVM`](#evm-namespace) | [`evm_snapshot`](#evm_snapshot) | `SUPPORTED` | Snapshot the state of the blockchain at the current block | +| `HARDHAT` | `hardhat_addCompilationResult` | `NOT IMPLEMENTED` | Add information about compiled contracts | +| `HARDHAT` | `hardhat_dropTransaction` | `NOT IMPLEMENTED` | Remove a transaction from the mempool | +| [`HARDHAT`](#hardhat-namespace) | [`hardhat_impersonateAccount`](#hardhat_impersonateaccount) | `SUPPORTED` | Impersonate an account | +| `HARDHAT` | `hardhat_getAutomine` | `NOT IMPLEMENTED` | Returns `true` if automatic mining is enabled, and `false` otherwise | +| `HARDHAT` | `hardhat_metadata` | `NOT IMPLEMENTED` | Returns the metadata of the current network | +| [`HARDHAT`](#hardhat-namespace) | [`hardhat_mine`](#hardhat_mine) | Mine any number of blocks at once, in constant time | +| `HARDHAT` | `hardhat_reset` | `NOT IMPLEMENTED` | Resets the state of the network | +| [`HARDHAT`](#hardhat-namespace) | [`hardhat_setBalance`](#hardhat_setbalance) | `SUPPORTED` | Modifies the balance of an account | +| [`HARDHAT`](#hardhat-namespace) | [`hardhat_setCode`](#hardhat_setcode) | `SUPPORTED` | Sets the bytecode of a given account | +| `HARDHAT` | `hardhat_setCoinbase` | `NOT IMPLEMENTED` | Sets the coinbase address | +| `HARDHAT` | `hardhat_setLoggingEnabled` | `NOT IMPLEMENTED` | Enables or disables logging in Hardhat Network | +| `HARDHAT` | `hardhat_setMinGasPrice` | `NOT IMPLEMENTED` | Sets the minimum gas price | +| `HARDHAT` | `hardhat_setNextBlockBaseFeePerGas` | `NOT IMPLEMENTED` | Sets the base fee per gas for the next block | +| `HARDHAT` | `hardhat_setPrevRandao` | `NOT IMPLEMENTED` | Sets the PREVRANDAO value of the next block | +| [`HARDHAT`](#hardhat-namespace) | [`hardhat_setNonce`](#hardhat_setnonce) | `SUPPORTED` | Sets the nonce of a given account | +| `HARDHAT` | `hardhat_setStorageAt` | `NOT IMPLEMENTED` | Sets the storage value at a given key for a given account | +| [`HARDHAT`](#hardhat-namespace) | [`hardhat_stopImpersonatingAccount`](#hardhat_stopimpersonatingaccount) | `SUPPORTED` | Stop impersonating an account after having previously used `hardhat_impersonateAccount` | +| [`NETWORK`](#network-namespace) | [`net_version`](#net_version) | `SUPPORTED` | Returns the current network id
_(default is `260`)_ | +| [`NETWORK`](#network-namespace) | [`net_peerCount`](#net_peercount) | `SUPPORTED` | Returns the number of peers currently connected to the client
_(hard-coded to `0`)_ | +| [`NETWORK`](#network-namespace) | [`net_listening`](#net_listening) | `SUPPORTED` | Returns `true` if the client is actively listening for network connections
_(hard-coded to `false`)_ | +| [`WEB3`](#web3-namespace) | [`web3_clientVersion`](#web3_clientversion) | `SUPPORTED` | Returns `zkSync/v2.0` | +| [`ZKS`](#zks-namespace) | [`zks_estimateFee`](#zks_estimateFee) | `SUPPORTED` | Gets the Fee estimation data for a given Request | +| `ZKS` | `zks_estimateGasL1ToL2` | `NOT IMPLEMENTED` | Estimate of the gas required for a L1 to L2 transaction | +| [`ZKS`](#zks-namespace) | [`zks_getAllAccountBalances`](#zks_getallaccountbalances) | `SUPPORTED` | Returns all balances for confirmed tokens given by an account address | +| [`ZKS`](#zks-namespace) | [`zks_getBridgeContracts`](#zks_getbridgecontracts) | `SUPPORTED` | Returns L1/L2 addresses of default bridges | +| [`ZKS`](#zks-namespace) | [`zks_getBlockDetails`](#zks_getblockdetails) | `SUPPORTED` | Returns additional zkSync-specific information about the L2 block | +| `ZKS` | `zks_getBytecodeByHash` | `NOT IMPLEMENTED` | Returns bytecode of a transaction given by its hash | +| [`ZKS`](#zks-namespace) | [`zks_getConfirmedTokens`](#zks_getconfirmedtokens) | `SUPPORTED` | Returns [address, symbol, name, and decimal] information of all tokens within a range of ids given by parameters `from` and `limit` | +| `ZKS` | `zks_getL1BatchBlockRange` | `NOT IMPLEMENTED` | Returns the range of blocks contained within a batch given by batch number | +| `ZKS` | `zks_getL1BatchDetails` | `NOT IMPLEMENTED` | Returns data pertaining to a given batch | +| `ZKS` | `zks_getL2ToL1LogProof` | `NOT IMPLEMENTED` | Given a transaction hash, and an index of the L2 to L1 log produced within the transaction, it returns the proof for the corresponding L2 to L1 log | +| `ZKS` | `zks_getL2ToL1MsgProof` | `NOT IMPLEMENTED` | Given a block, a sender, a message, and an optional message log index in the block containing the L1->L2 message, it returns the proof for the message sent via the L1Messenger system contract | +| `ZKS` | `zks_getMainContract` | `NOT IMPLEMENTED` | Returns the address of the zkSync Era contract | +| [`ZKS`](#zks-namespace) | [`zks_getRawBlockTransactions`](#zks_getrawblocktransactions) | `SUPPORTED` | Returns data of transactions in a block | +| `ZKS` | `zks_getTestnetPaymaster` | `NOT IMPLEMENTED` | Returns the address of the testnet paymaster | +| [`ZKS`](#zks-namespace) | [`zks_getTokenPrice`](#zks_getTokenPrice) | `SUPPORTED` | Gets the USD price of a token
_(`ETH` is hard-coded to `1_500`, while some others are `1`)_ | +| [`ZKS`](#zks-namespace) | [`zks_getTransactionDetails`](#zks_gettransactiondetails) | `SUPPORTED` | Returns data from a specific transaction given by the transaction hash | +| `ZKS` | `zks_L1BatchNumber` | `NOT IMPLEMENTED` | Returns the latest L1 batch number | +| `ZKS` | `zks_L1ChainId` | `NOT IMPLEMENTED` | Returns the chain id of the underlying L1 | + +## `CONFIG NAMESPACE` + +### `config_getShowCalls` + +[source](src/node/config.rs) + +Gets the current value of `show_calls` that's originally set with `--show-calls` option + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_getShowCalls","params": []}' +``` + +### `config_getCurrentTimestamp` + +[source](src/node/config.rs) + +Gets the value of `current_timestamp` for the node + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_getCurrentTimestamp","params": []}' +``` + +### `config_setShowCalls` + +[source](src/node/config.rs) + +Updates `show_calls` to print more detailed call traces + +#### Arguments + ++ `value: String ('None', 'User', 'System', 'All')` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_setShowCalls","params": ["all"]}' +``` + +### `config_setShowStorageLogs` + +[source](src/node/config.rs) + +Updates `show_storage_logs` to print storage log reads/writes + +#### Arguments + ++ `value: String ('None', 'Read', 'Write', 'All')` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_setShowStorageLogs","params": ["all"]}' +``` + +### `config_setShowVmDetails` + +[source](src/node/config.rs) + +Updates `show_vm_details` to print more detailed results from vm execution + +#### Arguments + ++ `value: String ('None', 'All')` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_setShowVmDetails","params": ["all"]}' +``` + +### `config_setShowGasDetails` + +[source](src/node/config.rs) + +Updates `show_gas_details` to print more details about gas estimation and usage + +#### Arguments + ++ `value: String ('None', 'All')` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_setShowGasDetails","params": ["all"]}' +``` + +### `config_setResolveHashes` + +[source](src/node/config.rs) + +Updates `resolve-hashes` to call OpenChain for human-readable ABI names in call traces + +#### Arguments + ++ `value: boolean` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_setResolveHashes","params": [true]}' +``` + +### `config_setLogLevel` + +[source](src/node/config.rs) + +Sets the logging level for the node and only displays the node logs. + +#### Arguments + ++ `level: LogLevel ('trace', 'debug', 'info', 'warn', 'error')` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_setLogLevel","params": ["trace"]}' +``` + +### `config_setLogging` + +[source](src/node/config.rs) + +Sets the fine-tuned logging levels for the node and any of its dependencies. +The directive format is comma-separated `module=level` for any number of modules. + +#### Arguments + ++ `directive: String (module=level,other_module=level)` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_setLogging","params": ["era_test_node=trace,hyper=debug"]}' +``` + +## `DEBUG NAMESPACE` + +### `debug_traceCall` + +[source](src/node/debug.rs) + +The `debug_traceCall` is similar to `eth_call` but returns call traces for each call. + +Currently calls can only be traced on the latest block. This is the default and hence the block argument can be omitted. + +The third argument mirrors the [`TraceConfig` of go-ethereum](https://geth.ethereum.org/docs/interacting-with-geth/rpc/ns-debug#traceconfig), but with the restriction that the only supported tracer is `CallTracer`. Memory, Stack and Storage traces are not supported. + +#### Arguments + ++ `transaction: Transaction` + ++ `block: BlockNumber` + ++ `tracer: TracerConfig` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "debug_traceCall", + "params": [{ + "to": "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "data": "0x0000", + "from": "0xa61464658AfeAf65CccaaFD3a512b69A83B77618", + "gas": "0x0000", + "gasPrice": "0x0000", + "value": "0x0000", + "nonce": "0x0000" + }, "latest"] + }' +``` + +### `debug_traceTransaction` + +[source](src/node/debug.rs) + +Returns call traces for the transaction with given hash. + +Currently only transactions executed on the dev node itself (ie, not from upstream when using fork mode) can be traced. + +The third argument mirrors the [`TraceConfig` of go-ethereum](https://geth.ethereum.org/docs/interacting-with-geth/rpc/ns-debug#traceconfig), but with the restriction that the only supported tracer is `CallTracer`. Memory, Stack and Storage traces are not supported. + +#### Arguments + +- `tx_hash: H256` + +- `options: TracerConfig` (optional) + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "debug_traceTransaction", + "params": [ + "0xd3a94ff697a573cb174ecce05126e952ecea6dee051526a3e389747ff86b0d99", + { "tracer": "callTracer", "tracerConfig": { "onlyTopCall": true } } + ] + }' +``` + +### `debug_traceBlockByHash` + +[source](src/node/debug.rs) + +Returns call traces for each transaction within a given block. + +Currently only transactions from blocks mined on the dev node itself (ie, not from upstream when using fork mode) can be traced. + +The third argument mirrors the [`TraceConfig` of go-ethereum](https://geth.ethereum.org/docs/interacting-with-geth/rpc/ns-debug#traceconfig), but with the restriction that the only supported tracer is `CallTracer`. Memory, Stack and Storage traces are not supported. + +#### Arguments + +- `blockHash: H256` + +- `options: TracerConfig` (optional) + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "debug_traceBlockByHash", + "params": [ + "0xd3a94ff697a573cb174ecce05126e952ecea6dee051526a3e389747ff86b0d99", + { "tracer": "callTracer", "tracerConfig": { "onlyTopCall": true } } + ] + }' +``` + +### `debug_traceBlockByNumber` + +[source](src/node/debug.rs) + +Returns call traces for each transaction within a given block. + +Currently only transactions from blocks mined on the dev node itself (ie, not from upstream when using fork mode) can be traced. + +The third argument mirrors the [`TraceConfig` of go-ethereum](https://geth.ethereum.org/docs/interacting-with-geth/rpc/ns-debug#traceconfig), but with the restriction that the only supported tracer is `CallTracer`. Memory, Stack and Storage traces are not supported. + +#### Arguments + +- `blockNumber: BlockNumber` + +- `options: TracerConfig` (optional) + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "debug_traceBlockByNumber", + "params": [ + "latest", + { "tracer": "callTracer", "tracerConfig": { "onlyTopCall": true } } + ] + }' +``` + +## `NETWORK NAMESPACE` + +### `net_version` + +[source](src/node/net.rs) + +Returns the current network id + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "net_version","params": []}' +``` + +### `net_peerCount` + +[source](src/node/net.rs) + +Returns the number of connected peers + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "net_peerCount","params": []}' +``` + +### `net_listening` + +[source](src/node/net.rs) + +Returns `true` if the node is listening for connections + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "net_listening","params": []}' +``` + +## `ETH NAMESPACE` + +### `eth_accounts` + +[source](src/node/eth.rs) + +Returns a list of addresses owned by client + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "eth_accounts","params": []}' +``` + +### `eth_chainId` + +[source](src/node/eth.rs) + +Returns the current chain id + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "eth_chainId","params": []}' +``` + +### `eth_estimateGas` + +[source](src/node/eth.rs) + +Generates and returns an estimate of how much gas is necessary to allow the transaction to complete + +#### Arguments + ++ `transaction: Transaction` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_estimateGas", + "params": [{ + "to": "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "data": "0x0000", + "from": "0xa61464658AfeAf65CccaaFD3a512b69A83B77618", + "gas": "0x0000", + "gasPrice": "0x0000", + "value": "0x0000", + "nonce": "0x0000" + }, "latest"] + }' +``` + +### `eth_feeHistory` + +[source](src/node/eth.rs) + +Returns the fee history for a given range of blocks + +#### Arguments + ++ `block_count: U64` ++ `newest_block: BlockNumber` ++ `reward_percentiles: Vec` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "eth_feeHistory","params": ["0x1", "latest", [25, 50 , 75]]}' +``` + +### `eth_gasPrice` + +[source](src/node/eth.rs) + +Returns the current price per gas in wei + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "eth_gasPrice","params": []}' +``` + +### `eth_getBalance` + +[source](src/node/eth.rs) + +Returns the balance of the account of given address + +#### Arguments + ++ `address: Address` + ++ `block: BlockNumber` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getBalance", + "params": ["0x0000000000000000000000000000000000000000", "latest"] +}' +``` + +### `eth_getBlockByHash` + +[source](src/node/eth.rs) + +Returns information about a block by block hash + +#### Arguments + ++ `hash: H256` + ++ `full: boolean` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getBlockByHash", + "params": ["0x0000000000000000000000000000000000000000000000000000000000000008", false] +}' +``` + +### `eth_getBlockByNumber` + +[source](src/node/eth.rs) + +Returns information about a block by block number + +#### Arguments + ++ `block: BlockNumber` + ++ `full: boolean` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getBlockByNumber", + "params": ["latest", true] +}' +``` + +### `eth_getBlockTransactionCountByHash` + +[source](src/node/eth.rs) + +Number of transactions in a block from a block matching the given block hash + +#### Arguments + ++ `block_hash: H256` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getBlockTransactionCountByHash", + "params": ["0x0000000000000000000000000000000000000000000000000000000000000008"] +}' +``` + +### `eth_getBlockTransactionCountByNumber` + +[source](src/node/eth.rs) + +Number of transactions in a block from a block matching the given block number + +#### Arguments + ++ `block_number: BlockNumber` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getBlockTransactionCountByNumber", + "params": ["latest"] +}' +``` + + +### `eth_getFilterChanges` + +[source](src/node/eth.rs) + +Polling method for a filter, which returns an array of logs, block hashes, or transaction hashes, depending on the filter type, which occurred since last poll + +#### Arguments + ++ `id: U256` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getFilterChanges", + "params": ["0x1"] +}' +``` + +### `eth_newBlockFilter` + +[source](src/node/eth.rs) + +Creates a filter in the node, to notify when a new block arrives + +#### Arguments + ++ _NONE__ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_newBlockFilter" +}' +``` + +### `eth_newFilter` + +[source](src/node/eth.rs) + +Creates a filter object, based on filter options, to notify when the state changes (logs) + +#### Arguments + ++ `filter: Filter` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_newFilter", + "params": [{ + "fromBlock": "0xa", + "toBlock": "0xff", + "address": "0x6b175474e89094c44da98b954eedeac495271d0f", + "topics": [] + }] +}' +``` + +### `eth_newPendingTransactionFilter` + +[source](src/node/eth.rs) + +Creates a filter in the node, to notify when new pending transactions arrive + +#### Arguments + ++ _NONE__ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_newPendingTransactionFilter" +}' +``` + +### `eth_uninstallFilter` + +[source](src/node/eth.rs) + +Uninstalls a filter with given id + +#### Arguments + ++ `id: U256` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_uninstallFilter", + "params": ["0x1"] +}' +``` + +### `eth_getFilterLogs` + +[source](src/node/eth.rs) + +Returns an array of all logs matching filter with given id + +#### Arguments + ++ `id: U256` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getFilterLogs", + "params": ["0x1"] +}' +``` + +### `eth_getLogs` + +[source](src/node/eth.rs) + +Returns an array of all logs matching a filter + +#### Arguments + ++ `filter: Filter` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getLogs", + "params": [{ + "fromBlock": "0xa", + "toBlock": "0xff", + "address": "0x6b175474e89094c44da98b954eedeac495271d0f", + "topics": [] + }] +}' +``` + +### `eth_getCode` + +[source](src/node/eth.rs) + +Returns code at a given address + +#### Arguments + ++ `address: Address` + ++ `block: BlockNumber` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getCode", + "params": ["0x0000000000000000000000000000000000000000", "latest"] +}' +``` + +### `eth_getTransactionByHash` + +[source](src/node/eth.rs) + +Returns the information about a transaction requested by transaction hash + +#### Arguments + ++ `hash: Hash` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getTransactionByHash", + "params": ["0x0000000000000000000000000000000000000000000000000000000000000000"] +}' +``` + +### `eth_getTransactionCount` + +[source](src/node/eth.rs) + +Returns the number of transactions sent from an address + +#### Arguments + ++ `address: Address` + ++ `block: BlockNumber` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getTransactionCount", + "params": ["0x0000000000000000000000000000000000000000", "latest"] +}' +``` + +### `eth_getTransactionReceipt` + +[source](src/node/eth.rs) + +Returns the transaction receipt for a given transaction hash + +#### Arguments + ++ `hash: H256` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getTransactionReceipt", + "params": ["0x0000000000000000000000000000000000000000"] +}' +``` + +### `eth_blockNumber` + +[source](src/node/eth.rs) + +Returns the number of most recent block + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "eth_blockNumber","params": []}' +``` + +### `eth_call` + +[source](src/node/eth.rs) + +Executes a new message call immediately without creating a transaction on the block chain + +#### Arguments + ++ `transaction: Transaction` + ++ `block: BlockNumber` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_call", + "params": [{ + "to": "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "data": "0x0000", + "from": "0xa61464658AfeAf65CccaaFD3a512b69A83B77618", + "gas": "0x0000", + "gasPrice": "0x0000", + "value": "0x0000", + "nonce": "0x0000" + }, "latest"] + }' +``` + +### `eth_sendRawTransaction` + +[source](src/node/eth.rs) + +Creates new message call transaction or a contract creation for signed transactions + +#### Arguments + ++ `transaction: Transaction` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "eth_sendRawTransaction","params": ["0x0000"] +}' +``` + +### `eth_syncing` + +[source](src/node/eth.rs) + +Returns syncing status of the node. This will always return `false`. + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "eth_syncing","params": [] +}' +``` + +### `eth_getStorageAt` + +[source](src/node/eth.rs) + +Returns the value from a storage position at a given address. + +#### Arguments + ++ `address: H160` ++ `position: U256` ++ `blockNumber: BlockIdVariant` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getStorageAt", + "params": ["0x123456789abcdef123456789abcdef1234567890", "0x0", "latest"] +}' +``` + +### `eth_getTransactionByBlockHashAndIndex` + +[source](src/node/eth.rs) + +Returns information about a transaction by block hash and transaction index position + +#### Arguments + ++ `block_hash: H256` ++ `index: U64` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getTransactionByBlockHashAndIndex", + "params": ["0x0000000000000000000000000000000000000000000000000000000000000008", "0x1"] +}' +``` + +### `eth_getTransactionByBlockNumberAndIndex` + +[source](src/node/eth.rs) + +Returns information about a transaction by block number and transaction index position + +#### Arguments + ++ `block_number: BlockNumber` ++ `index: U64` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getTransactionByBlockNumberAndIndex", + "params": ["latest", "0x1"] +}' +``` + +### `eth_protocolVersion` + +[source](src/node/eth.rs) + +Returns the current ethereum protocol version. + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_protocolVersion" +}' +``` + +### `eth_sendTransaction` + +[source](src/node/eth.rs) + +Creates new message call transaction or a contract creation, if the data field contains code. + +#### Arguments + ++ `transaction: TransactionRequest` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_sendTransaction", + "params": ["..."] +}' +``` + +## `HARDHAT NAMESPACE` + +### `hardhat_setBalance` + +[source](src/node/hardhat.rs) + +Sets the balance of the given address to the given balance. + +#### Arguments + ++ `address: Address` - The `Address` whose balance will be edited ++ `balance: U256` - The balance to set for the given address, in wei + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "hardhat_setBalance", + "params": [ + "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "0x1337" + ] + }' +``` + +### `hardhat_setNonce` + +[source](src/node/hardhat.rs) + +Modifies an account's nonce by overwriting it. +The new nonce must be greater than the existing nonce. + +#### Arguments + ++ `address: Address` - The `Address` whose nonce is to be changed ++ `nonce: U256` - The new nonce + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "hardhat_setNonce", + "params": [ + "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "0x1337" + ] + }' +``` + +### `hardhat_mine` + +[source](src/node/hardhat.rs) + +Sometimes you may want to advance the latest block number of the network by a large number of blocks. +One way to do this would be to call the evm_mine RPC method multiple times, but this is too slow if you want to mine thousands of blocks. +The hardhat_mine method can mine any number of blocks at once, in constant time. (It exhibits the same performance no matter how many blocks are mined.) + +#### Arguments + ++ `num_blocks: U64` - The number of blocks to mine. (Optional: defaults to 1) ++ `interval: U646` - The interval between the timestamps of each block, in seconds. (Optional: defaults to 1) + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "hardhat_mine", + "params": [ + "0xaa", + "0x100" + ] +}' + +``` +### `hardhat_impersonateAccount` + +[source](src/node/hardhat.rs) + +Begin impersonating account- subsequent transactions sent to the node will be committed as if they were initiated by the supplied address. + +#### Arguments + +- `address: Address` - The address to begin impersonating + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "hardhat_impersonateAccount", + "params": [ + "0x364d6D0333432C3Ac016Ca832fb8594A8cE43Ca6" + ] +}' +``` + +### `hardhat_stopImpersonatingAccount` + +[source](src/node/hardhat.rs) + +Stop impersonating account, should be used after calling `hardhat_impersonateAccount`. +Since we only impersonate one account at a time, the `address` argument is ignored and the current +impersonated account (if any) is cleared. + +#### Arguments + +- `address: Address` - (Optional) Argument accepted for compatibility and will be ignored + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "hardhat_stopImpersonatingAccount", + "params": [ + "0x364d6D0333432C3Ac016Ca832fb8594A8cE43Ca6" + ] +}' +``` + +### `hardhat_setCode` + +[source](src/node/hardhat.rs) + +Sets the code for a given address. + +#### Arguments + ++ `address: Address` - The `Address` whose code will be updated ++ `code: Bytes` - The code to set to + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "hardhat_setCode", + "params": [ + "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] + ] + }' +``` + +## `EVM NAMESPACE` + +### `evm_mine` + +[source](src/node/evm.rs) + +Mines an empty block + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "evm_mine","params": [] +}' +``` + +### `evm_increaseTime` + +[source](src/node/evm.rs) + +Increase the current timestamp for the node + +#### Arguments + ++ `time_delta_seconds: U64` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "evm_increaseTime","params": [10]}' +``` + +### `evm_setNextBlockTimestamp` + +[source](src/node/evm.rs) + +Sets the timestamp of the next block but doesn't mine one.. + +#### Arguments + ++ `timestamp: U64` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "evm_setNextBlockTimestamp","params": [1672527600]}' +``` + +### `evm_setTime` + +[source](src/node/evm.rs) + +Set the current timestamp for the node. Warning: This will allow you to move _backwards_ in time, which +may cause new blocks to appear to be mined before old blocks. This will result in an invalid state. + +#### Arguments + ++ `time: U64` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "evm_setTime","params": [1672527600]}' +``` + +### `evm_snapshot` + +[source](src/node/evm.rs) + +Snapshot the state of the blockchain at the current block. + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "evm_snapshot"}' +``` + +### `evm_revert` + +[source](src/node/evm.rs) + +Revert the state of the blockchain to a previous snapshot + +#### Arguments + ++ `snapshot_id: U64` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "evm_revert","params": ["0x1"]}' +``` + +## `WEB3 NAMESPACE` + +### `web3_clientVersion` + +[source](src/node/web3.rs) + +Returns the client version + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "web3_clientVersion" + }' +``` + +## `ZKS NAMESPACE` + +### `zks_estimateFee` + +[source](src/node/zks.rs) + +Generates and returns an estimate of how much gas is necessary to allow the transaction to complete + +#### Arguments + ++ `transaction: Transaction` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "zks_estimateFee", + "params": [{ + "to": "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "data": "0x0000", + "from": "0xa61464658AfeAf65CccaaFD3a512b69A83B77618", + "gas": "0x0000", + "gasPrice": "0x0000", + "value": "0x0000", + "nonce": "0x0000" + }] + }' +``` + +### `zks_getTokenPrice` + +[source](src/node/zks.rs) + +Returns the token price given an Address + +#### Arguments + ++ `address: Address` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "zks_getTokenPrice","params": ["0x0000000000000000000000000000000000000000"]}' +``` + +### `zks_getTransactionDetails` + +[source](src/node/zks.rs) + +Returns data from a specific transaction given by the transaction hash. + +#### Arguments + ++ `transactionHash: H256` + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "zks_getTransactionDetails","params": ["0xa5d62a85561295ed58f8daad4e9442691e6da4301a859f364d28a02917d6e04d"]}' +``` + +### `zks_getBlockDetails` + +[source](src/node/zks.rs) + +Returns additional zkSync-specific information about the L2 block. + +#### Arguments + ++ `block: u32` - The number of the block + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0", "id": 1, "method": "zks_getBlockDetails", "params": [ 140599 ]}' +``` + +### `zks_getBridgeContracts` + +[source](src/node/zks.rs) + +Returns L1/L2 addresses of default bridges. + +#### Arguments + ++ _NONE_ + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "2", + "method": "zks_getBridgeContracts" + }' +``` + +### `zks_getRawBlockTransactions` + +[source](src/node/zks.rs) + +Returns data of transactions in a block. + +#### Arguments + ++ `block: u32` - The number of the block + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0", "id": 1, "method": "zks_getRawBlockTransactions", "params": [ 140599 ]}' +``` + +### `zks_getConfirmedTokens` + +[source](src/zks.rs) + +Get list of the tokens supported by ZkSync Era. The tokens are returned in alphabetical order by their symbol. This means that the token id is its position in an alphabetically sorted array of tokens. + +#### Arguments + ++ `from: u32` - Offset of tokens ++ `limit: u8` - Limit of number of tokens to return + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "zks_getConfirmedTokens", + "params": [0, 100] +}' +``` + +### `zks_getAllAccountBalances` + +[source](src/zks.rs) + +Get all known balances for a given account. + +#### Arguments + ++ `address: Address` - The user address with balances to check. + +#### Status + +`SUPPORTED` + +#### Example + +```bash +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{ + "jsonrpc": "2.0", + "id": "1", + "method": "zks_getAllAccountBalances", + "params": ["0x364d6D0333432C3Ac016Ca832fb8594A8cE43Ca6"] +}' +``` diff --git a/.test-node-subtree/docs/release.md b/.test-node-subtree/docs/release.md new file mode 100644 index 00000000..fb63bee3 --- /dev/null +++ b/.test-node-subtree/docs/release.md @@ -0,0 +1,37 @@ +## Overview: `release.yaml` + +The release pipeline is aimed at automating the creation of GitHub releases, ensuring consistency and efficiency in our delivery process. The workflow is inspired by practices from [reth](https://github.com/paradigmxyz/reth/blob/main/.github/workflows/release.yml) and [Lighthouse](https://github.com/sigp/lighthouse/blob/693886b94176faa4cb450f024696cb69cda2fe58/.github/workflows/release.yml). + +### Release Workflow + +1. **Extract version**: The workflow extracts the version from the Git tag. The Git tag is being used to trigger the workflow. +2. **Build**: A matrix build is executed to generate binaries for multiple architectures. +3. **Draft Release**: A release draft is prepared with an automatically generated changelog and attached binaries. + +### First Run + +On the first execution of this workflow, the "All Changes" section of the release draft will be empty. This behaviour occurs because the action fetches commits between tags. Since there will be no prior tag for the first run, it does not populate this section. However, for subsequent runs, this section will feature all commits up to the given tag. The first run we will have to do so manually by running `git log main --oneline` and adding the commits. + +### Draft Release + +The workflow creates a **draft release** instead of a public one. This approach is intentional. It allows us to: + +- Add any additional commentary. +- Ensure checks and test CI jobs pass successfully. +- Prepare announcements or tweets related to the release prior to the release. +- Ensure it works as intended, and all the changes intended are present. + +Once the draft is reviewed and any required changes are made, we can finalize and create the release accordingly. + +**Note:** The binaries links in the table will not resolve until the release is made. That is, when a release is in "draft" form on GitHub, it is given an untagged-... URL. So when the release is made it will be tagged with the corresponding tag. + +### Triggering the Release Pipeline + +To trigger the release pipeline, you'll need to create and push a Git tag. Here are the commands: + +```bash +make new-release-tag +# Be sure to run the 'git push' command included in the output +``` + +The version number comes from [Cargo.toml](../Cargo.toml). This will trigger the `check.yaml` and `test.yaml` workflows, and `release.yaml`. \ No newline at end of file diff --git a/.test-node-subtree/docs/rustbook/.gitignore b/.test-node-subtree/docs/rustbook/.gitignore new file mode 100644 index 00000000..7585238e --- /dev/null +++ b/.test-node-subtree/docs/rustbook/.gitignore @@ -0,0 +1 @@ +book diff --git a/.test-node-subtree/docs/rustbook/book.toml b/.test-node-subtree/docs/rustbook/book.toml new file mode 100644 index 00000000..8c5f4029 --- /dev/null +++ b/.test-node-subtree/docs/rustbook/book.toml @@ -0,0 +1,6 @@ +[book] +authors = ["matter-labs"] +language = "en" +multilingual = false +src = "src" +title = "Era Test Node" diff --git a/.test-node-subtree/docs/rustbook/src/SUMMARY.md b/.test-node-subtree/docs/rustbook/src/SUMMARY.md new file mode 100644 index 00000000..22889fb4 --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/SUMMARY.md @@ -0,0 +1,22 @@ +# Summary + +- [Introduction](./introduction.md) + +# User Guide + +- [Installation](./installation.md) +- [Usage](./usage/README.md) + - [Basic](./usage/basic.md) + - [Forking Networks](./usage/fork.md) + - [Replay Remote Transactions](./usage/remote-tx.md) + - [Deploying Contracts](./usage/deploy-contracts.md) + - [Testing](./usage/testing.md) +- [Draft Chapter]() + +# Reference Guide + +- [Draft Chapter]() + +----------- + +[Contributors](misc/contributors.md) \ No newline at end of file diff --git a/.test-node-subtree/docs/rustbook/src/installation.md b/.test-node-subtree/docs/rustbook/src/installation.md new file mode 100644 index 00000000..e969f722 --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/installation.md @@ -0,0 +1,15 @@ +# Installation + +The node may be installed in the following ways: + +## zksync-cli +You can set up In-Memory Node quickly with `npx zksync-cli dev start`. +> *Note:* at the moment this method won't allow you to use additional features like forking networks or replaying transactions. + +## Release binary +Download `era-test-node`` from latest [Release](https://github.com/matter-labs/era-test-node/releases/latest) + +## Build from source +The project can be built from [source](https://github.com/matter-labs/era-test-node/releases/latest). Please note that you may +require some [prerequisites](https://github.com/matter-labs/era-test-node/tree/v0.1.0-alpha.6#-prerequisites) including the rust toolchain +to build the project from scratch. \ No newline at end of file diff --git a/.test-node-subtree/docs/rustbook/src/introduction.md b/.test-node-subtree/docs/rustbook/src/introduction.md new file mode 100644 index 00000000..9af4b5ac --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/introduction.md @@ -0,0 +1,10 @@ +# Introduction + +The In-memory node uses an in-memory database for storing state information and simplified hashmaps for tracking blocks and transactions. +In fork mode, it retrieves missing storage data from a remote source when not available locally. +Moreover it also uses the remote server (openchain) to resolve the ABI and topics to human readable names. + +You can visit the `era-test-node` repository [here](https://github.com/matter-labs/era-test-node) to learn more. + +Please keep in mind that `era-test-node` is still in its **alpha** stage, so some features might not be fully supported yet and may not work as fully intended. +It is [open-sourced](https://github.com/matter-labs/era-test-node) and contributions are welcomed. \ No newline at end of file diff --git a/.test-node-subtree/docs/rustbook/src/misc/contributors.md b/.test-node-subtree/docs/rustbook/src/misc/contributors.md new file mode 100644 index 00000000..0e5eb41a --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/misc/contributors.md @@ -0,0 +1,5 @@ +# Contributors + +Here is a list of the contributors who have helped improving mdBook. Big shout-out to them! + +* [nbaztec](https://github.com/nbaztec) \ No newline at end of file diff --git a/.test-node-subtree/docs/rustbook/src/usage/README.md b/.test-node-subtree/docs/rustbook/src/usage/README.md new file mode 100644 index 00000000..f61d7b51 --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/usage/README.md @@ -0,0 +1,50 @@ +# Usage + +In-Memory node can be utilized for a variety of reasons. + + +## Network Details +The `era_test_node` has the following default network configurations: + +* **L2 RPC:** `http://localhost:8011` +* **Network Id:** 260 + +These can be configured to your preference. + +> *Note:* Please note that the existing implementation does not facilitate communication with Layer 1. As a result, an L1 RPC is not available. + +## Caching + +The node will cache certain network request by default to disk in the `.cache` directory. Alternatively the caching can be disabled or set to in-memory only +via the `--cache=none|memory|disk` parameter. + +```bash +era_test_node --cache=none run +``` + +```bash +era_test_node --cache=memory run +``` + +Additionally when using `--cache=disk`, the cache directory may be specified via `--cache-dir` and the cache may +be reset on startup via `--reset-cache` parameters. +```bash +era_test_node --cache=disk --cache-dir=/tmp/foo --reset-cache run +``` + +## Pre-configured Rich Wallets + +The node also includes pre-configured "rich" accounts for testing: + +| Account Id | Private Key | +| ------------- | ------------- | +|0x36615Cf349d7F6344891B1e7CA7C72883F5dc049 | 0x7726827caac94a7f9e1b160f7ea819f172f7b6f9d2a97f992c38edeab82d4110 | +|0xa61464658AfeAf65CccaaFD3a512b69A83B77618 | 0xac1e735be8536c6534bb4f17f06f6afc73b2b5ba84ac2cfb12f7461b20c0bbe3 | +|0x0D43eB5B8a47bA8900d84AA36656c92024e9772e | 0xd293c684d884d56f8d6abd64fc76757d3664904e309a0645baf8522ab6366d9e | +|0xA13c10C0D5bd6f79041B9835c63f91de35A15883 | 0x850683b40d4a740aa6e745f889a6fdc8327be76e122f5aba645a5b02d0248db8 | +|0x8002cD98Cfb563492A6fB3E7C8243b7B9Ad4cc92 | 0xf12e28c0eb1ef4ff90478f6805b68d63737b7f33abfa091601140805da450d93 | +|0x4F9133D1d3F50011A6859807C837bdCB31Aaab13 | 0xe667e57a9b8aaa6709e51ff7d093f1c5b73b63f9987e4ab4aa9a5c699e024ee8 | +|0xbd29A1B981925B94eEc5c4F1125AF02a2Ec4d1cA | 0x28a574ab2de8a00364d5dd4b07c4f2f574ef7fcc2a86a197f65abaec836d1959 | +|0xedB6F5B4aab3dD95C7806Af42881FF12BE7e9daa | 0x74d8b3a188f7260f67698eb44da07397a298df5427df681ef68c45b34b61f998 | +|0xe706e60ab5Dc512C36A4646D719b889F398cbBcB | 0xbe79721778b48bcc679b78edac0ce48306a8578186ffcb9f2ee455ae6efeace1 | +|0xE90E12261CCb0F3F7976Ae611A29e84a6A85f424 | 0x3eb15da85647edd9a1159a4a13b9e7c56877c4eb33f614546d4db06a51868b1c | diff --git a/.test-node-subtree/docs/rustbook/src/usage/basic.md b/.test-node-subtree/docs/rustbook/src/usage/basic.md new file mode 100644 index 00000000..c6b03545 --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/usage/basic.md @@ -0,0 +1,33 @@ +# Basic + +Start the node: + +```sh +era_test_node run +``` + +The expected output will be as follows: + + +```log +12:34:56 [INFO] Starting network with chain id: L2ChainId(260) +12:34:56 [INFO] Rich Accounts +12:34:56 [INFO] ============= +12:34:56 [INFO] Account #0: 0x36615Cf349d7F6344891B1e7CA7C72883F5dc049 (1_000_000_000_000 ETH) +12:34:56 [INFO] Private Key: 0x7726827caac94a7f9e1b160f7ea819f172f7b6f9d2a97f992c38edeab82d4110 +12:34:56 [INFO] +12:34:56 [INFO] Account #1: 0xa61464658AfeAf65CccaaFD3a512b69A83B77618 (1_000_000_000_000 ETH) +12:34:56 [INFO] Private Key: 0xac1e735be8536c6534bb4f17f06f6afc73b2b5ba84ac2cfb12f7461b20c0bbe3 + +... + +12:34:56 [INFO] Account #9: 0xE90E12261CCb0F3F7976Ae611A29e84a6A85f424 (1_000_000_000_000 ETH) +12:34:56 [INFO] Private Key: 0x3eb15da85647edd9a1159a4a13b9e7c56877c4eb33f614546d4db06a51868b1c +12:34:56 [INFO] +12:34:56 [INFO] ======================================== +12:34:56 [INFO] Node is ready at 127.0.0.1:8011 +12:34:56 [INFO] ======================================== +``` + +> *Note:* When utilizing `era-test-node` with MetaMask, it's essential to note that any restart of the in-memory node will necessitate a reset of MetaMask's +cached account data (nonce, etc). To do this, navigate to `Settings`, then `Advanced`, and finally, select `Clear activity tab data`. diff --git a/.test-node-subtree/docs/rustbook/src/usage/bootloader.md b/.test-node-subtree/docs/rustbook/src/usage/bootloader.md new file mode 100644 index 00000000..210d7a7d --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/usage/bootloader.md @@ -0,0 +1 @@ +# Testing Bootloader diff --git a/.test-node-subtree/docs/rustbook/src/usage/deploy-contracts.md b/.test-node-subtree/docs/rustbook/src/usage/deploy-contracts.md new file mode 100644 index 00000000..82501d0d --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/usage/deploy-contracts.md @@ -0,0 +1,24 @@ +# Deploying Contracts + +For the deployment of your contracts, you have the flexibility to choose between two preferred methods: either by using Hardhat +with the `hardhat-zksync-deploy` and `hardhat-zksync-solc` plugins, or via `foundry-zksync`. +The following example will detail the process using `foundry-zksync`. + +Before proceeding, ensure that you've compiled your contracts using `zkforge zk-build`. +For instructions on how to do this, please refer to this [link](https://github.com/matter-labs/foundry-zksync#compile-with-zkforge-zk-build). + +```sh +zkforge zkc contracts/Greeter.sol:Greeter --constructor-args "ZkSync and Foundry" --private-key 7726827caac94a7f9e1b160f7ea819f172f7b6f9d2a97f992c38edeab82d4110 --rpc-url http://localhost:8011 --chain 260 +``` + +Here's an example of what you should expect to see: +```log +Deploying contract... ++-------------------------------------------------+ +Contract successfully deployed to address: 0x0a40ecde17dc16c4001bf0e4f5d5ff1818219b3b +Transaction Hash: 0x9d59bea38ca6f3cef365c23f339547bcc8ce28abb8344999ffffa5fa62c9ff8e +Gas used: 2570407 +Effective gas price: 500 +Block Number: 8072361 ++-------------------------------------------------+ +``` \ No newline at end of file diff --git a/.test-node-subtree/docs/rustbook/src/usage/fork.md b/.test-node-subtree/docs/rustbook/src/usage/fork.md new file mode 100644 index 00000000..2d01fdfb --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/usage/fork.md @@ -0,0 +1,87 @@ +# Forking Networks + +To fork the `sepolia-testnet`, use the following command: +```sh +era_test_node fork sepolia-testnet +``` + +You can also fork `mainnet` with +```sh +era_test_node fork mainnet +``` + +The expected output will be similar to the following: + +```log +14:50:12 INFO Creating fork from "https://mainnet.era.zksync.io:443" L1 block: L1BatchNumber(356201) L2 block: 21979120 with timestamp 1703083811, L1 gas price 41757081846 and protocol version: Some(Version18) +14:50:12 INFO Starting network with chain id: L2ChainId(260) +14:50:12 INFO +14:50:12 INFO Rich Accounts +14:50:12 INFO ============= +14:50:16 INFO Account #0: 0xBC989fDe9e54cAd2aB4392Af6dF60f04873A033A (1_000_000_000_000 ETH) +14:50:16 INFO Private Key: 0x3d3cbc973389cb26f657686445bcc75662b415b656078503592ac8c1abb8810e +14:50:16 INFO Mnemonic: mass wild lava ripple clog cabbage witness shell unable tribe rubber enter +14:50:16 INFO +14:50:16 INFO Account #1: 0x55bE1B079b53962746B2e86d12f158a41DF294A6 (1_000_000_000_000 ETH) +14:50:16 INFO Private Key: 0x509ca2e9e6acf0ba086477910950125e698d4ea70fa6f63e000c5a22bda9361c +14:50:16 INFO Mnemonic: crumble clutch mammal lecture lazy broken nominee visit gentle gather gym erupt + +... + +14:50:19 INFO Account #9: 0xe2b8Cb53a43a56d4d2AB6131C81Bd76B86D3AFe5 (1_000_000_000_000 ETH) +14:50:19 INFO Private Key: 0xb0680d66303a0163a19294f1ef8c95cd69a9d7902a4aca99c05f3e134e68a11a +14:50:19 INFO Mnemonic: increase pulp sing wood guilt cement satoshi tiny forum nuclear sudden thank +14:50:19 INFO +14:50:19 INFO ======================================== +14:50:19 INFO Node is ready at 127.0.0.1:8011 +14:50:19 INFO ======================================== +``` + +This command starts the node, forking it from the latest block on the zkSync Sepolia testnet. + +You also have the option to specify a custom http endpoint and a custom forking height, like so: + +```sh +# Usage: era_test_node fork --fork-at +era_test_node fork --fork-at 7000000 mainnet http://172.17.0.3:3060 +``` + +## Sending network calls + +You can send network calls against a running `era-test-node`. You can check the Goerli testnet LINK balance or mainnet USDT using `curl` or [foundry-zksync](https://github.com/matter-labs/foundry-zksync). + +To get started, launch the local in-memory node: +```sh +era_test_node fork goerli-testnet +``` + +Next, use curl to send a network call: +```sh +curl -X POST -H "Content-Type: application/json" --data '{"jsonrpc":"2.0","method":"eth_call","params":[{"to":"0x40609141Db628BeEE3BfAB8034Fc2D8278D0Cc78", "data":"0x06fdde03"}, "latest"],"id":1}' http://localhost:8011 +``` + +Here's an example of what you should expect to see: +```log +{"jsonrpc":"2.0","result":"0x00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000018436861696e4c696e6b20546f6b656e2028676f65726c69290000000000000000","id":1} +``` + +Or, if you prefer, use [foundry-zksync](https://github.com/matter-labs/foundry-zksync). Make sure to install and configure `foundry-zksync` before proceeding +(for installation instructions, please see this [link](https://github.com/matter-labs/foundry-zksync/tree/main#foundry-with-zksync-era-v01)): +```sh +zkcast call 0x40609141Db628BeEE3BfAB8034Fc2D8278D0Cc78 "name()(string)" --rpc-url http://localhost:8011 +``` + +Here's an example of what you should expect to see: +```log +ChainLink Token (goerli) +``` + +Retrieve the balance of a particular contract: +```sh +zkcast call 0x40609141Db628BeEE3BfAB8034Fc2D8278D0Cc78 "balanceOf(address)(uint256)" 0x40609141Db628BeEE3BfAB8034Fc2D8278D0Cc78 --rpc-url http://localhost:8011 +``` + +Here's an example of what you should expect to see: +```log +28762283719941475444443116625665 +``` \ No newline at end of file diff --git a/.test-node-subtree/docs/rustbook/src/usage/remote-tx.md b/.test-node-subtree/docs/rustbook/src/usage/remote-tx.md new file mode 100644 index 00000000..b976a16a --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/usage/remote-tx.md @@ -0,0 +1,90 @@ +# Replay Remote Transactions + +If you wish to replay a remote transaction locally for deep debugging, use the following command: + +```sh +# Usage: era_test_node replay_tx +era_test_node replay_tx sepolia-testnet 0x7119045573862797257e4441ff48bf5a3bc4d133a00d167c18dc955eda12cfac +``` + +For more detailed transaction information, such as call traces, add the `--show-calls` flag. If you want to see ABI names, add the `--resolve-hashes` flag. Here's an example: + +```sh +# Usage: era_test_node replay_tx +era_test_node --show-calls=user --resolve-hashes replay_tx sepolia-testnet 0x7119045573862797257e4441ff48bf5a3bc4d133a00d167c18dc955eda12cfac +``` + +Alternatively (if your node is already running) you can use `config_setShowCalls` and `config_setResolveHashes` RPC endpoints to configure these values. Here's an example: + +```sh +# era_test_node already running... + +# Set show-calls to User +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_setShowCalls","params": ["user"]}' + +# Enable resolve-hashes +curl --request POST \ + --url http://localhost:8011/ \ + --header 'content-type: application/json' \ + --data '{"jsonrpc": "2.0","id": "1","method": "config_setResolveHashes","params": [true]}' +``` + +Here's an example of what you could see when `--show-calls` and `--resolve-hashes` are configured: + +```log +Creating fork from "https://sepolia.era.zksync.dev:443" L1 block: L1BatchNumber(4513) L2 block: 14945 with timestamp 1703064786, L1 gas price 61083275326 and protocol version: Some(Version19) +Starting network with chain id: L2ChainId(300) +Running 1 transactions (one per batch) + +Validating 0x7119045573862797257e4441ff48bf5a3bc4d133a00d167c18dc955eda12cfac +Executing 0x7119045573862797257e4441ff48bf5a3bc4d133a00d167c18dc955eda12cfac +┌─────────────────────────┐ +│ TRANSACTION SUMMARY │ +└─────────────────────────┘ +Transaction: SUCCESS +Initiator: 0x4eaf936c172b5e5511959167e8ab4f7031113ca3 +Payer: 0x4eaf936c172b5e5511959167e8ab4f7031113ca3 +Gas - Limit: 2_487_330 | Used: 969_330 | Refunded: 1_518_000 +Use --show-gas-details flag or call config_setShowGasDetails to display more info + +==== Console logs: + +==== 22 call traces. Use --show-calls flag or call config_setShowCalls to display more info. + Call(Normal) 0x4eaf936c172b5e5511959167e8ab4f7031113ca3 validateTransaction(bytes32, bytes32, tuple) 1830339 + Call(Normal) 0x0000000000000000000000000000000000000001 0x89c19e9b 1766835 + Call(Normal) 0x4eaf936c172b5e5511959167e8ab4f7031113ca3 payForTransaction(bytes32, bytes32, tuple) 1789767 + Call(Normal) 0x4eaf936c172b5e5511959167e8ab4f7031113ca3 executeTransaction(bytes32, bytes32, tuple) 1671012 + Call(Mimic) 0x5d4fb5385ed95b65d1cd6a10ed9549613481ab2f 0x 1443393 + +==== 4 events +EthToken System Contract + Topics: + Transfer(address,address,uint256) + 0x0000000000000000000000004eaf936c172b5e5511959167e8ab4f7031113ca3 + 0x0000000000000000000000000000000000000000000000000000000000008001 + Data (Hex): 0x000000000000000000000000000000000000000000000000000c31dac51a6200 + +EthToken System Contract + Topics: + Transfer(address,address,uint256) + 0x0000000000000000000000000000000000000000000000000000000000008001 + 0x0000000000000000000000004eaf936c172b5e5511959167e8ab4f7031113ca3 + Data (Hex): 0x0000000000000000000000000000000000000000000000000009fc4d1bd4ad00 + +EthToken System Contract + Topics: + Transfer(address,address,uint256) + 0x0000000000000000000000004eaf936c172b5e5511959167e8ab4f7031113ca3 + 0x0000000000000000000000005d4fb5385ed95b65d1cd6a10ed9549613481ab2f + Data (Hex): 0x0000000000000000000000000000000000000000000000000090f705956a4008 + +EthToken System Contract + Topics: + Transfer(address,address,uint256) + 0x0000000000000000000000000000000000000000000000000000000000008001 + 0x0000000000000000000000004eaf936c172b5e5511959167e8ab4f7031113ca3 + Data (Hex): 0x000000000000000000000000000000000000000000000000000159273ab13800 +``` \ No newline at end of file diff --git a/.test-node-subtree/docs/rustbook/src/usage/testing.md b/.test-node-subtree/docs/rustbook/src/usage/testing.md new file mode 100644 index 00000000..0531fb89 --- /dev/null +++ b/.test-node-subtree/docs/rustbook/src/usage/testing.md @@ -0,0 +1,145 @@ +# Testing + +The node can be used to test different parameters of the system locally. + + +### Testing bootloader and system contracts +In-memory node allows testing of the currently compiled bootloader and system contracts. +This makes it possible to examine the effects of changes on already deployed contracts. + +> *Note:* These commands assume you have set `$ZKSYNC_HOME` in your shell profile file (e.g. `~/.bash_profile`, `~/.zshrc`) +to target your local copy of `era-test-node`. For instance: + +```sh +# Add path here: +export ZKSYNC_HOME=/path/to/era-test-node + +export PATH=$ZKSYNC_HOME/bin:$PATH +``` + +Firstly, you will need to preprocess and compile the contracts: +```sh +cd etc/system-contracts +yarn preprocess && yarn hardhat run ./scripts/compile-yul.ts +``` + +To use the locally compiled bootloader and system contracts, run: +```sh +RUST_LOG=vm=trace era_test_node --dev-use-local-contracts fork sepolia-testnet +``` + +## Writing and running tests locally +This section demonstrates how to author and execute tests locally against `era-test-node` using the `mocha` and `chai` testing frameworks. + +### Project configuration +Start by creating a new Hardhat project. If you need guidance, follow the [getting started guide](https://era.zksync.io/docs/tools/hardhat/getting-started.html). + +To incorporate the test libraries, execute: +```sh +yarn add -D mocha chai @types/mocha @types/chai +``` + +Add the following lines to your package.json in the root folder: +```json +"scripts": { + "test": "NODE_ENV=test hardhat test" +} +``` + +This script makes it possible to run tests in a Hardhat environment with the `NODE_ENV` env variable set as `test`. + +### Configuring tests +Adjust `hardhat.config.ts` to use the local node for testing: +> *Note:* Ensure `era-test-node` is running in another process before executing `yarn test`. + +```ts +import "@matterlabs/hardhat-zksync-deploy"; +import "@matterlabs/hardhat-zksync-solc"; + +module.exports = { + zksolc: { + version: "latest", + settings: {}, + }, + defaultNetwork: "zkSyncTestnet", + networks: { + hardhat: { + zksync: true, + }, + zkSyncTestnet: { + url: "http://localhost:8011", + ethNetwork: "http://localhost:8545", + zksync: true, + }, + }, + solidity: { + version: "0.8.17", + }, +}; +``` + +### Writing test scripts +Now, create your first test! Construct a test/main.test.ts file with the following code: + +```ts +import { expect } from "chai"; +import { Wallet, Provider, Contract } from "zksync-web3"; +import * as hre from "hardhat"; +import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; + +const RICH_WALLET_PK = "0x7726827caac94a7f9e1b160f7ea819f172f7b6f9d2a97f992c38edeab82d4110"; + +describe("Greeter", function () { + it("Should return the new greeting once it's changed", async function () { + const provider = Provider.getDefaultProvider(); + + const wallet = new Wallet(RICH_WALLET_PK, provider); + const deployer = new Deployer(hre, wallet); + + const artifact = await deployer.loadArtifact("Greeter"); + const greeter = await deployer.deploy(artifact, ["Hi"]); + + expect(await greeter.greet()).to.eq("Hi"); + + const setGreetingTx = await greeter.setGreeting("Hola, mundo!"); + // wait until the transaction is mined + await setGreetingTx.wait(); + + expect(await greeter.greet()).to.equal("Hola, mundo!"); + }); +}); +``` + +To run the test file, execute: +```sh +yarn test +``` + +Well done! You've successfully run your first local tests with zkSync Era and `era-test-node`. + +## CI/CD Testing with GitHub Actions +A GitHub Action is available for integrating era-test-node into your CI/CD environments. +This action offers high configurability and streamlines the process of testing your applications in an automated way. + +You can find this GitHub Action in the marketplace [here](https://github.com/marketplace/actions/era-test-node-action). + +### Example Usage +Below is an example yaml configuration to use the era-test-node GitHub Action in your workflow: +```yml +name: Run Era Test Node Action + +on: + push: + branches: [main] + +jobs: + build: + runs-on: ubuntu-latest + + steps: + - name: Checkout code + uses: actions/checkout@v2 + + - name: Run Era Test Node + uses: dutterbutter/era-test-node-action@latest +``` \ No newline at end of file diff --git a/.test-node-subtree/e2e-tests/.eslintrc.js b/.test-node-subtree/e2e-tests/.eslintrc.js new file mode 100644 index 00000000..03905dc1 --- /dev/null +++ b/.test-node-subtree/e2e-tests/.eslintrc.js @@ -0,0 +1,30 @@ +module.exports = { + env: { + es2021: true, + node: true, + }, + extends: ["eslint:recommended", "plugin:@typescript-eslint/recommended", "prettier"], + overrides: [ + { + env: { + node: true, + }, + files: [".eslintrc.{js,cjs}"], + parserOptions: { + sourceType: "script", + }, + }, + ], + parser: "@typescript-eslint/parser", + parserOptions: { + ecmaVersion: "latest", + sourceType: "module", + }, + plugins: ["@typescript-eslint", "mocha"], + + // Add rule exceptions here if they are too onerous to comply with + rules: { + "@typescript-eslint/ban-ts-comment": "off", + "mocha/no-exclusive-tests": "error", + }, +}; diff --git a/.test-node-subtree/e2e-tests/.gitignore b/.test-node-subtree/e2e-tests/.gitignore new file mode 100644 index 00000000..61748756 --- /dev/null +++ b/.test-node-subtree/e2e-tests/.gitignore @@ -0,0 +1,117 @@ +# nmv 08-08-2023 +# Ignore test results from mocha +test-results.json + +# Logs +logs +*.log +npm-debug.log* +yarn-debug.log* +yarn-error.log* +lerna-debug.log* +.vscode + +# hardhat artifacts +artifacts +cache + +# zksync artifacts +artifacts-zk +cache-zk + +# Diagnostic reports (https://nodejs.org/api/report.html) +report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json + +# Runtime data +pids +*.pid +*.seed +*.pid.lock + +# Directory for instrumented libs generated by jscoverage/JSCover +lib-cov + +# Coverage directory used by tools like istanbul +coverage +*.lcov + +# nyc test coverage +.nyc_output + +# Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files) +.grunt + +# Bower dependency directory (https://bower.io/) +bower_components + +# node-waf configuration +.lock-wscript + +# Compiled binary addons (https://nodejs.org/api/addons.html) +build/Release + +# Dependency directories +node_modules/ +jspm_packages/ + +# TypeScript v1 declaration files +typings/ + +# TypeScript cache +*.tsbuildinfo + +# Optional npm cache directory +.npm + +# Optional eslint cache +.eslintcache + +# Microbundle cache +.rpt2_cache/ +.rts2_cache_cjs/ +.rts2_cache_es/ +.rts2_cache_umd/ + +# Optional REPL history +.node_repl_history + +# Output of 'npm pack' +*.tgz + +# Yarn Integrity file +.yarn-integrity + +# dotenv environment variables file +.env +.env.test + +# parcel-bundler cache (https://parceljs.org/) +.cache + +# Next.js build output +.next + +# Nuxt.js build / generate output +.nuxt +dist + +# Gatsby files +.cache/ +# Comment in the public line in if your project uses Gatsby and *not* Next.js +# https://nextjs.org/blog/next-9-1#public-directory-support +# public + +# vuepress build output +.vuepress/dist + +# Serverless directories +.serverless/ + +# FuseBox cache +.fusebox/ + +# DynamoDB Local files +.dynamodb/ + +# TernJS port file +.tern-port diff --git a/.test-node-subtree/e2e-tests/.prettierrc b/.test-node-subtree/e2e-tests/.prettierrc new file mode 100644 index 00000000..3d9ca181 --- /dev/null +++ b/.test-node-subtree/e2e-tests/.prettierrc @@ -0,0 +1,8 @@ +{ + "printWidth": 80, + "useTabs": false, + "semi": true, + "singleQuote": false, + "trailingComma": "es5", + "bracketSpacing": true +} \ No newline at end of file diff --git a/.test-node-subtree/e2e-tests/.yarn/install-state.gz b/.test-node-subtree/e2e-tests/.yarn/install-state.gz new file mode 100644 index 00000000..57c21171 Binary files /dev/null and b/.test-node-subtree/e2e-tests/.yarn/install-state.gz differ diff --git a/.test-node-subtree/e2e-tests/.yarnrc.yml b/.test-node-subtree/e2e-tests/.yarnrc.yml new file mode 100644 index 00000000..3186f3f0 --- /dev/null +++ b/.test-node-subtree/e2e-tests/.yarnrc.yml @@ -0,0 +1 @@ +nodeLinker: node-modules diff --git a/.test-node-subtree/e2e-tests/README.md b/.test-node-subtree/e2e-tests/README.md new file mode 100644 index 00000000..67728364 --- /dev/null +++ b/.test-node-subtree/e2e-tests/README.md @@ -0,0 +1,14 @@ +# Era Test Node E2E Tests project + +This project is used for running e2e tests against `era_test_node` + +## Project structure + +- `/contracts`: smart contracts. +- `/test`: test files +- `hardhat.config.ts`: configuration file. + +## Commands + +- `yarn hardhat compile` will compile the contracts. +- `yarn test`: run tests. diff --git a/.test-node-subtree/e2e-tests/contracts/ERC20.sol b/.test-node-subtree/e2e-tests/contracts/ERC20.sol new file mode 100644 index 00000000..bd56500f --- /dev/null +++ b/.test-node-subtree/e2e-tests/contracts/ERC20.sol @@ -0,0 +1,33 @@ +// SPDX-License-Identifier: MIT +pragma solidity ^0.8.0; + +import "@openzeppelin/contracts/token/ERC20/ERC20.sol"; + +/** + * @dev This contract is for basic demonstration purposes only. It should not be used in production. + * It is for the convenience of the ERC20FixedPaymaster.sol contract and its corresponding test file. + */ +contract MyERC20 is ERC20 { + uint8 private _decimals; + + constructor( + string memory name, + string memory symbol, + uint8 decimals_ + ) payable ERC20(name, symbol) { + _decimals = decimals_; + } + + function mint(address _to, uint256 _amount) public returns (bool) { + _mint(_to, _amount); + return true; + } + + function decimals() public view override returns (uint8) { + return _decimals; + } + + function burn(address from, uint256 amount) public { + _burn(from, amount); + } +} \ No newline at end of file diff --git a/.test-node-subtree/e2e-tests/contracts/ERC20FixedPaymaster.sol b/.test-node-subtree/e2e-tests/contracts/ERC20FixedPaymaster.sol new file mode 100644 index 00000000..67c4a938 --- /dev/null +++ b/.test-node-subtree/e2e-tests/contracts/ERC20FixedPaymaster.sol @@ -0,0 +1,129 @@ +// SPDX-License-Identifier: MIT +pragma solidity ^0.8.0; + +import "@openzeppelin/contracts/token/ERC20/IERC20.sol"; + +import {IPaymaster, ExecutionResult, PAYMASTER_VALIDATION_SUCCESS_MAGIC} from "@matterlabs/zksync-contracts/l2/system-contracts/interfaces/IPaymaster.sol"; +import {IPaymasterFlow} from "@matterlabs/zksync-contracts/l2/system-contracts/interfaces/IPaymasterFlow.sol"; +import {TransactionHelper, Transaction} from "@matterlabs/zksync-contracts/l2/system-contracts/libraries/TransactionHelper.sol"; + +import "@matterlabs/zksync-contracts/l2/system-contracts/Constants.sol"; + +import "@openzeppelin/contracts/access/Ownable.sol"; + +/// @author Matter Labs +/// @notice This smart contract pays the gas fees for accounts with balance of a specific ERC20 token. It makes use of the approval-based flow paymaster. +contract ERC20FixedPaymaster is IPaymaster, Ownable { + uint256 constant PRICE_FOR_PAYING_FEES = 1; + + address public allowedToken; + + modifier onlyBootloader() { + require( + msg.sender == BOOTLOADER_FORMAL_ADDRESS, + "Only bootloader can call this method" + ); + // Continue execution if called from the bootloader. + _; + } + + constructor(address _erc20) { + allowedToken = _erc20; + } + + function validateAndPayForPaymasterTransaction( + bytes32, + bytes32, + Transaction calldata _transaction + ) + external + payable + onlyBootloader + returns (bytes4 magic, bytes memory context) + { + // By default we consider the transaction as accepted. + magic = PAYMASTER_VALIDATION_SUCCESS_MAGIC; + require( + _transaction.paymasterInput.length >= 4, + "The standard paymaster input must be at least 4 bytes long" + ); + + bytes4 paymasterInputSelector = bytes4( + _transaction.paymasterInput[0:4] + ); + if (paymasterInputSelector == IPaymasterFlow.approvalBased.selector) { + // While the transaction data consists of address, uint256 and bytes data, + // the data is not needed for this paymaster + (address token, uint256 amount, bytes memory data) = abi.decode( + _transaction.paymasterInput[4:], + (address, uint256, bytes) + ); + + // Verify if token is the correct one + require(token == allowedToken, "Invalid token"); + + // We verify that the user has provided enough allowance + address userAddress = address(uint160(_transaction.from)); + + address thisAddress = address(this); + + uint256 providedAllowance = IERC20(token).allowance( + userAddress, + thisAddress + ); + require( + providedAllowance >= PRICE_FOR_PAYING_FEES, + "Min allowance too low" + ); + + // Note, that while the minimal amount of ETH needed is tx.gasPrice * tx.gasLimit, + // neither paymaster nor account are allowed to access this context variable. + uint256 requiredETH = _transaction.gasLimit * + _transaction.maxFeePerGas; + + try + IERC20(token).transferFrom(userAddress, thisAddress, amount) + {} catch (bytes memory revertReason) { + // If the revert reason is empty or represented by just a function selector, + // we replace the error with a more user-friendly message + if (revertReason.length <= 4) { + revert("Failed to transferFrom from users' account"); + } else { + assembly { + revert(add(0x20, revertReason), mload(revertReason)) + } + } + } + + // The bootloader never returns any data, so it can safely be ignored here. + (bool success, ) = payable(BOOTLOADER_FORMAL_ADDRESS).call{ + value: requiredETH + }(""); + require( + success, + "Failed to transfer tx fee to the bootloader. Paymaster balance might not be enough." + ); + } else { + revert("Unsupported paymaster flow"); + } + } + + function postTransaction( + bytes calldata _context, + Transaction calldata _transaction, + bytes32, + bytes32, + ExecutionResult _txResult, + uint256 _maxRefundedGas + ) external payable override onlyBootloader { + } + + function withdraw(address _to) external onlyOwner { + // send paymaster funds to the owner + (bool success, ) = payable(_to).call{value: address(this).balance}(""); + require(success, "Failed to withdraw funds from paymaster."); + } + + receive() external payable {} + +} \ No newline at end of file diff --git a/.test-node-subtree/e2e-tests/contracts/ERC721.sol b/.test-node-subtree/e2e-tests/contracts/ERC721.sol new file mode 100644 index 00000000..2f352f6a --- /dev/null +++ b/.test-node-subtree/e2e-tests/contracts/ERC721.sol @@ -0,0 +1,33 @@ +// SPDX-License-Identifier: MIT +pragma solidity ^0.8.0; + +// Importing OpenZeppelin's ERC721 Implementation +import "@openzeppelin/contracts/token/ERC721/ERC721.sol"; +// Importing OpenZeppelin's Ownable contract to control ownership +import "@openzeppelin/contracts/access/Ownable.sol"; + +/** + * @dev This contract is for basic demonstration purposes only. It should not be used in production. + * It is for the convenience of the ERC721GatedPaymaster.sol contract and its corresponding test file. + */ +contract MyNFT is ERC721, Ownable { + // Maintains a counter of token IDs for uniqueness + uint256 public tokenCounter; + + // A constructor that gives my NFT a name and a symbol + constructor () ERC721 ("MyNFT", "MNFT"){ + // Initializes the tokenCounter to 0. Every new token has a unique ID starting from 1 + tokenCounter = 0; + } + + // Creates an NFT collection, with a unique token ID + function mint(address recipient) public onlyOwner returns (uint256) { + // Increases the tokenCounter by 1 and then mints the token with this new ID + _safeMint(recipient, tokenCounter); + + // Increments the token counter for the next token to be minted + tokenCounter = tokenCounter + 1; + + return tokenCounter; + } +} \ No newline at end of file diff --git a/.test-node-subtree/e2e-tests/contracts/ERC721GatedPaymaster.sol b/.test-node-subtree/e2e-tests/contracts/ERC721GatedPaymaster.sol new file mode 100644 index 00000000..b7b032fc --- /dev/null +++ b/.test-node-subtree/e2e-tests/contracts/ERC721GatedPaymaster.sol @@ -0,0 +1,96 @@ +// SPDX-License-Identifier: MIT +pragma solidity ^0.8.0; + +import "@openzeppelin/contracts/token/ERC721/IERC721.sol"; + +import {IPaymaster, ExecutionResult, PAYMASTER_VALIDATION_SUCCESS_MAGIC} from "@matterlabs/zksync-contracts/l2/system-contracts/interfaces/IPaymaster.sol"; +import {IPaymasterFlow} from "@matterlabs/zksync-contracts/l2/system-contracts/interfaces/IPaymasterFlow.sol"; +import {TransactionHelper, Transaction} from "@matterlabs/zksync-contracts/l2/system-contracts/libraries/TransactionHelper.sol"; + +import "@matterlabs/zksync-contracts/l2/system-contracts/Constants.sol"; + +import "@openzeppelin/contracts/access/Ownable.sol"; + +/// @author Matter Labs +/// @notice This smart contract pays the gas fees on behalf of users that are the owner of a specific NFT asset +contract ERC721GatedPaymaster is IPaymaster, Ownable { + IERC721 private immutable nft_asset; + + modifier onlyBootloader() { + require( + msg.sender == BOOTLOADER_FORMAL_ADDRESS, + "Only bootloader can call this method" + ); + // Continue execution if called from the bootloader. + _; + } + + // The constructor takes the address of the ERC721 contract as an argument. + // The ERC721 contract is the asset that the user must hold in order to use the paymaster. + constructor(address _erc721) { + nft_asset = IERC721(_erc721); // Initialize the ERC721 contract + } + + // The gas fees will be paid for by the paymaster if the user is the owner of the required NFT asset. + function validateAndPayForPaymasterTransaction( + bytes32, + bytes32, + Transaction calldata _transaction + ) + external + payable + onlyBootloader + returns (bytes4 magic, bytes memory context) + { + // By default we consider the transaction as accepted. + magic = PAYMASTER_VALIDATION_SUCCESS_MAGIC; + require( + _transaction.paymasterInput.length >= 4, + "The standard paymaster input must be at least 4 bytes long" + ); + + bytes4 paymasterInputSelector = bytes4( + _transaction.paymasterInput[0:4] + ); + + // Use the general paymaster flow + if (paymasterInputSelector == IPaymasterFlow.general.selector) { + address userAddress = address(uint160(_transaction.from)); + // Verify if user has the required NFT asset in order to use paymaster + require( + nft_asset.balanceOf(userAddress) > 0, + "User does not hold the required NFT asset and therefore must for their own gas!" + ); + // Note, that while the minimal amount of ETH needed is tx.gasPrice * tx.gasLimit, + // neither paymaster nor account are allowed to access this context variable. + uint256 requiredETH = _transaction.gasLimit * + _transaction.maxFeePerGas; + + // The bootloader never returns any data, so it can safely be ignored here. + (bool success, ) = payable(BOOTLOADER_FORMAL_ADDRESS).call{ + value: requiredETH + }(""); + } else { + revert("Invalid paymaster flow"); + } + } + + function postTransaction( + bytes calldata _context, + Transaction calldata _transaction, + bytes32, + bytes32, + ExecutionResult _txResult, + uint256 _maxRefundedGas + ) external payable override onlyBootloader { + } + + function withdraw(address payable _to) external onlyOwner { + // send paymaster funds to the owner + uint256 balance = address(this).balance; + (bool success, ) = _to.call{value: balance}(""); + require(success, "Failed to withdraw funds from paymaster."); + } + + receive() external payable {} +} \ No newline at end of file diff --git a/.test-node-subtree/e2e-tests/contracts/Greeter.sol b/.test-node-subtree/e2e-tests/contracts/Greeter.sol new file mode 100644 index 00000000..abbbc8a7 --- /dev/null +++ b/.test-node-subtree/e2e-tests/contracts/Greeter.sol @@ -0,0 +1,37 @@ +//SPDX-License-Identifier: Unlicense +pragma solidity ^0.8.0; + +import "@openzeppelin/contracts/access/Ownable.sol"; +import "hardhat/console.sol"; + +contract Greeter is Ownable { + string private greeting; + event LogString(string value); + + constructor(string memory _greeting) { + greeting = _greeting; + } + + function greet() public view returns (string memory) { + return greeting; + } + + function setGreeting(string memory _greeting) public { + console.log("setGreeting called"); + console.log(_greeting); + emit LogString(string.concat("Greeting is being updated to ", _greeting)); + + require( + keccak256(abi.encodePacked((_greeting))) != keccak256(abi.encodePacked(("test"))), + "Received a test value" + ); + greeting = _greeting; + } + + function setGreetingByOwner(string memory _greeting) public onlyOwner { + console.log("setGreetingByOwner called"); + console.log(_greeting); + emit LogString(string.concat("Greeting is being updated to ", _greeting)); + greeting = _greeting; + } +} diff --git a/.test-node-subtree/e2e-tests/contracts/Primary.sol b/.test-node-subtree/e2e-tests/contracts/Primary.sol new file mode 100644 index 00000000..0dcf8f37 --- /dev/null +++ b/.test-node-subtree/e2e-tests/contracts/Primary.sol @@ -0,0 +1,25 @@ +// SPDX-License-Identifier: MIT + +pragma solidity ^0.8.0; + +import "./Secondary.sol"; + +contract Primary { + Secondary secondary; + + constructor(address _secondary) { + secondary = Secondary(_secondary); + } + + function name() public pure returns (string memory) { + return "Primary"; + } + + function calculate(uint256 value) public returns (uint) { + return secondary.multiply(value); + } + + function shouldRevert() public view returns (uint) { + return secondary.shouldRevert(); + } +} diff --git a/.test-node-subtree/e2e-tests/contracts/Return5.sol b/.test-node-subtree/e2e-tests/contracts/Return5.sol new file mode 100644 index 00000000..f14a2709 --- /dev/null +++ b/.test-node-subtree/e2e-tests/contracts/Return5.sol @@ -0,0 +1,9 @@ +// SPDX-License-Identifier: GPL-3.0 + +pragma solidity >=0.8.2 <0.9.0; + +contract Return5 { + function value() public pure returns (uint8) { + return 5; + } +} diff --git a/.test-node-subtree/e2e-tests/contracts/Secondary.sol b/.test-node-subtree/e2e-tests/contracts/Secondary.sol new file mode 100644 index 00000000..a2ca5680 --- /dev/null +++ b/.test-node-subtree/e2e-tests/contracts/Secondary.sol @@ -0,0 +1,24 @@ +// SPDX-License-Identifier: MIT + +pragma solidity ^0.8.0; + +contract Secondary { + uint data; + + constructor(uint _data) { + data = _data; + } + + function name() public pure returns (string memory) { + return "Secondary"; + } + + function multiply(uint256 value) public view returns (uint) { + return data * value; + } + + function shouldRevert() public pure returns (uint) { + require(false, "This should revert"); + return 1; + } +} diff --git a/.test-node-subtree/e2e-tests/hardhat.config.ts b/.test-node-subtree/e2e-tests/hardhat.config.ts new file mode 100644 index 00000000..45378c06 --- /dev/null +++ b/.test-node-subtree/e2e-tests/hardhat.config.ts @@ -0,0 +1,35 @@ +import { HardhatUserConfig } from "hardhat/config"; + +import "@matterlabs/hardhat-zksync-deploy"; +import "@matterlabs/hardhat-zksync-solc"; +import "@nomiclabs/hardhat-ethers"; + +const config: HardhatUserConfig = { + zksolc: { + version: "latest", + settings: {}, + }, + defaultNetwork: "zkSyncTestnet", + networks: { + zkSyncTestnet: { + // Using 127.0.0.1 instead of localhost is necessary for CI builds + url: "http://127.0.0.1:8011", + // ethNetwork isn't necessary, but leaving for posterity + ethNetwork: "http://127.0.0.1:8545", + zksync: true, + }, + }, + solidity: { + version: "0.8.17", + }, + mocha: { + // Multiple reports allow view of the ouput in the console and as a JSON for the test result exporter in CI + reporter: "mocha-multi", + reporterOptions: { + spec: "-", + json: "test-results.json", + }, + }, +}; + +export default config; diff --git a/.test-node-subtree/e2e-tests/helpers/constants.ts b/.test-node-subtree/e2e-tests/helpers/constants.ts new file mode 100644 index 00000000..79d60d5b --- /dev/null +++ b/.test-node-subtree/e2e-tests/helpers/constants.ts @@ -0,0 +1,82 @@ +export const RichAccounts = [ + { + Account: "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + PrivateKey: "0x7726827caac94a7f9e1b160f7ea819f172f7b6f9d2a97f992c38edeab82d4110", + }, + { + Account: "0xa61464658AfeAf65CccaaFD3a512b69A83B77618", + PrivateKey: "0xac1e735be8536c6534bb4f17f06f6afc73b2b5ba84ac2cfb12f7461b20c0bbe3", + }, + { + Account: "0x0D43eB5B8a47bA8900d84AA36656c92024e9772e", + PrivateKey: "0xd293c684d884d56f8d6abd64fc76757d3664904e309a0645baf8522ab6366d9e", + }, + { + Account: "0xA13c10C0D5bd6f79041B9835c63f91de35A15883", + PrivateKey: "0x850683b40d4a740aa6e745f889a6fdc8327be76e122f5aba645a5b02d0248db8", + }, + { + Account: "0x8002cD98Cfb563492A6fB3E7C8243b7B9Ad4cc92", + PrivateKey: "0xf12e28c0eb1ef4ff90478f6805b68d63737b7f33abfa091601140805da450d93", + }, + { + Account: "0x4F9133D1d3F50011A6859807C837bdCB31Aaab13", + PrivateKey: "0xe667e57a9b8aaa6709e51ff7d093f1c5b73b63f9987e4ab4aa9a5c699e024ee8", + }, + { + Account: "0xbd29A1B981925B94eEc5c4F1125AF02a2Ec4d1cA", + PrivateKey: "0x28a574ab2de8a00364d5dd4b07c4f2f574ef7fcc2a86a197f65abaec836d1959", + }, + { + Account: "0xedB6F5B4aab3dD95C7806Af42881FF12BE7e9daa", + PrivateKey: "0x74d8b3a188f7260f67698eb44da07397a298df5427df681ef68c45b34b61f998", + }, + { + Account: "0xe706e60ab5Dc512C36A4646D719b889F398cbBcB", + PrivateKey: "0xbe79721778b48bcc679b78edac0ce48306a8578186ffcb9f2ee455ae6efeace1", + }, + { + Account: "0xE90E12261CCb0F3F7976Ae611A29e84a6A85f424", + PrivateKey: "0x3eb15da85647edd9a1159a4a13b9e7c56877c4eb33f614546d4db06a51868b1c", + }, + { + Account: "0xBC989fDe9e54cAd2aB4392Af6dF60f04873A033A", + PrivateKey: "0x3d3cbc973389cb26f657686445bcc75662b415b656078503592ac8c1abb8810e", + }, + { + Account: "0x55bE1B079b53962746B2e86d12f158a41DF294A6", + PrivateKey: "0x509ca2e9e6acf0ba086477910950125e698d4ea70fa6f63e000c5a22bda9361c", + }, + { + Account: "0xCE9e6063674DC585F6F3c7eaBe82B9936143Ba6C", + PrivateKey: "0x71781d3a358e7a65150e894264ccc594993fbc0ea12d69508a340bc1d4f5bfbc", + }, + { + Account: "0xd986b0cB0D1Ad4CCCF0C4947554003fC0Be548E9", + PrivateKey: "0x379d31d4a7031ead87397f332aab69ef5cd843ba3898249ca1046633c0c7eefe", + }, + { + Account: "0x87d6ab9fE5Adef46228fB490810f0F5CB16D6d04", + PrivateKey: "0x105de4e75fe465d075e1daae5647a02e3aad54b8d23cf1f70ba382b9f9bee839", + }, + { + Account: "0x78cAD996530109838eb016619f5931a03250489A", + PrivateKey: "0x7becc4a46e0c3b512d380ca73a4c868f790d1055a7698f38fb3ca2b2ac97efbb", + }, + { + Account: "0xc981b213603171963F81C687B9fC880d33CaeD16", + PrivateKey: "0xe0415469c10f3b1142ce0262497fe5c7a0795f0cbfd466a6bfa31968d0f70841", + }, + { + Account: "0x42F3dc38Da81e984B92A95CBdAAA5fA2bd5cb1Ba", + PrivateKey: "0x4d91647d0a8429ac4433c83254fb9625332693c848e578062fe96362f32bfe91", + }, + { + Account: "0x64F47EeD3dC749d13e49291d46Ea8378755fB6DF", + PrivateKey: "0x41c9f9518aa07b50cb1c0cc160d45547f57638dd824a8d85b5eb3bf99ed2bdeb", + }, + { + Account: "0xe2b8Cb53a43a56d4d2AB6131C81Bd76B86D3AFe5", + PrivateKey: "0xb0680d66303a0163a19294f1ef8c95cd69a9d7902a4aca99c05f3e134e68a11a", + }, +] as const; diff --git a/.test-node-subtree/e2e-tests/helpers/utils.ts b/.test-node-subtree/e2e-tests/helpers/utils.ts new file mode 100644 index 00000000..b948bfb2 --- /dev/null +++ b/.test-node-subtree/e2e-tests/helpers/utils.ts @@ -0,0 +1,60 @@ +import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; +import { expect } from "chai"; +import { Contract, Provider } from "zksync-web3"; +import * as hre from "hardhat"; +import { HttpNetworkUserConfig } from "hardhat/types"; + +/** + * * Deploy a contract using HardHat Deployer + * + * @param {Deployer} deployer - HardHat Deployer + * @param {string} contractName - Name of the contract, without file extension e.g. "Greeter" + * @param {string[]?} args - Optional arguments to pass to the contract constructor + * + * + * @returns {Promise} Returns a promise that resolves to the deployed contract + * @example + * const greeter = await deployContract(deployer, 'Greeter', ['Hi']); + */ +export async function deployContract(deployer: Deployer, contractName: string, args: string[] = []): Promise { + const artifact = await deployer.loadArtifact(contractName); + return await deployer.deploy(artifact, args); +} + +export function getTestProvider(): Provider { + const network = hre.userConfig.networks?.zkSyncTestnet; + return new Provider((network as HttpNetworkUserConfig).url); +} + +/** + * * Helper for validating error thrown contains string + * + * @param {any} method - Async function to be executed + * @param {string} errorMessage - String to be searched for in error message + * + * + * @returns {Promise} Returns an empty promise + * @example + * const action = async () => { + * await doSomething(); + * throw new Error("Error: Failure 100"); + * }; + * await expectThrowsAsync(action, "Failure 100"); + */ +export async function expectThrowsAsync( + // eslint-disable-next-line @typescript-eslint/ban-types + method: Function, + errorMessage: string +): Promise { + let error = null; + try { + await method(); + } catch (err) { + error = err; + } + + expect(error).to.be.an("Error"); + if (errorMessage) { + expect((error as Error).message).to.include(errorMessage); + } +} diff --git a/.test-node-subtree/e2e-tests/package.json b/.test-node-subtree/e2e-tests/package.json new file mode 100644 index 00000000..88ef6bee --- /dev/null +++ b/.test-node-subtree/e2e-tests/package.json @@ -0,0 +1,45 @@ +{ + "name": "era-test-node-e2e-tests", + "private": true, + "version": "1.0.0", + "main": "index.js", + "author": "The Matter Labs Team ", + "license": "MIT", + "devDependencies": { + "@matterlabs/eslint-config-vue": "^1.1.4", + "@matterlabs/hardhat-zksync-deploy": "^0.6.5", + "@matterlabs/hardhat-zksync-solc": "^0.4.2", + "@matterlabs/prettier-config": "^1.0.3", + "@matterlabs/zksync-contracts": "0.6.1", + "@nomiclabs/hardhat-ethers": "^2.2.3", + "@openzeppelin/contracts": "^4.9.3", + "@types/chai": "^4.3.4", + "@types/mocha": "^10.0.1", + "@types/node": "^18.17.12", + "@typescript-eslint/eslint-plugin": "latest", + "@typescript-eslint/parser": "latest", + "chai": "^4.3.7", + "eslint": "^8.48.0", + "eslint-config-prettier": "^9.0.0", + "eslint-plugin-mocha": "^10.2.0", + "ethers": "^5.7.2", + "hardhat": "^2.12.4", + "mocha": "^10.2.0", + "mocha-multi": "^1.1.7", + "prettier": "^3.0.3", + "ts-node": "^10.9.1", + "typescript": "^4.9.4", + "zksync-web3": "^0.14.3" + }, + "prettier": "@matterlabs/prettier-config", + "scripts": { + "build": "hardhat compile", + "clean": "hardhat clean", + "fmt": "prettier --check \"**/*.{js,ts,md}\"", + "fmt:fix": "prettier --write \"**/*.{js,ts,md}\"", + "lint": "eslint . --ext .ts", + "lint:fix": "eslint . --fix --ext .ts", + "test": "hardhat test --network zkSyncTestnet", + "typecheck": "tsc -p . --noEmit" + } +} diff --git a/.test-node-subtree/e2e-tests/test/debug-apis.test.ts b/.test-node-subtree/e2e-tests/test/debug-apis.test.ts new file mode 100644 index 00000000..9dd77328 --- /dev/null +++ b/.test-node-subtree/e2e-tests/test/debug-apis.test.ts @@ -0,0 +1,167 @@ +import { expect } from "chai"; +import { Wallet } from "zksync-web3"; +import * as hre from "hardhat"; +import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; +import { RichAccounts } from "../helpers/constants"; +import { deployContract, expectThrowsAsync, getTestProvider } from "../helpers/utils"; +import { BigNumber } from "ethers"; + +const provider = getTestProvider(); + +describe("debug_traceCall", function () { + it("Should return error if block is not 'latest' or unspecified", async function () { + expectThrowsAsync(async () => { + await provider.send("debug_traceCall", [{ to: "0xf39Fd6e51aad88F6F4ce6aB8827279cffFb92266" }, "earliest"]); + }, "block parameter should be 'latest' or unspecified"); + + expectThrowsAsync(async () => { + await provider.send("debug_traceCall", [{ to: "0xf39Fd6e51aad88F6F4ce6aB8827279cffFb92266" }, "1"]); + }, "block parameter should be 'latest' or unspecified"); + }); + + it("Should only trace top-level calls with onlyTopCall", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + + const deployer = new Deployer(hre, wallet); + const secondary = await deployContract(deployer, "Secondary", ["3"]); + await deployContract(deployer, "Primary", [secondary.address]); + + const result = await provider.send("debug_traceCall", [ + { + to: secondary.address, + data: secondary.interface.encodeFunctionData("multiply", ["4"]), + gas: "0x5f5e100", + }, + "latest", + { tracer: "callTracer", tracerConfig: { onlyTopCall: true } }, + ]); + + const { calls, revertReason } = result; + + // call should be successful + expect(revertReason).to.equal(null); + + // should have no subcalls + expect(calls.length).to.equal(0); + }); + + it("Should trace contract calls", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + + const deployer = new Deployer(hre, wallet); + const secondary = await deployContract(deployer, "Secondary", ["3"]); + const primary = await deployContract(deployer, "Primary", [secondary.address]); + + const result = await provider.send("debug_traceCall", [ + { + to: primary.address, + data: primary.interface.encodeFunctionData("calculate", ["4"]), + gas: "0x5f5e100", + }, + ]); + + const { calls, output, revertReason } = result; + + // call should be successful + expect(revertReason).to.equal(null); + + // subcall from primary to secondary contract should be present + const contract_call = calls[0].calls.at(-1).calls[0].calls[0]; + expect(contract_call.from.toLowerCase()).to.equal(primary.address.toLowerCase()); + expect(contract_call.to.toLowerCase()).to.equal(secondary.address.toLowerCase()); + + const [output_number] = primary.interface.decodeFunctionResult("calculate", output); + expect(output_number.toNumber()).to.equal(12); + }); +}); + +describe("debug_traceTransaction", function () { + it("Should return null if txn hash is unknown", async function () { + const result = await provider.send("debug_traceTransaction", [ + "0xd3a94ff697a573cb174ecce05126e952ecea6dee051526a3e389747ff86b0d99", + ]); + expect(result).to.equal(null); + }); + + it("Should trace prior transactions", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + + const txReceipt = await greeter.setGreeting("Luke Skywalker"); + const trace = await provider.send("debug_traceTransaction", [txReceipt.hash]); + + // call should be successful + expect(trace.error).to.equal(null); + expect(trace.calls.length).to.equal(1); + + // gas limit should match + expect(BigNumber.from(trace.gas).toNumber()).to.equal(txReceipt.gasLimit.toNumber()); + }); + + it("Should respect only_top_calls option", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + + const txReceipt = await greeter.setGreeting("Luke Skywalker"); + const trace = await provider.send("debug_traceTransaction", [ + txReceipt.hash, + { tracer: "callTracer", tracerConfig: { onlyTopCall: true } }, + ]); + + // call should be successful + expect(trace.error).to.equal(null); + expect(trace.calls.length).to.equal(0); + }); +}); + +describe("debug_traceBlockByHash", function () { + it("Should trace prior blocks", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + + const txReceipt = await greeter.setGreeting("Luke Skywalker"); + const latestBlock = await provider.getBlock("latest"); + const block = await provider.getBlock(latestBlock.number - 1); + + const traces = await provider.send("debug_traceBlockByHash", [block.hash]); + + // block should have 1 traces + expect(traces.length).to.equal(1); + + // should contain trace for our tx + const trace = traces[0].result; + expect(trace.input).to.equal(txReceipt.data); + }); +}); + +describe("debug_traceBlockByNumber", function () { + it("Should trace prior blocks", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + + const txReceipt = await greeter.setGreeting("Luke Skywalker"); + + // latest block will be empty, check we get no traces for it + const empty_traces = await provider.send("debug_traceBlockByNumber", ["latest"]); + expect(empty_traces.length).to.equal(0); + + // latest - 1 should contain our traces + const latestBlock = await provider.getBlock("latest"); + const traces = await provider.send("debug_traceBlockByNumber", [(latestBlock.number - 1).toString(16)]); + + // block should have 1 traces + expect(traces.length).to.equal(1); + + // should contain trace for our tx + const trace = traces[0].result; + expect(trace.input).to.equal(txReceipt.data); + }); +}); diff --git a/.test-node-subtree/e2e-tests/test/erc20-fixed-paymaster.test.ts b/.test-node-subtree/e2e-tests/test/erc20-fixed-paymaster.test.ts new file mode 100644 index 00000000..6cbc3551 --- /dev/null +++ b/.test-node-subtree/e2e-tests/test/erc20-fixed-paymaster.test.ts @@ -0,0 +1,115 @@ +import { expect } from "chai"; +import { Wallet, Provider, Contract, utils } from "zksync-web3"; +import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; +import * as ethers from "ethers"; +import * as hre from "hardhat"; + +import { expectThrowsAsync, getTestProvider } from "../helpers/utils"; +import { RichAccounts } from "../helpers/constants"; + +describe("ERC20FixedPaymaster", function () { + let provider: Provider; + let richWallet: Wallet; + let deployer: Deployer; + let userWallet: Wallet; + let paymaster: Contract; + let greeter: Contract; + let token: Contract; + + before(async function () { + provider = getTestProvider(); + richWallet = new Wallet(RichAccounts[0].PrivateKey, provider); + deployer = new Deployer(hre, richWallet); + + // Setup new wallet + const emptyWallet = Wallet.createRandom(); + userWallet = new Wallet(emptyWallet.privateKey, provider); + + // Deploy ERC20 token, Paymaster, and Greeter + let artifact = await deployer.loadArtifact("MyERC20"); + token = await deployer.deploy(artifact, ["MyToken", "MyToken", 18]); + artifact = await deployer.loadArtifact("ERC20FixedPaymaster"); + paymaster = await deployer.deploy(artifact, [token.address]); + artifact = await deployer.loadArtifact("Greeter"); + greeter = await deployer.deploy(artifact, ["Hi"]); + + // Fund Paymaster + await provider.send("hardhat_setBalance", [paymaster.address, ethers.utils.parseEther("10")._hex]); + }); + + async function executeGreetingTransaction(user: Wallet, greeting: string) { + const gasPrice = await provider.getGasPrice(); + const token_address = token.address.toString(); + + const paymasterParams = utils.getPaymasterParams(paymaster.address, { + type: "ApprovalBased", + token: token_address, + minimalAllowance: ethers.BigNumber.from(1), + // empty bytes as testnet paymaster does not use innerInput + innerInput: new Uint8Array(), + }); + + // Estimate gasLimit via paymaster + const gasLimit = await greeter.connect(user).estimateGas.setGreeting(greeting, { + customData: { + gasPerPubdata: utils.DEFAULT_GAS_PER_PUBDATA_LIMIT, + paymasterParams, + }, + }); + + const setGreetingTx = await greeter.connect(user).setGreeting(greeting, { + maxPriorityFeePerGas: ethers.BigNumber.from(0), + maxFeePerGas: gasPrice, + gasLimit, + customData: { + gasPerPubdata: utils.DEFAULT_GAS_PER_PUBDATA_LIMIT, + paymasterParams, + }, + }); + + await setGreetingTx.wait(); + } + + it("user with MyERC20 token can update message for free", async function () { + // Arrange + const initialMintAmount = ethers.utils.parseEther("3"); + const success = await token.mint(userWallet.address, initialMintAmount); + await success.wait(); + + const userInitialTokenBalance = await token.balanceOf(userWallet.address); + const userInitialETHBalance = await userWallet.getBalance(); + const initialPaymasterBalance = await provider.getBalance(paymaster.address); + + // Act + await executeGreetingTransaction(userWallet, "Hola, mundo!"); + + // Assert + const finalETHBalance = await userWallet.getBalance(); + const finalUserTokenBalance = await token.balanceOf(userWallet.address); + const finalPaymasterBalance = await provider.getBalance(paymaster.address); + + expect(await greeter.greet()).to.equal("Hola, mundo!"); + expect(initialPaymasterBalance.gt(finalPaymasterBalance)).to.be.true; + expect(userInitialETHBalance).to.eql(finalETHBalance); + expect(userInitialTokenBalance.gt(finalUserTokenBalance)).to.be.true; + }); + + it("should allow owner to withdraw all funds", async function () { + // Arrange + // Act + const tx = await paymaster.connect(richWallet).withdraw(userWallet.address); + await tx.wait(); + + // Assert + const finalContractBalance = await provider.getBalance(paymaster.address); + expect(finalContractBalance).to.eql(ethers.BigNumber.from(0)); + }); + + it("should prevent non-owners from withdrawing funds", async function () { + const action = async () => { + await paymaster.connect(userWallet).withdraw(userWallet.address); + }; + + await expectThrowsAsync(action, "Ownable: caller is not the owner"); + }); +}); diff --git a/.test-node-subtree/e2e-tests/test/erc721-gated-paymaster.test.ts b/.test-node-subtree/e2e-tests/test/erc721-gated-paymaster.test.ts new file mode 100644 index 00000000..3229136b --- /dev/null +++ b/.test-node-subtree/e2e-tests/test/erc721-gated-paymaster.test.ts @@ -0,0 +1,118 @@ +import { expect } from "chai"; +import { Wallet, Provider, Contract, utils } from "zksync-web3"; +import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; +import * as ethers from "ethers"; +import * as hre from "hardhat"; + +import { expectThrowsAsync, getTestProvider } from "../helpers/utils"; +import { RichAccounts } from "../helpers/constants"; + +describe("ERC721GatedPaymaster", function () { + let provider: Provider; + let wallet: Wallet; + let deployer: Deployer; + let nftUserWallet: Wallet; + let paymaster: Contract; + let greeter: Contract; + let erc721: Contract; + + before(async function () { + provider = getTestProvider(); + wallet = new Wallet(RichAccounts[0].PrivateKey, provider); + deployer = new Deployer(hre, wallet); + + // Setup new wallets + nftUserWallet = Wallet.createRandom(); + nftUserWallet = new Wallet(nftUserWallet.privateKey, provider); + + // Deploy NFT and Paymaster + let artifact = await deployer.loadArtifact("MyNFT"); + erc721 = await deployer.deploy(artifact, []); + artifact = await deployer.loadArtifact("ERC721GatedPaymaster"); + paymaster = await deployer.deploy(artifact, [erc721.address]); + artifact = await deployer.loadArtifact("Greeter"); + greeter = await deployer.deploy(artifact, ["Hi"]); + + // Fund Paymaster + await provider.send("hardhat_setBalance", [paymaster.address, ethers.utils.parseEther("10")._hex]); + + // Assign NFT to nftUserWallet + const tx = await erc721.mint(nftUserWallet.address); + await tx.wait(); + }); + + async function executeGreetingTransaction(user: Wallet, greeting: string) { + const gasPrice = await provider.getGasPrice(); + const paymasterParams = utils.getPaymasterParams(paymaster.address, { + type: "General", + // empty bytes as paymaster does not use innerInput + innerInput: new Uint8Array(), + }); + + // estimate gasLimit via paymaster + const gasLimit = await greeter.connect(user).estimateGas.setGreeting(greeting, { + customData: { + gasPerPubdata: utils.DEFAULT_GAS_PER_PUBDATA_LIMIT, + paymasterParams: paymasterParams, + }, + }); + + const setGreetingTx = await greeter.connect(user).setGreeting(greeting, { + maxPriorityFeePerGas: ethers.BigNumber.from(0), + maxFeePerGas: gasPrice, + gasLimit, + customData: { + gasPerPubdata: utils.DEFAULT_GAS_PER_PUBDATA_LIMIT, + paymasterParams, + }, + }); + + await setGreetingTx.wait(); + } + + it("should not pay for gas fees when user has NFT", async function () { + // Arrange + const initialBalance = await nftUserWallet.getBalance(); + + // Act + await executeGreetingTransaction(nftUserWallet, "Hello World"); + + // Assert + expect(await greeter.greet()).to.equal("Hello World"); + const newBalance = await nftUserWallet.getBalance(); + expect(newBalance).to.eql(initialBalance); + }); + + it("should require the user to have the NFT", async function () { + // Arrange + let normalUserWallet = Wallet.createRandom(); + normalUserWallet = new Wallet(normalUserWallet.privateKey, provider); + + // Act + const action = async () => { + await executeGreetingTransaction(normalUserWallet, "Hello World"); + }; + + // Assert + await expectThrowsAsync(action, "User does not hold the required NFT asset and therefore must for their own gas!"); + }); + + it("should allow owner to withdraw all funds", async function () { + // Arrange + // Act + const tx = await paymaster.connect(wallet).withdraw(nftUserWallet.address); + await tx.wait(); + + // Assert + const finalContractBalance = await provider.getBalance(paymaster.address); + expect(finalContractBalance).to.eql(ethers.BigNumber.from(0)); + }); + + it("should prevent non-owners from withdrawing funds", async function () { + const action = async () => { + await paymaster.connect(nftUserWallet).withdraw(nftUserWallet.address); + }; + + await expectThrowsAsync(action, "Ownable: caller is not the owner"); + }); +}); diff --git a/.test-node-subtree/e2e-tests/test/eth-apis.test.ts b/.test-node-subtree/e2e-tests/test/eth-apis.test.ts new file mode 100644 index 00000000..6c8d8e11 --- /dev/null +++ b/.test-node-subtree/e2e-tests/test/eth-apis.test.ts @@ -0,0 +1,20 @@ +import { expect } from "chai"; +import { getTestProvider } from "../helpers/utils"; +import { RichAccounts } from "../helpers/constants"; +import { ethers } from "ethers"; + +const provider = getTestProvider(); + +describe("eth_accounts", function () { + it("Should return rich accounts", async function () { + // Arrange + const richAccounts = RichAccounts.map((ra) => ethers.utils.getAddress(ra.Account)).sort(); + + // Act + const response: string[] = await provider.send("eth_accounts", []); + const accounts = response.map((addr) => ethers.utils.getAddress(addr)).sort(); + + // Assert + expect(accounts).to.deep.equal(richAccounts); + }); +}); diff --git a/.test-node-subtree/e2e-tests/test/evm-apis.test.ts b/.test-node-subtree/e2e-tests/test/evm-apis.test.ts new file mode 100644 index 00000000..5bdd8d70 --- /dev/null +++ b/.test-node-subtree/e2e-tests/test/evm-apis.test.ts @@ -0,0 +1,132 @@ +import { expect } from "chai"; +import * as hre from "hardhat"; +import { deployContract, getTestProvider } from "../helpers/utils"; +import { Wallet } from "zksync-web3"; +import { RichAccounts } from "../helpers/constants"; +import { BigNumber, ethers } from "ethers"; +import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; + +const provider = getTestProvider(); + +describe("evm_mine", function () { + it("Should mine one block", async function () { + // Arrange + const startingBlock = await provider.getBlock("latest"); + + // Act + await provider.send("evm_mine", []); + + // Assert + const latestBlock = await provider.getBlock("latest"); + expect(latestBlock.number).to.equal(startingBlock.number + 1); + }); +}); + +describe("evm_increaseTime", function () { + it("Should increase current timestamp of the node", async function () { + // Arrange + const timeIncreaseInSeconds = 13; + const wallet = new Wallet(RichAccounts[0].PrivateKey, provider); + const userWallet = Wallet.createRandom().connect(provider); + let expectedTimestamp: number = await provider.send("config_getCurrentTimestamp", []); + expectedTimestamp += timeIncreaseInSeconds * 1000; + + // Act + await provider.send("evm_increaseTime", [timeIncreaseInSeconds]); + + await wallet.sendTransaction({ + to: userWallet.address, + value: ethers.utils.parseEther("0.1"), + }); + expectedTimestamp += 2; // New transaction will add two blocks + + // Assert + const newBlockTimestamp = (await provider.getBlock("latest")).timestamp; + expect(newBlockTimestamp).to.equal(expectedTimestamp); + }); +}); + +describe("evm_setNextBlockTimestamp", function () { + it("Should set current timestamp of the node to specific value", async function () { + // Arrange + const timeIncreaseInMS = 123; + let expectedTimestamp: number = await provider.send("config_getCurrentTimestamp", []); + expectedTimestamp += timeIncreaseInMS; + const wallet = new Wallet(RichAccounts[0].PrivateKey, provider); + const userWallet = Wallet.createRandom().connect(provider); + + // Act + await provider.send("evm_setNextBlockTimestamp", [expectedTimestamp]); + + await wallet.sendTransaction({ + to: userWallet.address, + value: ethers.utils.parseEther("0.1"), + }); + expectedTimestamp += 2; // New transaction will add two blocks + + // Assert + const newBlockTimestamp = (await provider.getBlock("latest")).timestamp; + expect(newBlockTimestamp).to.equal(expectedTimestamp); + }); +}); + +describe("evm_setTime", function () { + it("Should set current timestamp of the node to specific value", async function () { + // Arrange + const timeIncreaseInMS = 123; + let expectedTimestamp: number = await provider.send("config_getCurrentTimestamp", []); + expectedTimestamp += timeIncreaseInMS; + const wallet = new Wallet(RichAccounts[0].PrivateKey, provider); + const userWallet = Wallet.createRandom().connect(provider); + + // Act + await provider.send("evm_setTime", [expectedTimestamp]); + + await wallet.sendTransaction({ + to: userWallet.address, + value: ethers.utils.parseEther("0.1"), + }); + expectedTimestamp += 2; // New transaction will add two blocks + + // Assert + const newBlockTimestamp = (await provider.getBlock("latest")).timestamp; + expect(newBlockTimestamp).to.equal(expectedTimestamp); + }); +}); + +describe("evm_snapshot", function () { + it("Should return incrementing snapshot ids", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + expect(await greeter.greet()).to.eq("Hi"); + + // Act + const snapshotId1: string = await provider.send("evm_snapshot", []); + const snapshotId2: string = await provider.send("evm_snapshot", []); + + // Assert + expect(await greeter.greet()).to.eq("Hi"); + expect(BigNumber.from(snapshotId2).toString()).to.eq(BigNumber.from(snapshotId1).add(1).toString()); + }); +}); + +describe("evm_revert", function () { + it("Should revert with correct snapshot id", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + expect(await greeter.greet()).to.eq("Hi"); + const snapshotId = await provider.send("evm_snapshot", []); + const setGreetingTx = await greeter.setGreeting("Hola, mundo!"); + await setGreetingTx.wait(); + expect(await greeter.greet()).to.equal("Hola, mundo!"); + + // Act + const reverted: boolean = await provider.send("evm_revert", [snapshotId]); + + // Assert + expect(await greeter.greet()).to.eq("Hi"); + expect(reverted).to.be.true; + }); +}); diff --git a/.test-node-subtree/e2e-tests/test/hardhat-apis.test.ts b/.test-node-subtree/e2e-tests/test/hardhat-apis.test.ts new file mode 100644 index 00000000..760d4e17 --- /dev/null +++ b/.test-node-subtree/e2e-tests/test/hardhat-apis.test.ts @@ -0,0 +1,149 @@ +import { expect } from "chai"; +import { Wallet } from "zksync-web3"; +import { deployContract, getTestProvider } from "../helpers/utils"; +import { RichAccounts } from "../helpers/constants"; +import { ethers } from "hardhat"; +import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; +import * as hre from "hardhat"; +import { keccak256 } from "ethers/lib/utils"; +import { BigNumber } from "ethers"; + +const provider = getTestProvider(); + +describe("hardhat_setBalance", function () { + it("Should update the balance of an account", async function () { + // Arrange + const userWallet = Wallet.createRandom().connect(provider); + const newBalance = ethers.utils.parseEther("42"); + + // Act + await provider.send("hardhat_setBalance", [userWallet.address, newBalance._hex]); + + // Assert + const balance = await userWallet.getBalance(); + expect(balance.eq(newBalance)).to.true; + }); +}); + +describe("hardhat_setNonce", function () { + it("Should update the nonce of an account", async function () { + // Arrange + const userWallet = Wallet.createRandom().connect(provider); + const newNonce = 42; + + // Act + await provider.send("hardhat_setNonce", [userWallet.address, ethers.utils.hexlify(newNonce)]); + + // Assert + const nonce = await userWallet.getNonce(); + expect(nonce).to.equal(newNonce); + }); +}); + +describe("hardhat_mine", function () { + it("Should mine multiple blocks with a given interval", async function () { + // Arrange + const numberOfBlocks = 100; + const intervalInSeconds = 60; + const startingBlock = await provider.getBlock("latest"); + const startingTimestamp: number = await provider.send("config_getCurrentTimestamp", []); + + // Act + await provider.send("hardhat_mine", [ + ethers.utils.hexlify(numberOfBlocks), + ethers.utils.hexlify(intervalInSeconds), + ]); + + // Assert + const latestBlock = await provider.getBlock("latest"); + expect(latestBlock.number).to.equal(startingBlock.number + numberOfBlocks, "Block number mismatch"); + expect(latestBlock.timestamp).to.equal( + startingTimestamp + (numberOfBlocks - 1) * intervalInSeconds * 1000 + 1, + "Timestamp mismatch" + ); + }); +}); + +describe("hardhat_impersonateAccount & hardhat_stopImpersonatingAccount", function () { + it("Should allow transfers of funds without knowing the Private Key", async function () { + // Arrange + const userWallet = Wallet.createRandom().connect(provider); + const beforeBalance = await provider.getBalance(RichAccounts[0].Account); + + // Act + await provider.send("hardhat_impersonateAccount", [RichAccounts[0].Account]); + + const signer = await ethers.getSigner(RichAccounts[0].Account); + const tx = { + to: userWallet.address, + value: ethers.utils.parseEther("0.42"), + }; + + const recieptTx = await signer.sendTransaction(tx); + await recieptTx.wait(); + + // Assert + expect((await userWallet.getBalance()).eq(ethers.utils.parseEther("0.42"))).to.true; + expect((await provider.getBalance(RichAccounts[0].Account)).eq(beforeBalance.sub(ethers.utils.parseEther("0.42")))) + .to.true; + }); +}); + +describe("hardhat_setCode", function () { + it("Should set code at an address", async function () { + // Arrange + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const address = "0x1000000000000000000000000000000000001111"; + const artifact = await deployer.loadArtifact("Return5"); + const contractCode = [...ethers.utils.arrayify(artifact.deployedBytecode)]; + + // Act + await provider.send("hardhat_setCode", [address, contractCode]); + + // Assert + const result = await provider.send("eth_call", [ + { + to: address, + data: keccak256(ethers.utils.toUtf8Bytes("value()")).substring(0, 10), + from: wallet.address, + gas: "0x1000", + gasPrice: "0x0ee6b280", + value: "0x0", + nonce: "0x1", + }, + "latest", + ]); + expect(BigNumber.from(result).toNumber()).to.eq(5); + }); + + it("Should update code with a different smart contract", async function () { + // Arrange + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + expect(await greeter.greet()).to.eq("Hi"); + const artifact = await deployer.loadArtifact("Return5"); + const newContractCode = [...ethers.utils.arrayify(artifact.deployedBytecode)]; + + // Act + await provider.send("hardhat_setCode", [greeter.address, newContractCode]); + + // Assert + const result = await provider.send("eth_call", [ + { + to: greeter.address, + data: keccak256(ethers.utils.toUtf8Bytes("value()")).substring(0, 10), + from: wallet.address, + gas: "0x1000", + gasPrice: "0x0ee6b280", + value: "0x0", + nonce: "0x1", + }, + "latest", + ]); + expect(BigNumber.from(result).toNumber()).to.eq(5); + }); +}); diff --git a/.test-node-subtree/e2e-tests/test/main.test.ts b/.test-node-subtree/e2e-tests/test/main.test.ts new file mode 100644 index 00000000..a5739dad --- /dev/null +++ b/.test-node-subtree/e2e-tests/test/main.test.ts @@ -0,0 +1,106 @@ +import { expect } from "chai"; +import { Wallet } from "zksync-web3"; +import * as hre from "hardhat"; +import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; +import { ethers } from "ethers"; +import { RichAccounts } from "../helpers/constants"; +import { deployContract, expectThrowsAsync, getTestProvider } from "../helpers/utils"; +import { Log, TransactionReceipt } from "zksync-web3/build/src/types"; + +const provider = getTestProvider(); + +describe("Greeter Smart Contract", function () { + it("Should return the new greeting once it's changed", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + + expect(await greeter.greet()).to.eq("Hi"); + + const setGreetingTx = await greeter.setGreeting("Hola, mundo!"); + // wait until the transaction is mined + await setGreetingTx.wait(); + + expect(await greeter.greet()).to.equal("Hola, mundo!"); + }); + + it("should prevent non-owners from setting greeting", async function () { + const action = async () => { + const wallet = new Wallet(RichAccounts[0].PrivateKey, provider); + const deployer = new Deployer(hre, wallet); + + // setup user wallet with 3 ETH + const userWallet = Wallet.createRandom().connect(provider); + await wallet.sendTransaction({ + to: userWallet.address, + value: ethers.utils.parseEther("3"), + }); + + // deploy Greeter contract + const artifact = await deployer.loadArtifact("Greeter"); + const greeter = await deployer.deploy(artifact, ["Hello, world!"]); + + // should revert + const tx = await greeter.connect(userWallet).setGreetingByOwner("Hola, mundo!"); + await tx.wait(); + }; + + await expectThrowsAsync(action, "Ownable: caller is not the owner"); + }); + + it("Should produce event logs", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + + expect(await greeter.greet()).to.eq("Hi"); + + const setGreetingTx = await greeter.setGreeting("Luke Skywalker"); + const receipt: TransactionReceipt = await setGreetingTx.wait(); + + // Validate log is created + expect(receipt.logs.length).to.greaterThanOrEqual(1); + const setGreetingLog = receipt.logs[0]; + expect(setGreetingLog.address).to.equal(greeter.address); + + const eventInterface = new ethers.utils.Interface(["event LogString(string value)"]); + expect(eventInterface.parseLog(setGreetingLog).args[0]).to.equal("Greeting is being updated to Luke Skywalker"); + }); + + it("Should filter event logs", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + expect(await greeter.greet()).to.eq("Hi"); + + const setGreetingTx = await greeter.setGreeting("Luke Skywalker"); + let receipt: TransactionReceipt = await setGreetingTx.wait(); + + // Create filter + const topic = receipt.logs[0].topics[0]; + const filterId = await provider.send("eth_newFilter", [ + { + fromBlock: "earliest", + toBlock: "latest", + topics: [topic], + }, + ]); + + // New filter should be empty + let filterChanges: Log[] = await provider.send("eth_getFilterChanges", [filterId]); + expect(filterChanges).to.empty; + + // Emit logs and filter should not be empty + receipt = await (await greeter.setGreeting("Darth Vader")).wait(); + filterChanges = await provider.send("eth_getFilterChanges", [filterId]); + + expect(filterChanges.length).to.eq(1); + expect(filterChanges[0].transactionHash).to.eq(receipt.transactionHash); + expect(filterChanges[0].blockHash).to.eq(receipt.blockHash); + expect(filterChanges[0].removed).to.eq(false); + const eventInterface = new ethers.utils.Interface(["event LogString(string value)"]); + expect(eventInterface.parseLog(filterChanges[0]).args[0]).to.equal("Greeting is being updated to Darth Vader"); + }); +}); diff --git a/.test-node-subtree/e2e-tests/test/web3-apis.test.ts b/.test-node-subtree/e2e-tests/test/web3-apis.test.ts new file mode 100644 index 00000000..a17ad1d0 --- /dev/null +++ b/.test-node-subtree/e2e-tests/test/web3-apis.test.ts @@ -0,0 +1,17 @@ +import { expect } from "chai"; +import { getTestProvider } from "../helpers/utils"; + +const provider = getTestProvider(); + +describe("web3_clientVersion", function () { + it("Should return zkSync/v2.0", async function () { + // Arrange + const expectedClientVersion = "zkSync/v2.0"; + + // Act + const response: string = await provider.send("web3_clientVersion", []); + + // Assert + expect(response).to.equal(expectedClientVersion); + }); +}); diff --git a/.test-node-subtree/e2e-tests/test/zks-apis.test.ts b/.test-node-subtree/e2e-tests/test/zks-apis.test.ts new file mode 100644 index 00000000..a27e04dd --- /dev/null +++ b/.test-node-subtree/e2e-tests/test/zks-apis.test.ts @@ -0,0 +1,179 @@ +import { expect } from "chai"; +import { deployContract, getTestProvider } from "../helpers/utils"; +import { Wallet } from "zksync-web3"; +import { RichAccounts } from "../helpers/constants"; +import { BigNumber, ethers } from "ethers"; +import * as hre from "hardhat"; +import { TransactionRequest } from "zksync-web3/build/src/types"; +import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; + +const provider = getTestProvider(); + +interface Fee { + gas_limit: ethers.BigNumber; + gas_per_pubdata_limit: ethers.BigNumber; + max_fee_per_gas: ethers.BigNumber; + max_priority_fee_per_gas: ethers.BigNumber; +} + +describe("zks_estimateFee", function () { + it("Should return fee estimation data for transfer of 1 ETH", async function () { + // Arrange + const wallet = new Wallet(RichAccounts[0].PrivateKey, provider); + const userWallet = Wallet.createRandom().connect(provider); + const transaction: TransactionRequest = { + from: wallet.address, + to: userWallet.address, + value: ethers.utils.parseEther("1")._hex, + }; + + // Act + const response: Fee = await provider.send("zks_estimateFee", [transaction]); + + // Assert + expect(ethers.BigNumber.from(response.gas_limit)).to.eql(ethers.BigNumber.from("621166"), "Unexpected gas_limit"); + expect(ethers.BigNumber.from(response.gas_per_pubdata_limit)).to.eql( + ethers.BigNumber.from("4080"), + "Unexpected gas_per_pubdata_limit" + ); + expect(ethers.BigNumber.from(response.max_fee_per_gas)).to.eql( + ethers.BigNumber.from("250000000"), + "Unexpected max_fee_per_gas" + ); + expect(ethers.BigNumber.from(response.max_priority_fee_per_gas)).to.eql( + ethers.BigNumber.from("0"), + "Unexpected max_priority_fee_per_gas" + ); + }); +}); + +describe("zks_getTokenPrice", function () { + it("Should return fake token Price for ETH", async function () { + // Arrange + const ethAddress = "0x0000000000000000000000000000000000000000"; + + // Act + const response: string = await provider.send("zks_getTokenPrice", [ethAddress]); + + // Assert + expect(response).to.equal("1500"); + }); +}); + +describe("zks_getTransactionDetails", function () { + it("Should return transaction details for locally-executed transactions", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + + const txReceipt = await greeter.setGreeting("Luke Skywalker"); + const details = await provider.send("zks_getTransactionDetails", [txReceipt.hash]); + + expect(details["status"]).to.equal("included"); + expect(details["initiatorAddress"].toLowerCase()).to.equal(wallet.address.toLowerCase()); + }); +}); + +describe("zks_getBridgeContracts", function () { + it("Should return default values", async function () { + const bridgeAddresses = await provider.send("zks_getBridgeContracts", []); + + expect(bridgeAddresses).to.deep.equal({ + l1Erc20DefaultBridge: "0x0000000000000000000000000000000000000000", + l2Erc20DefaultBridge: "0x0000000000000000000000000000000000000000", + l1WethBridge: null, + l2WethBridge: null, + }); + }); +}); + +describe("zks_getBlockDetails", function () { + it("Should return block details for locally-produced blocks", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + await greeter.setGreeting("Luke Skywalker"); + + const latestBlock = await provider.getBlock("latest"); + const details = await provider.send("zks_getBlockDetails", [latestBlock.number]); + + expect(details["timestamp"]).to.equal(latestBlock.timestamp); + }); +}); + +describe("zks_getBytecodeByHash", function () { + it("Should fetch the stored bytecode at address", async function () { + // Arrange + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + const artifact = await deployer.loadArtifact("Greeter"); + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + const deployedContract = await greeter.deployTransaction.wait(); + expect(await greeter.greet()).to.eq("Hi"); + + // get the bytecode hash from the event + const contractDeployedHash = ethers.utils + .keccak256(ethers.utils.toUtf8Bytes("ContractDeployed(address,bytes32,address)")) + .substring(2); + const logs = await provider.send("eth_getLogs", [ + { + fromBlock: ethers.utils.hexlify(deployedContract.blockNumber), + toBlock: ethers.utils.hexlify(deployedContract.blockNumber), + address: "0x0000000000000000000000000000000000008006", // L2 Deployer address + topics: [contractDeployedHash], + }, + ]); + expect(logs).to.not.be.empty; + expect(logs[0].topics).to.have.lengthOf(4); + const bytecodeHash = logs[0].topics[2]; + + // Act + const bytecode = await provider.send("zks_getBytecodeByHash", [bytecodeHash]); + + // Assert + expect(ethers.utils.hexlify(bytecode)).to.equal(artifact.deployedBytecode); + }); +}); + +describe("zks_getRawBlockTransactions", function () { + it("Should return transactions for locally-produced blocks", async function () { + const wallet = new Wallet(RichAccounts[0].PrivateKey); + const deployer = new Deployer(hre, wallet); + + const greeter = await deployContract(deployer, "Greeter", ["Hi"]); + const receipt = await greeter.setGreeting("Luke Skywalker"); + + const latestBlock = await provider.getBlock("latest"); + const txns = await provider.send("zks_getRawBlockTransactions", [latestBlock.number - 1]); + + expect(txns.length).to.equal(1); + expect(txns[0]["execute"]["calldata"]).to.equal(receipt.data); + }); +}); + +describe("zks_getConfirmedTokens", function () { + it("Should return only Ether", async function () { + const tokens = await provider.send("zks_getConfirmedTokens", [0, 100]); + expect(tokens.length).to.equal(1); + expect(tokens[0].name).to.equal("Ether"); + }); +}); + +describe("zks_getAllAccountBalances", function () { + it("Should return balance of a rich account", async function () { + // Arrange + const account = RichAccounts[0].Account; + const expectedBalance = ethers.utils.parseEther("1000000000000"); // 1_000_000_000_000 ETH + const ethAddress = "0x000000000000000000000000000000000000800a"; + await provider.send("hardhat_setBalance", [account, expectedBalance._hex]); + + // Act + const balances = await provider.send("zks_getAllAccountBalances", [account]); + const ethBalance = BigNumber.from(balances[ethAddress]); + + // Assert + expect(ethBalance.eq(expectedBalance)).to.be.true; + }); +}); diff --git a/.test-node-subtree/e2e-tests/tsconfig.json b/.test-node-subtree/e2e-tests/tsconfig.json new file mode 100644 index 00000000..e3c6e88f --- /dev/null +++ b/.test-node-subtree/e2e-tests/tsconfig.json @@ -0,0 +1,21 @@ +{ + "compilerOptions": { + "target": "ESNext", + "module": "CommonJS", + "baseUrl": ".", + "lib": ["ESNext"], + "declaration": true, + "moduleResolution": "Node", + "allowSyntheticDefaultImports": true, + "importHelpers": false, + "skipLibCheck": true, + "preserveSymlinks": true, + "skipDefaultLibCheck": true, + "preserveConstEnums": true, + "sourceMap": false, + "esModuleInterop": true, + "noEmit": true, + "strict": true, + }, + "include": ["./**/*.ts"] + } \ No newline at end of file diff --git a/.test-node-subtree/e2e-tests/yarn.lock b/.test-node-subtree/e2e-tests/yarn.lock new file mode 100644 index 00000000..2fe3c168 --- /dev/null +++ b/.test-node-subtree/e2e-tests/yarn.lock @@ -0,0 +1,4570 @@ +# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. +# yarn lockfile v1 + + +"@aashutoshrathi/word-wrap@^1.2.3": + version "1.2.6" + resolved "https://registry.yarnpkg.com/@aashutoshrathi/word-wrap/-/word-wrap-1.2.6.tgz#bd9154aec9983f77b3a034ecaa015c2e4201f6cf" + integrity sha512-1Yjs2SvM8TflER/OD3cOjhWWOZb58A2t7wpE2S9XfBYTiIl+XFhQG2bjy4Pu1I+EAlCNUzRDYDdFwFYUKvXcIA== + +"@balena/dockerignore@^1.0.2": + version "1.0.2" + resolved "https://registry.yarnpkg.com/@balena/dockerignore/-/dockerignore-1.0.2.tgz#9ffe4726915251e8eb69f44ef3547e0da2c03e0d" + integrity sha512-wMue2Sy4GAVTk6Ic4tJVcnfdau+gx2EnG7S+uAEe+TWJFqE4YoWN4/H8MSLj4eYJKxGg26lZwboEniNiNwZQ6Q== + +"@chainsafe/as-sha256@^0.3.1": + version "0.3.1" + resolved "https://registry.yarnpkg.com/@chainsafe/as-sha256/-/as-sha256-0.3.1.tgz#3639df0e1435cab03f4d9870cc3ac079e57a6fc9" + integrity sha512-hldFFYuf49ed7DAakWVXSJODuq3pzJEguD8tQ7h+sGkM18vja+OFoJI9krnGmgzyuZC2ETX0NOIcCTy31v2Mtg== + +"@chainsafe/persistent-merkle-tree@^0.4.2": + version "0.4.2" + resolved "https://registry.yarnpkg.com/@chainsafe/persistent-merkle-tree/-/persistent-merkle-tree-0.4.2.tgz#4c9ee80cc57cd3be7208d98c40014ad38f36f7ff" + integrity sha512-lLO3ihKPngXLTus/L7WHKaw9PnNJWizlOF1H9NNzHP6Xvh82vzg9F2bzkXhYIFshMZ2gTCEz8tq6STe7r5NDfQ== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + +"@chainsafe/persistent-merkle-tree@^0.5.0": + version "0.5.0" + resolved "https://registry.yarnpkg.com/@chainsafe/persistent-merkle-tree/-/persistent-merkle-tree-0.5.0.tgz#2b4a62c9489a5739dedd197250d8d2f5427e9f63" + integrity sha512-l0V1b5clxA3iwQLXP40zYjyZYospQLZXzBVIhhr9kDg/1qHZfzzHw0jj4VPBijfYCArZDlPkRi1wZaV2POKeuw== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + +"@chainsafe/ssz@^0.10.0": + version "0.10.2" + resolved "https://registry.yarnpkg.com/@chainsafe/ssz/-/ssz-0.10.2.tgz#c782929e1bb25fec66ba72e75934b31fd087579e" + integrity sha512-/NL3Lh8K+0q7A3LsiFq09YXS9fPE+ead2rr7vM2QK8PLzrNsw3uqrif9bpRX5UxgeRjM+vYi+boCM3+GM4ovXg== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + "@chainsafe/persistent-merkle-tree" "^0.5.0" + +"@chainsafe/ssz@^0.9.2": + version "0.9.4" + resolved "https://registry.yarnpkg.com/@chainsafe/ssz/-/ssz-0.9.4.tgz#696a8db46d6975b600f8309ad3a12f7c0e310497" + integrity sha512-77Qtg2N1ayqs4Bg/wvnWfg5Bta7iy7IRh8XqXh7oNMeP2HBbBwx8m6yTpA8p0EHItWPEBkgZd5S5/LSlp3GXuQ== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + "@chainsafe/persistent-merkle-tree" "^0.4.2" + case "^1.6.3" + +"@cspotcode/source-map-support@^0.8.0": + version "0.8.1" + resolved "https://registry.yarnpkg.com/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz#00629c35a688e05a88b1cda684fb9d5e73f000a1" + integrity sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw== + dependencies: + "@jridgewell/trace-mapping" "0.3.9" + +"@eslint-community/eslint-utils@^4.2.0", "@eslint-community/eslint-utils@^4.4.0": + version "4.4.0" + resolved "https://registry.yarnpkg.com/@eslint-community/eslint-utils/-/eslint-utils-4.4.0.tgz#a23514e8fb9af1269d5f7788aa556798d61c6b59" + integrity sha512-1/sA4dwrzBAyeUoQ6oxahHKmrZvsnLCg4RfxW3ZFGGmQkSNQPFNLV9CUEFQP1x9EYXHTo5p6xdhZM1Ne9p/AfA== + dependencies: + eslint-visitor-keys "^3.3.0" + +"@eslint-community/regexpp@^4.4.0", "@eslint-community/regexpp@^4.5.1", "@eslint-community/regexpp@^4.6.1": + version "4.9.1" + resolved "https://registry.yarnpkg.com/@eslint-community/regexpp/-/regexpp-4.9.1.tgz#449dfa81a57a1d755b09aa58d826c1262e4283b4" + integrity sha512-Y27x+MBLjXa+0JWDhykM3+JE+il3kHKAEqabfEWq3SDhZjLYb6/BHL/JKFnH3fe207JaXkyDo685Oc2Glt6ifA== + +"@eslint/eslintrc@^2.1.2": + version "2.1.2" + resolved "https://registry.yarnpkg.com/@eslint/eslintrc/-/eslintrc-2.1.2.tgz#c6936b4b328c64496692f76944e755738be62396" + integrity sha512-+wvgpDsrB1YqAMdEUCcnTlpfVBH7Vqn6A/NT3D8WVXFIaKMlErPIZT3oCIAVCOtarRpMtelZLqJeU3t7WY6X6g== + dependencies: + ajv "^6.12.4" + debug "^4.3.2" + espree "^9.6.0" + globals "^13.19.0" + ignore "^5.2.0" + import-fresh "^3.2.1" + js-yaml "^4.1.0" + minimatch "^3.1.2" + strip-json-comments "^3.1.1" + +"@eslint/js@8.51.0": + version "8.51.0" + resolved "https://registry.yarnpkg.com/@eslint/js/-/js-8.51.0.tgz#6d419c240cfb2b66da37df230f7e7eef801c32fa" + integrity sha512-HxjQ8Qn+4SI3/AFv6sOrDB+g6PpUTDwSJiQqOrnneEk8L71161srI9gjzzZvYVbzHiVg/BvcH95+cK/zfIt4pg== + +"@ethersproject/abi@5.7.0", "@ethersproject/abi@^5.1.2", "@ethersproject/abi@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abi/-/abi-5.7.0.tgz#b3f3e045bbbeed1af3947335c247ad625a44e449" + integrity sha512-351ktp42TiRcYB3H1OP8yajPeAQstMW/yCFokj/AthP9bLHzQFPlOrxOcwYEDkUAICmOHljvN4K39OMTMUa9RA== + dependencies: + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/abstract-provider@5.7.0", "@ethersproject/abstract-provider@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abstract-provider/-/abstract-provider-5.7.0.tgz#b0a8550f88b6bf9d51f90e4795d48294630cb9ef" + integrity sha512-R41c9UkchKCpAqStMYUpdunjo3pkEvZC3FAwZn5S5MGbXoMQOHIdHItezTETxAO5bevtMApSyEhn9+CHcDsWBw== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/networks" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/web" "^5.7.0" + +"@ethersproject/abstract-signer@5.7.0", "@ethersproject/abstract-signer@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abstract-signer/-/abstract-signer-5.7.0.tgz#13f4f32117868452191a4649723cb086d2b596b2" + integrity sha512-a16V8bq1/Cz+TGCkE2OPMTOUDLS3grCpdjoJCYNnVBbdYEMSgKrU0+B90s8b6H+ByYTBZN7a3g76jdIJi7UfKQ== + dependencies: + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + +"@ethersproject/address@5.7.0", "@ethersproject/address@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/address/-/address-5.7.0.tgz#19b56c4d74a3b0a46bfdbb6cfcc0a153fc697f37" + integrity sha512-9wYhYt7aghVGo758POM5nqcOMaE168Q6aRLJZwUmiqSrAungkG74gSSeKEIR7ukixesdRZGPgVqme6vmxs1fkA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + +"@ethersproject/base64@5.7.0", "@ethersproject/base64@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/base64/-/base64-5.7.0.tgz#ac4ee92aa36c1628173e221d0d01f53692059e1c" + integrity sha512-Dr8tcHt2mEbsZr/mwTPIQAf3Ai0Bks/7gTw9dSqk1mQvhW3XvRlmDJr/4n+wg1JmCl16NZue17CDh8xb/vZ0sQ== + dependencies: + "@ethersproject/bytes" "^5.7.0" + +"@ethersproject/basex@5.7.0", "@ethersproject/basex@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/basex/-/basex-5.7.0.tgz#97034dc7e8938a8ca943ab20f8a5e492ece4020b" + integrity sha512-ywlh43GwZLv2Voc2gQVTKBoVQ1mti3d8HK5aMxsfu/nRDnMmNqaSJ3r3n85HBByT8OpoY96SXM1FogC533T4zw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + +"@ethersproject/bignumber@5.7.0", "@ethersproject/bignumber@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/bignumber/-/bignumber-5.7.0.tgz#e2f03837f268ba655ffba03a57853e18a18dc9c2" + integrity sha512-n1CAdIHRWjSucQO3MC1zPSVgV/6dy/fjL9pMrPP9peL+QxEg9wOsVqwD4+818B6LUEtaXzVHQiuivzRoxPxUGw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + bn.js "^5.2.1" + +"@ethersproject/bytes@5.7.0", "@ethersproject/bytes@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/bytes/-/bytes-5.7.0.tgz#a00f6ea8d7e7534d6d87f47188af1148d71f155d" + integrity sha512-nsbxwgFXWh9NyYWo+U8atvmMsSdKJprTcICAkvbBffT75qDocbuggBU0SJiVK2MuTrp0q+xvLkTnGMPK1+uA9A== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/constants@5.7.0", "@ethersproject/constants@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/constants/-/constants-5.7.0.tgz#df80a9705a7e08984161f09014ea012d1c75295e" + integrity sha512-DHI+y5dBNvkpYUMiRQyxRBYBefZkJfo70VUkUAsRjcPs47muV9evftfZ0PJVCXYbAiCgght0DtcF9srFQmIgWA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + +"@ethersproject/contracts@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/contracts/-/contracts-5.7.0.tgz#c305e775abd07e48aa590e1a877ed5c316f8bd1e" + integrity sha512-5GJbzEU3X+d33CdfPhcyS+z8MzsTrBGk/sc+G+59+tPa9yFkl6HQ9D6L0QMgNTA9q8dT0XKxxkyp883XsQvbbg== + dependencies: + "@ethersproject/abi" "^5.7.0" + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + +"@ethersproject/hash@5.7.0", "@ethersproject/hash@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/hash/-/hash-5.7.0.tgz#eb7aca84a588508369562e16e514b539ba5240a7" + integrity sha512-qX5WrQfnah1EFnO5zJv1v46a8HW0+E5xuBBDTwMFZLuVTx0tbU2kkx15NqdjxecrLGatQN9FGQKpb1FKdHCt+g== + dependencies: + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/base64" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/hdnode@5.7.0", "@ethersproject/hdnode@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/hdnode/-/hdnode-5.7.0.tgz#e627ddc6b466bc77aebf1a6b9e47405ca5aef9cf" + integrity sha512-OmyYo9EENBPPf4ERhR7oj6uAtUAhYGqOnIS+jE5pTXvdKBS99ikzq1E7Iv0ZQZ5V36Lqx1qZLeak0Ra16qpeOg== + dependencies: + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/basex" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/pbkdf2" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + "@ethersproject/signing-key" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/wordlists" "^5.7.0" + +"@ethersproject/json-wallets@5.7.0", "@ethersproject/json-wallets@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/json-wallets/-/json-wallets-5.7.0.tgz#5e3355287b548c32b368d91014919ebebddd5360" + integrity sha512-8oee5Xgu6+RKgJTkvEMl2wDgSPSAQ9MB/3JYjFV9jlKvcYHUXZC+cQp0njgmxdHkYWn8s6/IqIZYm0YWCjO/0g== + dependencies: + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/hdnode" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/pbkdf2" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/random" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + aes-js "3.0.0" + scrypt-js "3.0.1" + +"@ethersproject/keccak256@5.7.0", "@ethersproject/keccak256@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/keccak256/-/keccak256-5.7.0.tgz#3186350c6e1cd6aba7940384ec7d6d9db01f335a" + integrity sha512-2UcPboeL/iW+pSg6vZ6ydF8tCnv3Iu/8tUmLLzWWGzxWKFFqOBQFLo6uLUv6BDrLgCDfN28RJ/wtByx+jZ4KBg== + dependencies: + "@ethersproject/bytes" "^5.7.0" + js-sha3 "0.8.0" + +"@ethersproject/logger@5.7.0", "@ethersproject/logger@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/logger/-/logger-5.7.0.tgz#6ce9ae168e74fecf287be17062b590852c311892" + integrity sha512-0odtFdXu/XHtjQXJYA3u9G0G8btm0ND5Cu8M7i5vhEcE8/HmF4Lbdqanwyv4uQTr2tx6b7fQRmgLrsnpQlmnig== + +"@ethersproject/networks@5.7.1", "@ethersproject/networks@^5.7.0": + version "5.7.1" + resolved "https://registry.yarnpkg.com/@ethersproject/networks/-/networks-5.7.1.tgz#118e1a981d757d45ccea6bb58d9fd3d9db14ead6" + integrity sha512-n/MufjFYv3yFcUyfhnXotyDlNdFb7onmkSy8aQERi2PjNcnWQ66xXxa3XlS8nCcA8aJKJjIIMNJTC7tu80GwpQ== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/pbkdf2@5.7.0", "@ethersproject/pbkdf2@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/pbkdf2/-/pbkdf2-5.7.0.tgz#d2267d0a1f6e123f3771007338c47cccd83d3102" + integrity sha512-oR/dBRZR6GTyaofd86DehG72hY6NpAjhabkhxgr3X2FpJtJuodEl2auADWBZfhDHgVCbu3/H/Ocq2uC6dpNjjw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + +"@ethersproject/properties@5.7.0", "@ethersproject/properties@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/properties/-/properties-5.7.0.tgz#a6e12cb0439b878aaf470f1902a176033067ed30" + integrity sha512-J87jy8suntrAkIZtecpxEPxY//szqr1mlBaYlQ0r4RCaiD2hjheqF9s1LVE8vVuJCXisjIP+JgtK/Do54ej4Sw== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/providers@5.7.2", "@ethersproject/providers@^5.7.1", "@ethersproject/providers@^5.7.2": + version "5.7.2" + resolved "https://registry.yarnpkg.com/@ethersproject/providers/-/providers-5.7.2.tgz#f8b1a4f275d7ce58cf0a2eec222269a08beb18cb" + integrity sha512-g34EWZ1WWAVgr4aptGlVBF8mhl3VWjv+8hoAnzStu8Ah22VHBsuGzP17eb6xDVRzw895G4W7vvx60lFFur/1Rg== + dependencies: + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/base64" "^5.7.0" + "@ethersproject/basex" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/networks" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/random" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/web" "^5.7.0" + bech32 "1.1.4" + ws "7.4.6" + +"@ethersproject/random@5.7.0", "@ethersproject/random@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/random/-/random-5.7.0.tgz#af19dcbc2484aae078bb03656ec05df66253280c" + integrity sha512-19WjScqRA8IIeWclFme75VMXSBvi4e6InrUNuaR4s5pTF2qNhcGdCUwdxUVGtDDqC00sDLCO93jPQoDUH4HVmQ== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/rlp@5.7.0", "@ethersproject/rlp@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/rlp/-/rlp-5.7.0.tgz#de39e4d5918b9d74d46de93af80b7685a9c21304" + integrity sha512-rBxzX2vK8mVF7b0Tol44t5Tb8gomOHkj5guL+HhzQ1yBh/ydjGnpw6at+X6Iw0Kp3OzzzkcKp8N9r0W4kYSs9w== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/sha2@5.7.0", "@ethersproject/sha2@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/sha2/-/sha2-5.7.0.tgz#9a5f7a7824ef784f7f7680984e593a800480c9fb" + integrity sha512-gKlH42riwb3KYp0reLsFTokByAKoJdgFCwI+CCiX/k+Jm2mbNs6oOaCjYQSlI1+XBVejwH2KrmCbMAT/GnRDQw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + hash.js "1.1.7" + +"@ethersproject/signing-key@5.7.0", "@ethersproject/signing-key@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/signing-key/-/signing-key-5.7.0.tgz#06b2df39411b00bc57c7c09b01d1e41cf1b16ab3" + integrity sha512-MZdy2nL3wO0u7gkB4nA/pEf8lu1TlFswPNmy8AiYkfKTdO6eXBJyUdmHO/ehm/htHw9K/qF8ujnTyUAD+Ry54Q== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + bn.js "^5.2.1" + elliptic "6.5.4" + hash.js "1.1.7" + +"@ethersproject/solidity@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/solidity/-/solidity-5.7.0.tgz#5e9c911d8a2acce2a5ebb48a5e2e0af20b631cb8" + integrity sha512-HmabMd2Dt/raavyaGukF4XxizWKhKQ24DoLtdNbBmNKUOPqwjsKQSdV9GQtj9CBEea9DlzETlVER1gYeXXBGaA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/strings@5.7.0", "@ethersproject/strings@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/strings/-/strings-5.7.0.tgz#54c9d2a7c57ae8f1205c88a9d3a56471e14d5ed2" + integrity sha512-/9nu+lj0YswRNSH0NXYqrh8775XNyEdUQAuf3f+SmOrnVewcJ5SBNAjF7lpgehKi4abvNNXyf+HX86czCdJ8Mg== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/transactions@5.7.0", "@ethersproject/transactions@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/transactions/-/transactions-5.7.0.tgz#91318fc24063e057885a6af13fdb703e1f993d3b" + integrity sha512-kmcNicCp1lp8qanMTC3RIikGgoJ80ztTyvtsFvCYpSCfkjhD0jZ2LOrnbcuxuToLIUYYf+4XwD1rP+B/erDIhQ== + dependencies: + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + "@ethersproject/signing-key" "^5.7.0" + +"@ethersproject/units@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/units/-/units-5.7.0.tgz#637b563d7e14f42deeee39245275d477aae1d8b1" + integrity sha512-pD3xLMy3SJu9kG5xDGI7+xhTEmGXlEqXU4OfNapmfnxLVY4EMSSRp7j1k7eezutBPH7RBN/7QPnwR7hzNlEFeg== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/wallet@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/wallet/-/wallet-5.7.0.tgz#4e5d0790d96fe21d61d38fb40324e6c7ef350b2d" + integrity sha512-MhmXlJXEJFBFVKrDLB4ZdDzxcBxQ3rLyCkhNqVu3CDYvR97E+8r01UgrI+TI99Le+aYm/in/0vp86guJuM7FCA== + dependencies: + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/hdnode" "^5.7.0" + "@ethersproject/json-wallets" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/random" "^5.7.0" + "@ethersproject/signing-key" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/wordlists" "^5.7.0" + +"@ethersproject/web@5.7.1", "@ethersproject/web@^5.7.0": + version "5.7.1" + resolved "https://registry.yarnpkg.com/@ethersproject/web/-/web-5.7.1.tgz#de1f285b373149bee5928f4eb7bcb87ee5fbb4ae" + integrity sha512-Gueu8lSvyjBWL4cYsWsjh6MtMwM0+H4HvqFPZfB6dV8ctbP9zFAO73VG1cMWae0FLPCtz0peKPpZY8/ugJJX2w== + dependencies: + "@ethersproject/base64" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/wordlists@5.7.0", "@ethersproject/wordlists@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/wordlists/-/wordlists-5.7.0.tgz#8fb2c07185d68c3e09eb3bfd6e779ba2774627f5" + integrity sha512-S2TFNJNfHWVHNE6cNDjbVlZ6MgE17MIxMbMg2zv3wn+3XSJGosL1m9ZVv3GXCf/2ymSsQ+hRI5IzoMJTG6aoVA== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@fastify/busboy@^2.0.0": + version "2.0.0" + resolved "https://registry.yarnpkg.com/@fastify/busboy/-/busboy-2.0.0.tgz#f22824caff3ae506b18207bad4126dbc6ccdb6b8" + integrity sha512-JUFJad5lv7jxj926GPgymrWQxxjPYuJNiNjNMzqT+HiuP6Vl3dk5xzG+8sTX96np0ZAluvaMzPsjhHZ5rNuNQQ== + +"@humanwhocodes/config-array@^0.11.11": + version "0.11.11" + resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.11.tgz#88a04c570dbbc7dd943e4712429c3df09bc32844" + integrity sha512-N2brEuAadi0CcdeMXUkhbZB84eskAc8MEX1By6qEchoVywSgXPIjou4rYsl0V3Hj0ZnuGycGCjdNgockbzeWNA== + dependencies: + "@humanwhocodes/object-schema" "^1.2.1" + debug "^4.1.1" + minimatch "^3.0.5" + +"@humanwhocodes/module-importer@^1.0.1": + version "1.0.1" + resolved "https://registry.yarnpkg.com/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz#af5b2691a22b44be847b0ca81641c5fb6ad0172c" + integrity sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA== + +"@humanwhocodes/object-schema@^1.2.1": + version "1.2.1" + resolved "https://registry.yarnpkg.com/@humanwhocodes/object-schema/-/object-schema-1.2.1.tgz#b520529ec21d8e5945a1851dfd1c32e94e39ff45" + integrity sha512-ZnQMnLV4e7hDlUvw8H+U8ASL02SS2Gn6+9Ac3wGGLIe7+je2AeAOxPY+izIPJDfFDb7eDjev0Us8MO1iFRN8hA== + +"@jridgewell/resolve-uri@^3.0.3": + version "3.1.1" + resolved "https://registry.yarnpkg.com/@jridgewell/resolve-uri/-/resolve-uri-3.1.1.tgz#c08679063f279615a3326583ba3a90d1d82cc721" + integrity sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA== + +"@jridgewell/sourcemap-codec@^1.4.10": + version "1.4.15" + resolved "https://registry.yarnpkg.com/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz#d7c6e6755c78567a951e04ab52ef0fd26de59f32" + integrity sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg== + +"@jridgewell/trace-mapping@0.3.9": + version "0.3.9" + resolved "https://registry.yarnpkg.com/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz#6534fd5933a53ba7cbf3a17615e273a0d1273ff9" + integrity sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ== + dependencies: + "@jridgewell/resolve-uri" "^3.0.3" + "@jridgewell/sourcemap-codec" "^1.4.10" + +"@matterlabs/eslint-config-vue@^1.1.4": + version "1.1.4" + resolved "https://registry.yarnpkg.com/@matterlabs/eslint-config-vue/-/eslint-config-vue-1.1.4.tgz#a322b9f3e5c23541c41e38bfa001913d3045e661" + integrity sha512-JL83ZcsCT31sT2ALK2dsOppbJf9Qz8gVQa1Q+YEtUrXFzcizbYmAA37tO6jcG/R8NF3jM+FSsobAo1SEHlWpFg== + dependencies: + "@vue/eslint-config-prettier" "^7.0.0" + "@vue/eslint-config-typescript" "^10.0.0" + eslint-plugin-import "^2.26.0" + eslint-plugin-vue "^8.6.0" + +"@matterlabs/hardhat-zksync-deploy@^0.6.5": + version "0.6.5" + resolved "https://registry.yarnpkg.com/@matterlabs/hardhat-zksync-deploy/-/hardhat-zksync-deploy-0.6.5.tgz#fe56bf30850e71c8d328ac1a06a100c1a0af6e3e" + integrity sha512-EZpvn8pDslfO3UA2obT8FOi5jsHhxYS5ndIR7tjL2zXKbvkbpoJR5rgKoGTJJm0riaCud674sQcxMOybVQ+2gg== + dependencies: + "@matterlabs/hardhat-zksync-solc" "0.4.2" + chalk "4.1.2" + ts-morph "^19.0.0" + +"@matterlabs/hardhat-zksync-solc@0.4.2", "@matterlabs/hardhat-zksync-solc@^0.4.2": + version "0.4.2" + resolved "https://registry.yarnpkg.com/@matterlabs/hardhat-zksync-solc/-/hardhat-zksync-solc-0.4.2.tgz#64121082e88c5ab22eb4e9594d120e504f6af499" + integrity sha512-6NFWPSZiOAoo7wNuhMg4ztj7mMEH+tLrx09WuCbcURrHPijj/KxYNsJD6Uw5lapKr7G8H7SQISGid1/MTXVmXQ== + dependencies: + "@nomiclabs/hardhat-docker" "^2.0.0" + chalk "4.1.2" + dockerode "^3.3.4" + fs-extra "^11.1.1" + proper-lockfile "^4.1.2" + semver "^7.5.1" + +"@matterlabs/prettier-config@^1.0.3": + version "1.0.3" + resolved "https://registry.yarnpkg.com/@matterlabs/prettier-config/-/prettier-config-1.0.3.tgz#3e2eb559c0112bbe9671895f935700dad2a15d38" + integrity sha512-JW7nHREPqEtjBWz3EfxLarkmJBD8vi7Kx/1AQ6eBZnz12eHc1VkOyrc6mpR5ogTf0dOUNXFAfZut+cDe2dn4kQ== + +"@matterlabs/zksync-contracts@0.6.1": + version "0.6.1" + resolved "https://registry.yarnpkg.com/@matterlabs/zksync-contracts/-/zksync-contracts-0.6.1.tgz#39f061959d5890fd0043a2f1ae710f764b172230" + integrity sha512-+hucLw4DhGmTmQlXOTEtpboYCaOm/X2VJcWmnW4abNcOgQXEHX+mTxQrxEfPjIZT0ZE6z5FTUrOK9+RgUZwBMQ== + +"@metamask/eth-sig-util@^4.0.0": + version "4.0.1" + resolved "https://registry.yarnpkg.com/@metamask/eth-sig-util/-/eth-sig-util-4.0.1.tgz#3ad61f6ea9ad73ba5b19db780d40d9aae5157088" + integrity sha512-tghyZKLHZjcdlDqCA3gNZmLeR0XvOE9U1qoQO9ohyAZT6Pya+H9vkBPcsyXytmYLNgVoin7CKCmweo/R43V+tQ== + dependencies: + ethereumjs-abi "^0.6.8" + ethereumjs-util "^6.2.1" + ethjs-util "^0.1.6" + tweetnacl "^1.0.3" + tweetnacl-util "^0.15.1" + +"@noble/hashes@1.2.0", "@noble/hashes@~1.2.0": + version "1.2.0" + resolved "https://registry.yarnpkg.com/@noble/hashes/-/hashes-1.2.0.tgz#a3150eeb09cc7ab207ebf6d7b9ad311a9bdbed12" + integrity sha512-FZfhjEDbT5GRswV3C6uvLPHMiVD6lQBmpoX5+eSiPaMTXte/IKqI5dykDxzZB/WBeK/CDuQRBWarPdi3FNY2zQ== + +"@noble/secp256k1@1.7.1", "@noble/secp256k1@~1.7.0": + version "1.7.1" + resolved "https://registry.yarnpkg.com/@noble/secp256k1/-/secp256k1-1.7.1.tgz#b251c70f824ce3ca7f8dc3df08d58f005cc0507c" + integrity sha512-hOUk6AyBFmqVrv7k5WAw/LpszxVbj9gGN4JRkIX52fdFAj1UA61KXmZDvqVEm+pOyec3+fIeZB02LYa/pWOArw== + +"@nodelib/fs.scandir@2.1.5": + version "2.1.5" + resolved "https://registry.yarnpkg.com/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz#7619c2eb21b25483f6d167548b4cfd5a7488c3d5" + integrity sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g== + dependencies: + "@nodelib/fs.stat" "2.0.5" + run-parallel "^1.1.9" + +"@nodelib/fs.stat@2.0.5", "@nodelib/fs.stat@^2.0.2": + version "2.0.5" + resolved "https://registry.yarnpkg.com/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz#5bd262af94e9d25bd1e71b05deed44876a222e8b" + integrity sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A== + +"@nodelib/fs.walk@^1.2.3", "@nodelib/fs.walk@^1.2.8": + version "1.2.8" + resolved "https://registry.yarnpkg.com/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz#e95737e8bb6746ddedf69c556953494f196fe69a" + integrity sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg== + dependencies: + "@nodelib/fs.scandir" "2.1.5" + fastq "^1.6.0" + +"@nomicfoundation/ethereumjs-block@5.0.2": + version "5.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-block/-/ethereumjs-block-5.0.2.tgz#13a7968f5964f1697da941281b7f7943b0465d04" + integrity sha512-hSe6CuHI4SsSiWWjHDIzWhSiAVpzMUcDRpWYzN0T9l8/Rz7xNn3elwVOJ/tAyS0LqL6vitUD78Uk7lQDXZun7Q== + dependencies: + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-trie" "6.0.2" + "@nomicfoundation/ethereumjs-tx" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + ethereum-cryptography "0.1.3" + ethers "^5.7.1" + +"@nomicfoundation/ethereumjs-blockchain@7.0.2": + version "7.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-blockchain/-/ethereumjs-blockchain-7.0.2.tgz#45323b673b3d2fab6b5008535340d1b8fea7d446" + integrity sha512-8UUsSXJs+MFfIIAKdh3cG16iNmWzWC/91P40sazNvrqhhdR/RtGDlFk2iFTGbBAZPs2+klZVzhRX8m2wvuvz3w== + dependencies: + "@nomicfoundation/ethereumjs-block" "5.0.2" + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-ethash" "3.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-trie" "6.0.2" + "@nomicfoundation/ethereumjs-tx" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + abstract-level "^1.0.3" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + level "^8.0.0" + lru-cache "^5.1.1" + memory-level "^1.0.0" + +"@nomicfoundation/ethereumjs-common@4.0.2": + version "4.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-common/-/ethereumjs-common-4.0.2.tgz#a15d1651ca36757588fdaf2a7d381a150662a3c3" + integrity sha512-I2WGP3HMGsOoycSdOTSqIaES0ughQTueOsddJ36aYVpI3SN8YSusgRFLwzDJwRFVIYDKx/iJz0sQ5kBHVgdDwg== + dependencies: + "@nomicfoundation/ethereumjs-util" "9.0.2" + crc-32 "^1.2.0" + +"@nomicfoundation/ethereumjs-ethash@3.0.2": + version "3.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-ethash/-/ethereumjs-ethash-3.0.2.tgz#da77147f806401ee996bfddfa6487500118addca" + integrity sha512-8PfoOQCcIcO9Pylq0Buijuq/O73tmMVURK0OqdjhwqcGHYC2PwhbajDh7GZ55ekB0Px197ajK3PQhpKoiI/UPg== + dependencies: + "@nomicfoundation/ethereumjs-block" "5.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + abstract-level "^1.0.3" + bigint-crypto-utils "^3.0.23" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-evm@2.0.2": + version "2.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-evm/-/ethereumjs-evm-2.0.2.tgz#4c2f4b84c056047102a4fa41c127454e3f0cfcf6" + integrity sha512-rBLcUaUfANJxyOx9HIdMX6uXGin6lANCulIm/pjMgRqfiCRMZie3WKYxTSd8ZE/d+qT+zTedBF4+VHTdTSePmQ== + dependencies: + "@ethersproject/providers" "^5.7.1" + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-tx" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + mcl-wasm "^0.7.1" + rustbn.js "~0.2.0" + +"@nomicfoundation/ethereumjs-rlp@5.0.2": + version "5.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-rlp/-/ethereumjs-rlp-5.0.2.tgz#4fee8dc58a53ac6ae87fb1fca7c15dc06c6b5dea" + integrity sha512-QwmemBc+MMsHJ1P1QvPl8R8p2aPvvVcKBbvHnQOKBpBztEo0omN0eaob6FeZS/e3y9NSe+mfu3nNFBHszqkjTA== + +"@nomicfoundation/ethereumjs-statemanager@2.0.2": + version "2.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-statemanager/-/ethereumjs-statemanager-2.0.2.tgz#3ba4253b29b1211cafe4f9265fee5a0d780976e0" + integrity sha512-dlKy5dIXLuDubx8Z74sipciZnJTRSV/uHG48RSijhgm1V7eXYFC567xgKtsKiVZB1ViTP9iFL4B6Je0xD6X2OA== + dependencies: + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + ethers "^5.7.1" + js-sdsl "^4.1.4" + +"@nomicfoundation/ethereumjs-trie@6.0.2": + version "6.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-trie/-/ethereumjs-trie-6.0.2.tgz#9a6dbd28482dca1bc162d12b3733acab8cd12835" + integrity sha512-yw8vg9hBeLYk4YNg5MrSJ5H55TLOv2FSWUTROtDtTMMmDGROsAu+0tBjiNGTnKRi400M6cEzoFfa89Fc5k8NTQ== + dependencies: + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + "@types/readable-stream" "^2.3.13" + ethereum-cryptography "0.1.3" + readable-stream "^3.6.0" + +"@nomicfoundation/ethereumjs-tx@5.0.2": + version "5.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-tx/-/ethereumjs-tx-5.0.2.tgz#117813b69c0fdc14dd0446698a64be6df71d7e56" + integrity sha512-T+l4/MmTp7VhJeNloMkM+lPU3YMUaXdcXgTGCf8+ZFvV9NYZTRLFekRwlG6/JMmVfIfbrW+dRRJ9A6H5Q/Z64g== + dependencies: + "@chainsafe/ssz" "^0.9.2" + "@ethersproject/providers" "^5.7.2" + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-util@9.0.2": + version "9.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-util/-/ethereumjs-util-9.0.2.tgz#16bdc1bb36f333b8a3559bbb4b17dac805ce904d" + integrity sha512-4Wu9D3LykbSBWZo8nJCnzVIYGvGCuyiYLIJa9XXNVt1q1jUzHdB+sJvx95VGCpPkCT+IbLecW6yfzy3E1bQrwQ== + dependencies: + "@chainsafe/ssz" "^0.10.0" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-vm@7.0.2": + version "7.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-vm/-/ethereumjs-vm-7.0.2.tgz#3b0852cb3584df0e18c182d0672a3596c9ca95e6" + integrity sha512-Bj3KZT64j54Tcwr7Qm/0jkeZXJMfdcAtRBedou+Hx0dPOSIgqaIr0vvLwP65TpHbak2DmAq+KJbW2KNtIoFwvA== + dependencies: + "@nomicfoundation/ethereumjs-block" "5.0.2" + "@nomicfoundation/ethereumjs-blockchain" "7.0.2" + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-evm" "2.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-statemanager" "2.0.2" + "@nomicfoundation/ethereumjs-trie" "6.0.2" + "@nomicfoundation/ethereumjs-tx" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + mcl-wasm "^0.7.1" + rustbn.js "~0.2.0" + +"@nomicfoundation/solidity-analyzer-darwin-arm64@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-darwin-arm64/-/solidity-analyzer-darwin-arm64-0.1.1.tgz#4c858096b1c17fe58a474fe81b46815f93645c15" + integrity sha512-KcTodaQw8ivDZyF+D76FokN/HdpgGpfjc/gFCImdLUyqB6eSWVaZPazMbeAjmfhx3R0zm/NYVzxwAokFKgrc0w== + +"@nomicfoundation/solidity-analyzer-darwin-x64@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-darwin-x64/-/solidity-analyzer-darwin-x64-0.1.1.tgz#6e25ccdf6e2d22389c35553b64fe6f3fdaec432c" + integrity sha512-XhQG4BaJE6cIbjAVtzGOGbK3sn1BO9W29uhk9J8y8fZF1DYz0Doj8QDMfpMu+A6TjPDs61lbsmeYodIDnfveSA== + +"@nomicfoundation/solidity-analyzer-freebsd-x64@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-freebsd-x64/-/solidity-analyzer-freebsd-x64-0.1.1.tgz#0a224ea50317139caeebcdedd435c28a039d169c" + integrity sha512-GHF1VKRdHW3G8CndkwdaeLkVBi5A9u2jwtlS7SLhBc8b5U/GcoL39Q+1CSO3hYqePNP+eV5YI7Zgm0ea6kMHoA== + +"@nomicfoundation/solidity-analyzer-linux-arm64-gnu@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-arm64-gnu/-/solidity-analyzer-linux-arm64-gnu-0.1.1.tgz#dfa085d9ffab9efb2e7b383aed3f557f7687ac2b" + integrity sha512-g4Cv2fO37ZsUENQ2vwPnZc2zRenHyAxHcyBjKcjaSmmkKrFr64yvzeNO8S3GBFCo90rfochLs99wFVGT/0owpg== + +"@nomicfoundation/solidity-analyzer-linux-arm64-musl@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-arm64-musl/-/solidity-analyzer-linux-arm64-musl-0.1.1.tgz#c9e06b5d513dd3ab02a7ac069c160051675889a4" + integrity sha512-WJ3CE5Oek25OGE3WwzK7oaopY8xMw9Lhb0mlYuJl/maZVo+WtP36XoQTb7bW/i8aAdHW5Z+BqrHMux23pvxG3w== + +"@nomicfoundation/solidity-analyzer-linux-x64-gnu@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-x64-gnu/-/solidity-analyzer-linux-x64-gnu-0.1.1.tgz#8d328d16839e52571f72f2998c81e46bf320f893" + integrity sha512-5WN7leSr5fkUBBjE4f3wKENUy9HQStu7HmWqbtknfXkkil+eNWiBV275IOlpXku7v3uLsXTOKpnnGHJYI2qsdA== + +"@nomicfoundation/solidity-analyzer-linux-x64-musl@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-x64-musl/-/solidity-analyzer-linux-x64-musl-0.1.1.tgz#9b49d0634b5976bb5ed1604a1e1b736f390959bb" + integrity sha512-KdYMkJOq0SYPQMmErv/63CwGwMm5XHenEna9X9aB8mQmhDBrYrlAOSsIPgFCUSL0hjxE3xHP65/EPXR/InD2+w== + +"@nomicfoundation/solidity-analyzer-win32-arm64-msvc@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-arm64-msvc/-/solidity-analyzer-win32-arm64-msvc-0.1.1.tgz#e2867af7264ebbcc3131ef837878955dd6a3676f" + integrity sha512-VFZASBfl4qiBYwW5xeY20exWhmv6ww9sWu/krWSesv3q5hA0o1JuzmPHR4LPN6SUZj5vcqci0O6JOL8BPw+APg== + +"@nomicfoundation/solidity-analyzer-win32-ia32-msvc@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-ia32-msvc/-/solidity-analyzer-win32-ia32-msvc-0.1.1.tgz#0685f78608dd516c8cdfb4896ed451317e559585" + integrity sha512-JnFkYuyCSA70j6Si6cS1A9Gh1aHTEb8kOTBApp/c7NRTFGNMH8eaInKlyuuiIbvYFhlXW4LicqyYuWNNq9hkpQ== + +"@nomicfoundation/solidity-analyzer-win32-x64-msvc@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-x64-msvc/-/solidity-analyzer-win32-x64-msvc-0.1.1.tgz#c9a44f7108646f083b82e851486e0f6aeb785836" + integrity sha512-HrVJr6+WjIXGnw3Q9u6KQcbZCtk0caVWhCdFADySvRyUxJ8PnzlaP+MhwNE8oyT8OZ6ejHBRrrgjSqDCFXGirw== + +"@nomicfoundation/solidity-analyzer@^0.1.0": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer/-/solidity-analyzer-0.1.1.tgz#f5f4d36d3f66752f59a57e7208cd856f3ddf6f2d" + integrity sha512-1LMtXj1puAxyFusBgUIy5pZk3073cNXYnXUpuNKFghHbIit/xZgbk0AokpUADbNm3gyD6bFWl3LRFh3dhVdREg== + optionalDependencies: + "@nomicfoundation/solidity-analyzer-darwin-arm64" "0.1.1" + "@nomicfoundation/solidity-analyzer-darwin-x64" "0.1.1" + "@nomicfoundation/solidity-analyzer-freebsd-x64" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-arm64-gnu" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-arm64-musl" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-x64-gnu" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-x64-musl" "0.1.1" + "@nomicfoundation/solidity-analyzer-win32-arm64-msvc" "0.1.1" + "@nomicfoundation/solidity-analyzer-win32-ia32-msvc" "0.1.1" + "@nomicfoundation/solidity-analyzer-win32-x64-msvc" "0.1.1" + +"@nomiclabs/hardhat-docker@^2.0.0": + version "2.0.2" + resolved "https://registry.yarnpkg.com/@nomiclabs/hardhat-docker/-/hardhat-docker-2.0.2.tgz#ae964be17951275a55859ff7358e9e7c77448846" + integrity sha512-XgGEpRT3wlA1VslyB57zyAHV+oll8KnV1TjwnxxC1tpAL04/lbdwpdO5KxInVN8irMSepqFpsiSkqlcnvbE7Ng== + dependencies: + dockerode "^2.5.8" + fs-extra "^7.0.1" + node-fetch "^2.6.0" + +"@nomiclabs/hardhat-ethers@^2.2.3": + version "2.2.3" + resolved "https://registry.yarnpkg.com/@nomiclabs/hardhat-ethers/-/hardhat-ethers-2.2.3.tgz#b41053e360c31a32c2640c9a45ee981a7e603fe0" + integrity sha512-YhzPdzb612X591FOe68q+qXVXGG2ANZRvDo0RRUtimev85rCrAlv/TLMEZw5c+kq9AbzocLTVX/h2jVIFPL9Xg== + +"@openzeppelin/contracts@^4.9.3": + version "4.9.3" + resolved "https://registry.yarnpkg.com/@openzeppelin/contracts/-/contracts-4.9.3.tgz#00d7a8cf35a475b160b3f0293a6403c511099364" + integrity sha512-He3LieZ1pP2TNt5JbkPA4PNT9WC3gOTOlDcFGJW4Le4QKqwmiNJCRt44APfxMxvq7OugU/cqYuPcSBzOw38DAg== + +"@scure/base@~1.1.0": + version "1.1.3" + resolved "https://registry.yarnpkg.com/@scure/base/-/base-1.1.3.tgz#8584115565228290a6c6c4961973e0903bb3df2f" + integrity sha512-/+SgoRjLq7Xlf0CWuLHq2LUZeL/w65kfzAPG5NH9pcmBhs+nunQTn4gvdwgMTIXnt9b2C/1SeL2XiysZEyIC9Q== + +"@scure/bip32@1.1.5": + version "1.1.5" + resolved "https://registry.yarnpkg.com/@scure/bip32/-/bip32-1.1.5.tgz#d2ccae16dcc2e75bc1d75f5ef3c66a338d1ba300" + integrity sha512-XyNh1rB0SkEqd3tXcXMi+Xe1fvg+kUIcoRIEujP1Jgv7DqW2r9lg3Ah0NkFaCs9sTkQAQA8kw7xiRXzENi9Rtw== + dependencies: + "@noble/hashes" "~1.2.0" + "@noble/secp256k1" "~1.7.0" + "@scure/base" "~1.1.0" + +"@scure/bip39@1.1.1": + version "1.1.1" + resolved "https://registry.yarnpkg.com/@scure/bip39/-/bip39-1.1.1.tgz#b54557b2e86214319405db819c4b6a370cf340c5" + integrity sha512-t+wDck2rVkh65Hmv280fYdVdY25J9YeEUIgn2LG1WM6gxFkGzcksoDiUkWVpVp3Oex9xGC68JU2dSbUfwZ2jPg== + dependencies: + "@noble/hashes" "~1.2.0" + "@scure/base" "~1.1.0" + +"@sentry/core@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/core/-/core-5.30.0.tgz#6b203664f69e75106ee8b5a2fe1d717379b331f3" + integrity sha512-TmfrII8w1PQZSZgPpUESqjB+jC6MvZJZdLtE/0hZ+SrnKhW3x5WlYLvTXZpcWePYBku7rl2wn1RZu6uT0qCTeg== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/minimal" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/hub@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/hub/-/hub-5.30.0.tgz#2453be9b9cb903404366e198bd30c7ca74cdc100" + integrity sha512-2tYrGnzb1gKz2EkMDQcfLrDTvmGcQPuWxLnJKXJvYTQDGLlEvi2tWz1VIHjunmOvJrB5aIQLhm+dcMRwFZDCqQ== + dependencies: + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/minimal@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/minimal/-/minimal-5.30.0.tgz#ce3d3a6a273428e0084adcb800bc12e72d34637b" + integrity sha512-BwWb/owZKtkDX+Sc4zCSTNcvZUq7YcH3uAVlmh/gtR9rmUvbzAA3ewLuB3myi4wWRAMEtny6+J/FN/x+2wn9Xw== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/types" "5.30.0" + tslib "^1.9.3" + +"@sentry/node@^5.18.1": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/node/-/node-5.30.0.tgz#4ca479e799b1021285d7fe12ac0858951c11cd48" + integrity sha512-Br5oyVBF0fZo6ZS9bxbJZG4ApAjRqAnqFFurMVJJdunNb80brh7a5Qva2kjhm+U6r9NJAB5OmDyPkA1Qnt+QVg== + dependencies: + "@sentry/core" "5.30.0" + "@sentry/hub" "5.30.0" + "@sentry/tracing" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + cookie "^0.4.1" + https-proxy-agent "^5.0.0" + lru_map "^0.3.3" + tslib "^1.9.3" + +"@sentry/tracing@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/tracing/-/tracing-5.30.0.tgz#501d21f00c3f3be7f7635d8710da70d9419d4e1f" + integrity sha512-dUFowCr0AIMwiLD7Fs314Mdzcug+gBVo/+NCMyDw8tFxJkwWAKl7Qa2OZxLQ0ZHjakcj1hNKfCQJ9rhyfOl4Aw== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/minimal" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/types@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/types/-/types-5.30.0.tgz#19709bbe12a1a0115bc790b8942917da5636f402" + integrity sha512-R8xOqlSTZ+htqrfteCWU5Nk0CDN5ApUTvrlvBuiH1DyP6czDZ4ktbZB0hAgBlVcK0U+qpD3ag3Tqqpa5Q67rPw== + +"@sentry/utils@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/utils/-/utils-5.30.0.tgz#9a5bd7ccff85ccfe7856d493bffa64cabc41e980" + integrity sha512-zaYmoH0NWWtvnJjC9/CBseXMtKHm/tm40sz3YfJRxeQjyzRqNQPgivpd9R/oDJCYj999mzdW382p/qi2ypjLww== + dependencies: + "@sentry/types" "5.30.0" + tslib "^1.9.3" + +"@ts-morph/common@~0.20.0": + version "0.20.0" + resolved "https://registry.yarnpkg.com/@ts-morph/common/-/common-0.20.0.tgz#3f161996b085ba4519731e4d24c35f6cba5b80af" + integrity sha512-7uKjByfbPpwuzkstL3L5MQyuXPSKdoNG93Fmi2JoDcTf3pEP731JdRFAduRVkOs8oqxPsXKA+ScrWkdQ8t/I+Q== + dependencies: + fast-glob "^3.2.12" + minimatch "^7.4.3" + mkdirp "^2.1.6" + path-browserify "^1.0.1" + +"@tsconfig/node10@^1.0.7": + version "1.0.9" + resolved "https://registry.yarnpkg.com/@tsconfig/node10/-/node10-1.0.9.tgz#df4907fc07a886922637b15e02d4cebc4c0021b2" + integrity sha512-jNsYVVxU8v5g43Erja32laIDHXeoNvFEpX33OK4d6hljo3jDhCBDhx5dhCCTMWUojscpAagGiRkBKxpdl9fxqA== + +"@tsconfig/node12@^1.0.7": + version "1.0.11" + resolved "https://registry.yarnpkg.com/@tsconfig/node12/-/node12-1.0.11.tgz#ee3def1f27d9ed66dac6e46a295cffb0152e058d" + integrity sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag== + +"@tsconfig/node14@^1.0.0": + version "1.0.3" + resolved "https://registry.yarnpkg.com/@tsconfig/node14/-/node14-1.0.3.tgz#e4386316284f00b98435bf40f72f75a09dabf6c1" + integrity sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow== + +"@tsconfig/node16@^1.0.2": + version "1.0.4" + resolved "https://registry.yarnpkg.com/@tsconfig/node16/-/node16-1.0.4.tgz#0b92dcc0cc1c81f6f306a381f28e31b1a56536e9" + integrity sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA== + +"@types/bn.js@^4.11.3": + version "4.11.6" + resolved "https://registry.yarnpkg.com/@types/bn.js/-/bn.js-4.11.6.tgz#c306c70d9358aaea33cd4eda092a742b9505967c" + integrity sha512-pqr857jrp2kPuO9uRjZ3PwnJTjoQy+fcdxvBTvHm6dkmEL9q+hDD/2j/0ELOBPtPnS8LjCX0gI9nbl8lVkadpg== + dependencies: + "@types/node" "*" + +"@types/bn.js@^5.1.0": + version "5.1.2" + resolved "https://registry.yarnpkg.com/@types/bn.js/-/bn.js-5.1.2.tgz#162f5238c46f4bcbac07a98561724eca1fcf0c5e" + integrity sha512-dkpZu0szUtn9UXTmw+e0AJFd4D2XAxDnsCLdc05SfqpqzPEBft8eQr8uaFitfo/dUUOZERaLec2hHMG87A4Dxg== + dependencies: + "@types/node" "*" + +"@types/chai@^4.3.4": + version "4.3.8" + resolved "https://registry.yarnpkg.com/@types/chai/-/chai-4.3.8.tgz#aa200a264a3bc78ccfc1718eedbd3b9d5a591270" + integrity sha512-yW/qTM4mRBBcsA9Xw9FbcImYtFPY7sgr+G/O5RDYVmxiy9a+pE5FyoFUi8JYCZY5nicj8atrr1pcfPiYpeNGOA== + +"@types/json-schema@^7.0.12", "@types/json-schema@^7.0.9": + version "7.0.13" + resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.13.tgz#02c24f4363176d2d18fc8b70b9f3c54aba178a85" + integrity sha512-RbSSoHliUbnXj3ny0CNFOoxrIDV6SUGyStHsvDqosw6CkdPV8TtWGlfecuK4ToyMEAql6pzNxgCFKanovUzlgQ== + +"@types/json5@^0.0.29": + version "0.0.29" + resolved "https://registry.yarnpkg.com/@types/json5/-/json5-0.0.29.tgz#ee28707ae94e11d2b827bcbe5270bcea7f3e71ee" + integrity sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ== + +"@types/lru-cache@^5.1.0": + version "5.1.1" + resolved "https://registry.yarnpkg.com/@types/lru-cache/-/lru-cache-5.1.1.tgz#c48c2e27b65d2a153b19bfc1a317e30872e01eef" + integrity sha512-ssE3Vlrys7sdIzs5LOxCzTVMsU7i9oa/IaW92wF32JFb3CVczqOkru2xspuKczHEbG3nvmPY7IFqVmGGHdNbYw== + +"@types/mocha@^10.0.1": + version "10.0.2" + resolved "https://registry.yarnpkg.com/@types/mocha/-/mocha-10.0.2.tgz#96d63314255540a36bf24da094cce7a13668d73b" + integrity sha512-NaHL0+0lLNhX6d9rs+NSt97WH/gIlRHmszXbQ/8/MV/eVcFNdeJ/GYhrFuUc8K7WuPhRhTSdMkCp8VMzhUq85w== + +"@types/node@*": + version "20.8.5" + resolved "https://registry.yarnpkg.com/@types/node/-/node-20.8.5.tgz#13352ae1f80032171616910e8aba2e3e52e57d96" + integrity sha512-SPlobFgbidfIeOYlzXiEjSYeIJiOCthv+9tSQVpvk4PAdIIc+2SmjNVzWXk9t0Y7dl73Zdf+OgXKHX9XtkqUpw== + dependencies: + undici-types "~5.25.1" + +"@types/node@^18.17.12": + version "18.18.5" + resolved "https://registry.yarnpkg.com/@types/node/-/node-18.18.5.tgz#afc0fd975df946d6e1add5bbf98264225b212244" + integrity sha512-4slmbtwV59ZxitY4ixUZdy1uRLf9eSIvBWPQxNjhHYWEtn0FryfKpyS2cvADYXTayWdKEIsJengncrVvkI4I6A== + +"@types/pbkdf2@^3.0.0": + version "3.1.0" + resolved "https://registry.yarnpkg.com/@types/pbkdf2/-/pbkdf2-3.1.0.tgz#039a0e9b67da0cdc4ee5dab865caa6b267bb66b1" + integrity sha512-Cf63Rv7jCQ0LaL8tNXmEyqTHuIJxRdlS5vMh1mj5voN4+QFhVZnlZruezqpWYDiJ8UTzhP0VmeLXCmBk66YrMQ== + dependencies: + "@types/node" "*" + +"@types/readable-stream@^2.3.13": + version "2.3.15" + resolved "https://registry.yarnpkg.com/@types/readable-stream/-/readable-stream-2.3.15.tgz#3d79c9ceb1b6a57d5f6e6976f489b9b5384321ae" + integrity sha512-oM5JSKQCcICF1wvGgmecmHldZ48OZamtMxcGGVICOJA8o8cahXC1zEVAif8iwoc5j8etxFaRFnf095+CDsuoFQ== + dependencies: + "@types/node" "*" + safe-buffer "~5.1.1" + +"@types/secp256k1@^4.0.1": + version "4.0.4" + resolved "https://registry.yarnpkg.com/@types/secp256k1/-/secp256k1-4.0.4.tgz#33c760de627fce1f449c2d4270da07e4da54c830" + integrity sha512-oN0PFsYxDZnX/qSJ5S5OwaEDTYfekhvaM5vqui2bu1AA39pKofmgL104Q29KiOXizXS2yLjSzc5YdTyMKdcy4A== + dependencies: + "@types/node" "*" + +"@types/semver@^7.3.12", "@types/semver@^7.5.0": + version "7.5.3" + resolved "https://registry.yarnpkg.com/@types/semver/-/semver-7.5.3.tgz#9a726e116beb26c24f1ccd6850201e1246122e04" + integrity sha512-OxepLK9EuNEIPxWNME+C6WwbRAOOI2o2BaQEGzz5Lu2e4Z5eDnEo+/aVEDMIXywoJitJ7xWd641wrGLZdtwRyw== + +"@typescript-eslint/eslint-plugin@^5.0.0": + version "5.62.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.62.0.tgz#aeef0328d172b9e37d9bab6dbc13b87ed88977db" + integrity sha512-TiZzBSJja/LbhNPvk6yc0JrX9XqhQ0hdh6M2svYfsHGejaKFIAGd9MQ+ERIMzLGlN/kZoYIgdxFV0PuljTKXag== + dependencies: + "@eslint-community/regexpp" "^4.4.0" + "@typescript-eslint/scope-manager" "5.62.0" + "@typescript-eslint/type-utils" "5.62.0" + "@typescript-eslint/utils" "5.62.0" + debug "^4.3.4" + graphemer "^1.4.0" + ignore "^5.2.0" + natural-compare-lite "^1.4.0" + semver "^7.3.7" + tsutils "^3.21.0" + +"@typescript-eslint/eslint-plugin@latest": + version "6.7.5" + resolved "https://registry.yarnpkg.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-6.7.5.tgz#f4024b9f63593d0c2b5bd6e4ca027e6f30934d4f" + integrity sha512-JhtAwTRhOUcP96D0Y6KYnwig/MRQbOoLGXTON2+LlyB/N35SP9j1boai2zzwXb7ypKELXMx3DVk9UTaEq1vHEw== + dependencies: + "@eslint-community/regexpp" "^4.5.1" + "@typescript-eslint/scope-manager" "6.7.5" + "@typescript-eslint/type-utils" "6.7.5" + "@typescript-eslint/utils" "6.7.5" + "@typescript-eslint/visitor-keys" "6.7.5" + debug "^4.3.4" + graphemer "^1.4.0" + ignore "^5.2.4" + natural-compare "^1.4.0" + semver "^7.5.4" + ts-api-utils "^1.0.1" + +"@typescript-eslint/parser@^5.0.0": + version "5.62.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/parser/-/parser-5.62.0.tgz#1b63d082d849a2fcae8a569248fbe2ee1b8a56c7" + integrity sha512-VlJEV0fOQ7BExOsHYAGrgbEiZoi8D+Bl2+f6V2RrXerRSylnp+ZBHmPvaIa8cz0Ajx7WO7Z5RqfgYg7ED1nRhA== + dependencies: + "@typescript-eslint/scope-manager" "5.62.0" + "@typescript-eslint/types" "5.62.0" + "@typescript-eslint/typescript-estree" "5.62.0" + debug "^4.3.4" + +"@typescript-eslint/parser@latest": + version "6.7.5" + resolved "https://registry.yarnpkg.com/@typescript-eslint/parser/-/parser-6.7.5.tgz#8d7ca3d1fbd9d5a58cc4d30b2aa797a760137886" + integrity sha512-bIZVSGx2UME/lmhLcjdVc7ePBwn7CLqKarUBL4me1C5feOd663liTGjMBGVcGr+BhnSLeP4SgwdvNnnkbIdkCw== + dependencies: + "@typescript-eslint/scope-manager" "6.7.5" + "@typescript-eslint/types" "6.7.5" + "@typescript-eslint/typescript-estree" "6.7.5" + "@typescript-eslint/visitor-keys" "6.7.5" + debug "^4.3.4" + +"@typescript-eslint/scope-manager@5.62.0": + version "5.62.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/scope-manager/-/scope-manager-5.62.0.tgz#d9457ccc6a0b8d6b37d0eb252a23022478c5460c" + integrity sha512-VXuvVvZeQCQb5Zgf4HAxc04q5j+WrNAtNh9OwCsCgpKqESMTu3tF/jhZ3xG6T4NZwWl65Bg8KuS2uEvhSfLl0w== + dependencies: + "@typescript-eslint/types" "5.62.0" + "@typescript-eslint/visitor-keys" "5.62.0" + +"@typescript-eslint/scope-manager@6.7.5": + version "6.7.5" + resolved "https://registry.yarnpkg.com/@typescript-eslint/scope-manager/-/scope-manager-6.7.5.tgz#1cf33b991043886cd67f4f3600b8e122fc14e711" + integrity sha512-GAlk3eQIwWOJeb9F7MKQ6Jbah/vx1zETSDw8likab/eFcqkjSD7BI75SDAeC5N2L0MmConMoPvTsmkrg71+B1A== + dependencies: + "@typescript-eslint/types" "6.7.5" + "@typescript-eslint/visitor-keys" "6.7.5" + +"@typescript-eslint/type-utils@5.62.0": + version "5.62.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/type-utils/-/type-utils-5.62.0.tgz#286f0389c41681376cdad96b309cedd17d70346a" + integrity sha512-xsSQreu+VnfbqQpW5vnCJdq1Z3Q0U31qiWmRhr98ONQmcp/yhiPJFPq8MXiJVLiksmOKSjIldZzkebzHuCGzew== + dependencies: + "@typescript-eslint/typescript-estree" "5.62.0" + "@typescript-eslint/utils" "5.62.0" + debug "^4.3.4" + tsutils "^3.21.0" + +"@typescript-eslint/type-utils@6.7.5": + version "6.7.5" + resolved "https://registry.yarnpkg.com/@typescript-eslint/type-utils/-/type-utils-6.7.5.tgz#0a65949ec16588d8956f6d967f7d9c84ddb2d72a" + integrity sha512-Gs0qos5wqxnQrvpYv+pf3XfcRXW6jiAn9zE/K+DlmYf6FcpxeNYN0AIETaPR7rHO4K2UY+D0CIbDP9Ut0U4m1g== + dependencies: + "@typescript-eslint/typescript-estree" "6.7.5" + "@typescript-eslint/utils" "6.7.5" + debug "^4.3.4" + ts-api-utils "^1.0.1" + +"@typescript-eslint/types@5.62.0": + version "5.62.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/types/-/types-5.62.0.tgz#258607e60effa309f067608931c3df6fed41fd2f" + integrity sha512-87NVngcbVXUahrRTqIK27gD2t5Cu1yuCXxbLcFtCzZGlfyVWWh8mLHkoxzjsB6DDNnvdL+fW8MiwPEJyGJQDgQ== + +"@typescript-eslint/types@6.7.5": + version "6.7.5" + resolved "https://registry.yarnpkg.com/@typescript-eslint/types/-/types-6.7.5.tgz#4571320fb9cf669de9a95d9849f922c3af809790" + integrity sha512-WboQBlOXtdj1tDFPyIthpKrUb+kZf2VroLZhxKa/VlwLlLyqv/PwUNgL30BlTVZV1Wu4Asu2mMYPqarSO4L5ZQ== + +"@typescript-eslint/typescript-estree@5.62.0": + version "5.62.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/typescript-estree/-/typescript-estree-5.62.0.tgz#7d17794b77fabcac615d6a48fb143330d962eb9b" + integrity sha512-CmcQ6uY7b9y694lKdRB8FEel7JbU/40iSAPomu++SjLMntB+2Leay2LO6i8VnJk58MtE9/nQSFIH6jpyRWyYzA== + dependencies: + "@typescript-eslint/types" "5.62.0" + "@typescript-eslint/visitor-keys" "5.62.0" + debug "^4.3.4" + globby "^11.1.0" + is-glob "^4.0.3" + semver "^7.3.7" + tsutils "^3.21.0" + +"@typescript-eslint/typescript-estree@6.7.5": + version "6.7.5" + resolved "https://registry.yarnpkg.com/@typescript-eslint/typescript-estree/-/typescript-estree-6.7.5.tgz#4578de1a26e9f24950f029a4f00d1bfe41f15a39" + integrity sha512-NhJiJ4KdtwBIxrKl0BqG1Ur+uw7FiOnOThcYx9DpOGJ/Abc9z2xNzLeirCG02Ig3vkvrc2qFLmYSSsaITbKjlg== + dependencies: + "@typescript-eslint/types" "6.7.5" + "@typescript-eslint/visitor-keys" "6.7.5" + debug "^4.3.4" + globby "^11.1.0" + is-glob "^4.0.3" + semver "^7.5.4" + ts-api-utils "^1.0.1" + +"@typescript-eslint/utils@5.62.0": + version "5.62.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-5.62.0.tgz#141e809c71636e4a75daa39faed2fb5f4b10df86" + integrity sha512-n8oxjeb5aIbPFEtmQxQYOLI0i9n5ySBEY/ZEHHZqKQSFnxio1rv6dthascc9dLuwrL0RC5mPCxB7vnAVGAYWAQ== + dependencies: + "@eslint-community/eslint-utils" "^4.2.0" + "@types/json-schema" "^7.0.9" + "@types/semver" "^7.3.12" + "@typescript-eslint/scope-manager" "5.62.0" + "@typescript-eslint/types" "5.62.0" + "@typescript-eslint/typescript-estree" "5.62.0" + eslint-scope "^5.1.1" + semver "^7.3.7" + +"@typescript-eslint/utils@6.7.5": + version "6.7.5" + resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-6.7.5.tgz#ab847b53d6b65e029314b8247c2336843dba81ab" + integrity sha512-pfRRrH20thJbzPPlPc4j0UNGvH1PjPlhlCMq4Yx7EGjV7lvEeGX0U6MJYe8+SyFutWgSHsdbJ3BXzZccYggezA== + dependencies: + "@eslint-community/eslint-utils" "^4.4.0" + "@types/json-schema" "^7.0.12" + "@types/semver" "^7.5.0" + "@typescript-eslint/scope-manager" "6.7.5" + "@typescript-eslint/types" "6.7.5" + "@typescript-eslint/typescript-estree" "6.7.5" + semver "^7.5.4" + +"@typescript-eslint/visitor-keys@5.62.0": + version "5.62.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/visitor-keys/-/visitor-keys-5.62.0.tgz#2174011917ce582875954ffe2f6912d5931e353e" + integrity sha512-07ny+LHRzQXepkGg6w0mFY41fVUNBrL2Roj/++7V1txKugfjm/Ci/qSND03r2RhlJhJYMcTn9AhhSSqQp0Ysyw== + dependencies: + "@typescript-eslint/types" "5.62.0" + eslint-visitor-keys "^3.3.0" + +"@typescript-eslint/visitor-keys@6.7.5": + version "6.7.5" + resolved "https://registry.yarnpkg.com/@typescript-eslint/visitor-keys/-/visitor-keys-6.7.5.tgz#84c68d6ceb5b12d5246b918b84f2b79affd6c2f1" + integrity sha512-3MaWdDZtLlsexZzDSdQWsFQ9l9nL8B80Z4fImSpyllFC/KLqWQRdEcB+gGGO+N3Q2uL40EsG66wZLsohPxNXvg== + dependencies: + "@typescript-eslint/types" "6.7.5" + eslint-visitor-keys "^3.4.1" + +"@vue/eslint-config-prettier@^7.0.0": + version "7.1.0" + resolved "https://registry.yarnpkg.com/@vue/eslint-config-prettier/-/eslint-config-prettier-7.1.0.tgz#97936379c7fb1d982b9d2c6b122306e3c2e464c8" + integrity sha512-Pv/lVr0bAzSIHLd9iz0KnvAr4GKyCEl+h52bc4e5yWuDVtLgFwycF7nrbWTAQAS+FU6q1geVd07lc6EWfJiWKQ== + dependencies: + eslint-config-prettier "^8.3.0" + eslint-plugin-prettier "^4.0.0" + +"@vue/eslint-config-typescript@^10.0.0": + version "10.0.0" + resolved "https://registry.yarnpkg.com/@vue/eslint-config-typescript/-/eslint-config-typescript-10.0.0.tgz#3b63c8cf276962cb89414857581b9b424acf2820" + integrity sha512-F94cL8ug3FaYXlCfU5/wiGjk1qeadmoBpRGAOBq+qre3Smdupa59dd6ZJrsfRODpsMPyTG7330juMDsUvpZ3Rw== + dependencies: + "@typescript-eslint/eslint-plugin" "^5.0.0" + "@typescript-eslint/parser" "^5.0.0" + vue-eslint-parser "^8.0.0" + +JSONStream@1.3.2: + version "1.3.2" + resolved "https://registry.yarnpkg.com/JSONStream/-/JSONStream-1.3.2.tgz#c102371b6ec3a7cf3b847ca00c20bb0fce4c6dea" + integrity sha512-mn0KSip7N4e0UDPZHnqDsHECo5uGQrixQKnAskOM1BIB8hd7QKbd6il8IPRPudPHOeHiECoCFqhyMaRO9+nWyA== + dependencies: + jsonparse "^1.2.0" + through ">=2.2.7 <3" + +abstract-level@^1.0.0, abstract-level@^1.0.2, abstract-level@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/abstract-level/-/abstract-level-1.0.3.tgz#78a67d3d84da55ee15201486ab44c09560070741" + integrity sha512-t6jv+xHy+VYwc4xqZMn2Pa9DjcdzvzZmQGRjTFc8spIbRGHgBrEKbPq+rYXc7CCo0lxgYvSgKVg9qZAhpVQSjA== + dependencies: + buffer "^6.0.3" + catering "^2.1.0" + is-buffer "^2.0.5" + level-supports "^4.0.0" + level-transcoder "^1.0.1" + module-error "^1.0.1" + queue-microtask "^1.2.3" + +acorn-jsx@^5.3.2: + version "5.3.2" + resolved "https://registry.yarnpkg.com/acorn-jsx/-/acorn-jsx-5.3.2.tgz#7ed5bb55908b3b2f1bc55c6af1653bada7f07937" + integrity sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ== + +acorn-walk@^8.1.1: + version "8.2.0" + resolved "https://registry.yarnpkg.com/acorn-walk/-/acorn-walk-8.2.0.tgz#741210f2e2426454508853a2f44d0ab83b7f69c1" + integrity sha512-k+iyHEuPgSw6SbuDpGQM+06HQUa04DZ3o+F6CSzXMvvI5KMvnaEqXe+YVe555R9nn6GPt404fos4wcgpw12SDA== + +acorn@^8.4.1, acorn@^8.9.0: + version "8.10.0" + resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.10.0.tgz#8be5b3907a67221a81ab23c7889c4c5526b62ec5" + integrity sha512-F0SAmZ8iUtS//m8DmCTA0jlh6TDKkHQyK6xc6V4KDTyZKA9dnvX9/3sRTVQrWm79glUAZbnmmNcdYwUIHWVybw== + +adm-zip@^0.4.16: + version "0.4.16" + resolved "https://registry.yarnpkg.com/adm-zip/-/adm-zip-0.4.16.tgz#cf4c508fdffab02c269cbc7f471a875f05570365" + integrity sha512-TFi4HBKSGfIKsK5YCkKaaFG2m4PEDyViZmEwof3MTIgzimHLto6muaHVpbrljdIvIrFZzEq/p4nafOeLcYegrg== + +aes-js@3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/aes-js/-/aes-js-3.0.0.tgz#e21df10ad6c2053295bcbb8dab40b09dbea87e4d" + integrity sha512-H7wUZRn8WpTq9jocdxQ2c8x2sKo9ZVmzfRE13GiNJXfp7NcKYEdvl3vspKjXox6RIG2VtaRe4JFvxG4rqp2Zuw== + +agent-base@6: + version "6.0.2" + resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-6.0.2.tgz#49fff58577cfee3f37176feab4c22e00f86d7f77" + integrity sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ== + dependencies: + debug "4" + +aggregate-error@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/aggregate-error/-/aggregate-error-3.1.0.tgz#92670ff50f5359bdb7a3e0d40d0ec30c5737687a" + integrity sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA== + dependencies: + clean-stack "^2.0.0" + indent-string "^4.0.0" + +ajv@^6.12.4: + version "6.12.6" + resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.12.6.tgz#baf5a62e802b07d977034586f8c3baf5adf26df4" + integrity sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g== + dependencies: + fast-deep-equal "^3.1.1" + fast-json-stable-stringify "^2.0.0" + json-schema-traverse "^0.4.1" + uri-js "^4.2.2" + +ansi-colors@4.1.1: + version "4.1.1" + resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-4.1.1.tgz#cbb9ae256bf750af1eab344f229aa27fe94ba348" + integrity sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA== + +ansi-colors@^4.1.1: + version "4.1.3" + resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-4.1.3.tgz#37611340eb2243e70cc604cad35d63270d48781b" + integrity sha512-/6w/C21Pm1A7aZitlI5Ni/2J6FFQN8i1Cvz3kHABAAbw93v/NlvKdVOqz7CCWz/3iv/JplRSEEZ83XION15ovw== + +ansi-escapes@^4.3.0: + version "4.3.2" + resolved "https://registry.yarnpkg.com/ansi-escapes/-/ansi-escapes-4.3.2.tgz#6b2291d1db7d98b6521d5f1efa42d0f3a9feb65e" + integrity sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ== + dependencies: + type-fest "^0.21.3" + +ansi-regex@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-5.0.1.tgz#082cb2c89c9fe8659a311a53bd6a4dc5301db304" + integrity sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ== + +ansi-styles@^3.2.1: + version "3.2.1" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-3.2.1.tgz#41fbb20243e50b12be0f04b8dedbf07520ce841d" + integrity sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA== + dependencies: + color-convert "^1.9.0" + +ansi-styles@^4.0.0, ansi-styles@^4.1.0: + version "4.3.0" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-4.3.0.tgz#edd803628ae71c04c85ae7a0906edad34b648937" + integrity sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg== + dependencies: + color-convert "^2.0.1" + +anymatch@~3.1.2: + version "3.1.3" + resolved "https://registry.yarnpkg.com/anymatch/-/anymatch-3.1.3.tgz#790c58b19ba1720a84205b57c618d5ad8524973e" + integrity sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw== + dependencies: + normalize-path "^3.0.0" + picomatch "^2.0.4" + +arg@^4.1.0: + version "4.1.3" + resolved "https://registry.yarnpkg.com/arg/-/arg-4.1.3.tgz#269fc7ad5b8e42cb63c896d5666017261c144089" + integrity sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA== + +argparse@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/argparse/-/argparse-2.0.1.tgz#246f50f3ca78a3240f6c997e8a9bd1eac49e4b38" + integrity sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q== + +array-buffer-byte-length@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/array-buffer-byte-length/-/array-buffer-byte-length-1.0.0.tgz#fabe8bc193fea865f317fe7807085ee0dee5aead" + integrity sha512-LPuwb2P+NrQw3XhxGc36+XSvuBPopovXYTR9Ew++Du9Yb/bx5AzBfrIsBoj0EZUifjQU+sHL21sseZ3jerWO/A== + dependencies: + call-bind "^1.0.2" + is-array-buffer "^3.0.1" + +array-includes@^3.1.6: + version "3.1.7" + resolved "https://registry.yarnpkg.com/array-includes/-/array-includes-3.1.7.tgz#8cd2e01b26f7a3086cbc87271593fe921c62abda" + integrity sha512-dlcsNBIiWhPkHdOEEKnehA+RNUWDc4UqFtnIXU4uuYDPtA4LDkr7qip2p0VvFAEXNDr0yWZ9PJyIRiGjRLQzwQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + get-intrinsic "^1.2.1" + is-string "^1.0.7" + +array-union@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/array-union/-/array-union-2.1.0.tgz#b798420adbeb1de828d84acd8a2e23d3efe85e8d" + integrity sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw== + +array.prototype.findlastindex@^1.2.2: + version "1.2.3" + resolved "https://registry.yarnpkg.com/array.prototype.findlastindex/-/array.prototype.findlastindex-1.2.3.tgz#b37598438f97b579166940814e2c0493a4f50207" + integrity sha512-LzLoiOMAxvy+Gd3BAq3B7VeIgPdo+Q8hthvKtXybMvRV0jrXfJM/t8mw7nNlpEcVlVUnCnM2KSX4XU5HmpodOA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + es-shim-unscopables "^1.0.0" + get-intrinsic "^1.2.1" + +array.prototype.flat@^1.3.1: + version "1.3.2" + resolved "https://registry.yarnpkg.com/array.prototype.flat/-/array.prototype.flat-1.3.2.tgz#1476217df8cff17d72ee8f3ba06738db5b387d18" + integrity sha512-djYB+Zx2vLewY8RWlNCUdHjDXs2XOgm602S9E7P/UpHgfeHL00cRiIF+IN/G/aUJ7kGPb6yO/ErDI5V2s8iycA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + es-shim-unscopables "^1.0.0" + +array.prototype.flatmap@^1.3.1: + version "1.3.2" + resolved "https://registry.yarnpkg.com/array.prototype.flatmap/-/array.prototype.flatmap-1.3.2.tgz#c9a7c6831db8e719d6ce639190146c24bbd3e527" + integrity sha512-Ewyx0c9PmpcsByhSW4r+9zDU7sGjFc86qf/kKtuSCRdhfbk0SNLLkaT5qvcHnRGgc5NP/ly/y+qkXkqONX54CQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + es-shim-unscopables "^1.0.0" + +arraybuffer.prototype.slice@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.2.tgz#98bd561953e3e74bb34938e77647179dfe6e9f12" + integrity sha512-yMBKppFur/fbHu9/6USUe03bZ4knMYiwFBcyiaXB8Go0qNehwX6inYPzK9U0NeQvGxKthcmHcaR8P5MStSRBAw== + dependencies: + array-buffer-byte-length "^1.0.0" + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + get-intrinsic "^1.2.1" + is-array-buffer "^3.0.2" + is-shared-array-buffer "^1.0.2" + +asn1@^0.2.6: + version "0.2.6" + resolved "https://registry.yarnpkg.com/asn1/-/asn1-0.2.6.tgz#0d3a7bb6e64e02a90c0303b31f292868ea09a08d" + integrity sha512-ix/FxPn0MDjeyJ7i/yoHGFt/EX6LyNbxSEhPPXODPL+KB0VPk86UYfL0lMdy+KCnv+fmvIzySwaK5COwqVbWTQ== + dependencies: + safer-buffer "~2.1.0" + +assertion-error@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/assertion-error/-/assertion-error-1.1.0.tgz#e60b6b0e8f301bd97e5375215bda406c85118c0b" + integrity sha512-jgsaNduz+ndvGyFt3uSuWqvy4lCnIJiovtouQN5JZHOKCS2QuhEdbcQHFhVksz2N2U9hXJo8odG7ETyWlEeuDw== + +available-typed-arrays@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/available-typed-arrays/-/available-typed-arrays-1.0.5.tgz#92f95616501069d07d10edb2fc37d3e1c65123b7" + integrity sha512-DMD0KiN46eipeziST1LPP/STfDU0sufISXmjSgvVsoU2tqxctQeASejWcfNtxYKqETM1UxQ8sp2OrSBWpHY6sw== + +balanced-match@^1.0.0: + version "1.0.2" + resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.2.tgz#e83e3a7e3f300b34cb9d87f615fa0cbf357690ee" + integrity sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw== + +base-x@^3.0.2: + version "3.0.9" + resolved "https://registry.yarnpkg.com/base-x/-/base-x-3.0.9.tgz#6349aaabb58526332de9f60995e548a53fe21320" + integrity sha512-H7JU6iBHTal1gp56aKoaa//YUxEaAOUiydvrV/pILqIHXTtqxSkATOnDA2u+jZ/61sD+L/412+7kzXRtWukhpQ== + dependencies: + safe-buffer "^5.0.1" + +base64-js@^1.3.1: + version "1.5.1" + resolved "https://registry.yarnpkg.com/base64-js/-/base64-js-1.5.1.tgz#1b1b440160a5bf7ad40b650f095963481903930a" + integrity sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA== + +bcrypt-pbkdf@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz#a4301d389b6a43f9b67ff3ca11a3f6637e360e9e" + integrity sha512-qeFIXtP4MSoi6NLqO12WfqARWWuCKi2Rn/9hJLEmtB5yTNr9DqFWkJRCf2qShWzPeAMRnOgCrq0sg/KLv5ES9w== + dependencies: + tweetnacl "^0.14.3" + +bech32@1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/bech32/-/bech32-1.1.4.tgz#e38c9f37bf179b8eb16ae3a772b40c356d4832e9" + integrity sha512-s0IrSOzLlbvX7yp4WBfPITzpAU8sqQcpsmwXDiKwrG4r491vwCO/XpejasRNl0piBMe/DvP4Tz0mIS/X1DPJBQ== + +bigint-crypto-utils@^3.0.23: + version "3.3.0" + resolved "https://registry.yarnpkg.com/bigint-crypto-utils/-/bigint-crypto-utils-3.3.0.tgz#72ad00ae91062cf07f2b1def9594006c279c1d77" + integrity sha512-jOTSb+drvEDxEq6OuUybOAv/xxoh3cuYRUIPyu8sSHQNKM303UQ2R1DAo45o1AkcIXw6fzbaFI1+xGGdaXs2lg== + +binary-extensions@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/binary-extensions/-/binary-extensions-2.2.0.tgz#75f502eeaf9ffde42fc98829645be4ea76bd9e2d" + integrity sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA== + +bl@^1.0.0: + version "1.2.3" + resolved "https://registry.yarnpkg.com/bl/-/bl-1.2.3.tgz#1e8dd80142eac80d7158c9dccc047fb620e035e7" + integrity sha512-pvcNpa0UU69UT341rO6AYy4FVAIkUHuZXRIWbq+zHnsVcRzDDjIAhGuuYoi0d//cwIwtt4pkpKycWEfjdV+vww== + dependencies: + readable-stream "^2.3.5" + safe-buffer "^5.1.1" + +bl@^4.0.3: + version "4.1.0" + resolved "https://registry.yarnpkg.com/bl/-/bl-4.1.0.tgz#451535264182bec2fbbc83a62ab98cf11d9f7b3a" + integrity sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w== + dependencies: + buffer "^5.5.0" + inherits "^2.0.4" + readable-stream "^3.4.0" + +blakejs@^1.1.0: + version "1.2.1" + resolved "https://registry.yarnpkg.com/blakejs/-/blakejs-1.2.1.tgz#5057e4206eadb4a97f7c0b6e197a505042fc3814" + integrity sha512-QXUSXI3QVc/gJME0dBpXrag1kbzOqCjCX8/b54ntNyW6sjtoqxqRk3LTmXzaJoh71zMsDCjM+47jS7XiwN/+fQ== + +bn.js@^4.11.0, bn.js@^4.11.8, bn.js@^4.11.9: + version "4.12.0" + resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-4.12.0.tgz#775b3f278efbb9718eec7361f483fb36fbbfea88" + integrity sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA== + +bn.js@^5.2.0, bn.js@^5.2.1: + version "5.2.1" + resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-5.2.1.tgz#0bc527a6a0d18d0aa8d5b0538ce4a77dccfa7b70" + integrity sha512-eXRvHzWyYPBuB4NBy0cmYQjGitUrtqwbvlzP3G6VFnNRbsZQIxQ10PbKKHt8gZ/HW/D/747aDl+QkDqg3KQLMQ== + +boolbase@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/boolbase/-/boolbase-1.0.0.tgz#68dff5fbe60c51eb37725ea9e3ed310dcc1e776e" + integrity sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww== + +brace-expansion@^1.1.7: + version "1.1.11" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd" + integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA== + dependencies: + balanced-match "^1.0.0" + concat-map "0.0.1" + +brace-expansion@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-2.0.1.tgz#1edc459e0f0c548486ecf9fc99f2221364b9a0ae" + integrity sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA== + dependencies: + balanced-match "^1.0.0" + +braces@^3.0.2, braces@~3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/braces/-/braces-3.0.2.tgz#3454e1a462ee8d599e236df336cd9ea4f8afe107" + integrity sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A== + dependencies: + fill-range "^7.0.1" + +brorand@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/brorand/-/brorand-1.1.0.tgz#12c25efe40a45e3c323eb8675a0a0ce57b22371f" + integrity sha512-cKV8tMCEpQs4hK/ik71d6LrPOnpkpGBR0wzxqr68g2m/LB2GxVYQroAjMJZRVM1Y4BCjCKc3vAamxSzOY2RP+w== + +browser-level@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/browser-level/-/browser-level-1.0.1.tgz#36e8c3183d0fe1c405239792faaab5f315871011" + integrity sha512-XECYKJ+Dbzw0lbydyQuJzwNXtOpbMSq737qxJN11sIRTErOMShvDpbzTlgju7orJKvx4epULolZAuJGLzCmWRQ== + dependencies: + abstract-level "^1.0.2" + catering "^2.1.1" + module-error "^1.0.2" + run-parallel-limit "^1.1.0" + +browser-stdout@1.3.1: + version "1.3.1" + resolved "https://registry.yarnpkg.com/browser-stdout/-/browser-stdout-1.3.1.tgz#baa559ee14ced73452229bad7326467c61fabd60" + integrity sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw== + +browserify-aes@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/browserify-aes/-/browserify-aes-1.2.0.tgz#326734642f403dabc3003209853bb70ad428ef48" + integrity sha512-+7CHXqGuspUn/Sl5aO7Ea0xWGAtETPXNSAjHo48JfLdPWcMng33Xe4znFvQweqc/uzk5zSOI3H52CYnjCfb5hA== + dependencies: + buffer-xor "^1.0.3" + cipher-base "^1.0.0" + create-hash "^1.1.0" + evp_bytestokey "^1.0.3" + inherits "^2.0.1" + safe-buffer "^5.0.1" + +bs58@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/bs58/-/bs58-4.0.1.tgz#be161e76c354f6f788ae4071f63f34e8c4f0a42a" + integrity sha512-Ok3Wdf5vOIlBrgCvTq96gBkJw+JUEzdBgyaza5HLtPm7yTHkjRy8+JzNyHF7BHa0bNWOQIp3m5YF0nnFcOIKLw== + dependencies: + base-x "^3.0.2" + +bs58check@^2.1.2: + version "2.1.2" + resolved "https://registry.yarnpkg.com/bs58check/-/bs58check-2.1.2.tgz#53b018291228d82a5aa08e7d796fdafda54aebfc" + integrity sha512-0TS1jicxdU09dwJMNZtVAfzPi6Q6QeN0pM1Fkzrjn+XYHvzMKPU3pHVpva+769iNVSfIYWf7LJ6WR+BuuMf8cA== + dependencies: + bs58 "^4.0.0" + create-hash "^1.1.0" + safe-buffer "^5.1.2" + +buffer-alloc-unsafe@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/buffer-alloc-unsafe/-/buffer-alloc-unsafe-1.1.0.tgz#bd7dc26ae2972d0eda253be061dba992349c19f0" + integrity sha512-TEM2iMIEQdJ2yjPJoSIsldnleVaAk1oW3DBVUykyOLsEsFmEc9kn+SFFPz+gl54KQNxlDnAwCXosOS9Okx2xAg== + +buffer-alloc@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/buffer-alloc/-/buffer-alloc-1.2.0.tgz#890dd90d923a873e08e10e5fd51a57e5b7cce0ec" + integrity sha512-CFsHQgjtW1UChdXgbyJGtnm+O/uLQeZdtbDo8mfUgYXCHSM1wgrVxXm6bSyrUuErEb+4sYVGCzASBRot7zyrow== + dependencies: + buffer-alloc-unsafe "^1.1.0" + buffer-fill "^1.0.0" + +buffer-fill@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/buffer-fill/-/buffer-fill-1.0.0.tgz#f8f78b76789888ef39f205cd637f68e702122b2c" + integrity sha512-T7zexNBwiiaCOGDg9xNX9PBmjrubblRkENuptryuI64URkXDFum9il/JGL8Lm8wYfAXpredVXXZz7eMHilimiQ== + +buffer-from@^1.0.0: + version "1.1.2" + resolved "https://registry.yarnpkg.com/buffer-from/-/buffer-from-1.1.2.tgz#2b146a6fd72e80b4f55d255f35ed59a3a9a41bd5" + integrity sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ== + +buffer-xor@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/buffer-xor/-/buffer-xor-1.0.3.tgz#26e61ed1422fb70dd42e6e36729ed51d855fe8d9" + integrity sha512-571s0T7nZWK6vB67HI5dyUF7wXiNcfaPPPTl6zYCNApANjIvYJTg7hlud/+cJpdAhS7dVzqMLmfhfHR3rAcOjQ== + +buffer@^5.5.0: + version "5.7.1" + resolved "https://registry.yarnpkg.com/buffer/-/buffer-5.7.1.tgz#ba62e7c13133053582197160851a8f648e99eed0" + integrity sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ== + dependencies: + base64-js "^1.3.1" + ieee754 "^1.1.13" + +buffer@^6.0.3: + version "6.0.3" + resolved "https://registry.yarnpkg.com/buffer/-/buffer-6.0.3.tgz#2ace578459cc8fbe2a70aaa8f52ee63b6a74c6c6" + integrity sha512-FTiCpNxtwiZZHEZbcbTIcZjERVICn9yq/pDFkTl95/AxzD1naBctN7YO68riM/gLSDY7sdrMby8hofADYuuqOA== + dependencies: + base64-js "^1.3.1" + ieee754 "^1.2.1" + +buildcheck@~0.0.6: + version "0.0.6" + resolved "https://registry.yarnpkg.com/buildcheck/-/buildcheck-0.0.6.tgz#89aa6e417cfd1e2196e3f8fe915eb709d2fe4238" + integrity sha512-8f9ZJCUXyT1M35Jx7MkBgmBMo3oHTTBIPLiY9xyL0pl3T5RwcPEY8cUHr5LBNfu/fk6c2T4DJZuVM/8ZZT2D2A== + +bytes@3.1.2: + version "3.1.2" + resolved "https://registry.yarnpkg.com/bytes/-/bytes-3.1.2.tgz#8b0beeb98605adf1b128fa4386403c009e0221a5" + integrity sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg== + +call-bind@^1.0.0, call-bind@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/call-bind/-/call-bind-1.0.2.tgz#b1d4e89e688119c3c9a903ad30abb2f6a919be3c" + integrity sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA== + dependencies: + function-bind "^1.1.1" + get-intrinsic "^1.0.2" + +callsites@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/callsites/-/callsites-3.1.0.tgz#b3630abd8943432f54b3f0519238e33cd7df2f73" + integrity sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ== + +camelcase@^6.0.0: + version "6.3.0" + resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-6.3.0.tgz#5685b95eb209ac9c0c177467778c9c84df58ba9a" + integrity sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA== + +case@^1.6.3: + version "1.6.3" + resolved "https://registry.yarnpkg.com/case/-/case-1.6.3.tgz#0a4386e3e9825351ca2e6216c60467ff5f1ea1c9" + integrity sha512-mzDSXIPaFwVDvZAHqZ9VlbyF4yyXRuX6IvB06WvPYkqJVO24kX1PPhv9bfpKNFZyxYFmmgo03HUiD8iklmJYRQ== + +catering@^2.1.0, catering@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/catering/-/catering-2.1.1.tgz#66acba06ed5ee28d5286133982a927de9a04b510" + integrity sha512-K7Qy8O9p76sL3/3m7/zLKbRkyOlSZAgzEaLhyj2mXS8PsCud2Eo4hAb8aLtZqHh0QGqLcb9dlJSu6lHRVENm1w== + +chai@^4.3.7: + version "4.3.10" + resolved "https://registry.yarnpkg.com/chai/-/chai-4.3.10.tgz#d784cec635e3b7e2ffb66446a63b4e33bd390384" + integrity sha512-0UXG04VuVbruMUYbJ6JctvH0YnC/4q3/AkT18q4NaITo91CUm0liMS9VqzT9vZhVQ/1eqPanMWjBM+Juhfb/9g== + dependencies: + assertion-error "^1.1.0" + check-error "^1.0.3" + deep-eql "^4.1.3" + get-func-name "^2.0.2" + loupe "^2.3.6" + pathval "^1.1.1" + type-detect "^4.0.8" + +chalk@4.1.2, chalk@^4.0.0, chalk@^4.1.0: + version "4.1.2" + resolved "https://registry.yarnpkg.com/chalk/-/chalk-4.1.2.tgz#aac4e2b7734a740867aeb16bf02aad556a1e7a01" + integrity sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA== + dependencies: + ansi-styles "^4.1.0" + supports-color "^7.1.0" + +chalk@^2.4.2: + version "2.4.2" + resolved "https://registry.yarnpkg.com/chalk/-/chalk-2.4.2.tgz#cd42541677a54333cf541a49108c1432b44c9424" + integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ== + dependencies: + ansi-styles "^3.2.1" + escape-string-regexp "^1.0.5" + supports-color "^5.3.0" + +check-error@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/check-error/-/check-error-1.0.3.tgz#a6502e4312a7ee969f646e83bb3ddd56281bd694" + integrity sha512-iKEoDYaRmd1mxM90a2OEfWhjsjPpYPuQ+lMYsoxB126+t8fw7ySEO48nmDg5COTjxDI65/Y2OWpeEHk3ZOe8zg== + dependencies: + get-func-name "^2.0.2" + +chokidar@3.5.3, chokidar@^3.4.0: + version "3.5.3" + resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-3.5.3.tgz#1cf37c8707b932bd1af1ae22c0432e2acd1903bd" + integrity sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw== + dependencies: + anymatch "~3.1.2" + braces "~3.0.2" + glob-parent "~5.1.2" + is-binary-path "~2.1.0" + is-glob "~4.0.1" + normalize-path "~3.0.0" + readdirp "~3.6.0" + optionalDependencies: + fsevents "~2.3.2" + +chownr@^1.0.1, chownr@^1.1.1: + version "1.1.4" + resolved "https://registry.yarnpkg.com/chownr/-/chownr-1.1.4.tgz#6fc9d7b42d32a583596337666e7d08084da2cc6b" + integrity sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg== + +ci-info@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/ci-info/-/ci-info-2.0.0.tgz#67a9e964be31a51e15e5010d58e6f12834002f46" + integrity sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ== + +cipher-base@^1.0.0, cipher-base@^1.0.1, cipher-base@^1.0.3: + version "1.0.4" + resolved "https://registry.yarnpkg.com/cipher-base/-/cipher-base-1.0.4.tgz#8760e4ecc272f4c363532f926d874aae2c1397de" + integrity sha512-Kkht5ye6ZGmwv40uUDZztayT2ThLQGfnj/T71N/XzeZeo3nf8foyW7zGTsPYkEya3m5f3cAypH+qe7YOrM1U2Q== + dependencies: + inherits "^2.0.1" + safe-buffer "^5.0.1" + +classic-level@^1.2.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/classic-level/-/classic-level-1.3.0.tgz#5e36680e01dc6b271775c093f2150844c5edd5c8" + integrity sha512-iwFAJQYtqRTRM0F6L8h4JCt00ZSGdOyqh7yVrhhjrOpFhmBjNlRUey64MCiyo6UmQHMJ+No3c81nujPv+n9yrg== + dependencies: + abstract-level "^1.0.2" + catering "^2.1.0" + module-error "^1.0.1" + napi-macros "^2.2.2" + node-gyp-build "^4.3.0" + +clean-stack@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/clean-stack/-/clean-stack-2.2.0.tgz#ee8472dbb129e727b31e8a10a427dee9dfe4008b" + integrity sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A== + +cliui@^7.0.2: + version "7.0.4" + resolved "https://registry.yarnpkg.com/cliui/-/cliui-7.0.4.tgz#a0265ee655476fc807aea9df3df8df7783808b4f" + integrity sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ== + dependencies: + string-width "^4.2.0" + strip-ansi "^6.0.0" + wrap-ansi "^7.0.0" + +code-block-writer@^12.0.0: + version "12.0.0" + resolved "https://registry.yarnpkg.com/code-block-writer/-/code-block-writer-12.0.0.tgz#4dd58946eb4234105aff7f0035977b2afdc2a770" + integrity sha512-q4dMFMlXtKR3XNBHyMHt/3pwYNA69EDk00lloMOaaUMKPUXBw6lpXtbu3MMVG6/uOihGnRDOlkyqsONEUj60+w== + +color-convert@^1.9.0: + version "1.9.3" + resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-1.9.3.tgz#bb71850690e1f136567de629d2d5471deda4c1e8" + integrity sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg== + dependencies: + color-name "1.1.3" + +color-convert@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-2.0.1.tgz#72d3a68d598c9bdb3af2ad1e84f21d896abd4de3" + integrity sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ== + dependencies: + color-name "~1.1.4" + +color-name@1.1.3: + version "1.1.3" + resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.3.tgz#a7d0558bd89c42f795dd42328f740831ca53bc25" + integrity sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw== + +color-name@~1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.4.tgz#c2a09a87acbde69543de6f63fa3995c826c536a2" + integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA== + +command-exists@^1.2.8: + version "1.2.9" + resolved "https://registry.yarnpkg.com/command-exists/-/command-exists-1.2.9.tgz#c50725af3808c8ab0260fd60b01fbfa25b954f69" + integrity sha512-LTQ/SGc+s0Xc0Fu5WaKnR0YiygZkm9eKFvyS+fRsU7/ZWFF8ykFM6Pc9aCVf1+xasOOZpO3BAVgVrKvsqKHV7w== + +commander@3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/commander/-/commander-3.0.2.tgz#6837c3fb677ad9933d1cfba42dd14d5117d6b39e" + integrity sha512-Gar0ASD4BDyKC4hl4DwHqDrmvjoxWKZigVnAbn5H1owvm4CxCPdb0HQDehwNYMJpla5+M2tPmPARzhtYuwpHow== + +concat-map@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" + integrity sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg== + +concat-stream@~1.6.2: + version "1.6.2" + resolved "https://registry.yarnpkg.com/concat-stream/-/concat-stream-1.6.2.tgz#904bdf194cd3122fc675c77fc4ac3d4ff0fd1a34" + integrity sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw== + dependencies: + buffer-from "^1.0.0" + inherits "^2.0.3" + readable-stream "^2.2.2" + typedarray "^0.0.6" + +cookie@^0.4.1: + version "0.4.2" + resolved "https://registry.yarnpkg.com/cookie/-/cookie-0.4.2.tgz#0e41f24de5ecf317947c82fc789e06a884824432" + integrity sha512-aSWTXFzaKWkvHO1Ny/s+ePFpvKsPnjc551iI41v3ny/ow6tBG5Vd+FuqGNhh1LxOmVzOlGUriIlOaokOvhaStA== + +core-util-is@~1.0.0: + version "1.0.3" + resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.3.tgz#a6042d3634c2b27e9328f837b965fac83808db85" + integrity sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ== + +cpu-features@~0.0.8: + version "0.0.9" + resolved "https://registry.yarnpkg.com/cpu-features/-/cpu-features-0.0.9.tgz#5226b92f0f1c63122b0a3eb84cb8335a4de499fc" + integrity sha512-AKjgn2rP2yJyfbepsmLfiYcmtNn/2eUvocUyM/09yB0YDiz39HteK/5/T4Onf0pmdYDMgkBoGvRLvEguzyL7wQ== + dependencies: + buildcheck "~0.0.6" + nan "^2.17.0" + +crc-32@^1.2.0: + version "1.2.2" + resolved "https://registry.yarnpkg.com/crc-32/-/crc-32-1.2.2.tgz#3cad35a934b8bf71f25ca524b6da51fb7eace2ff" + integrity sha512-ROmzCKrTnOwybPcJApAA6WBWij23HVfGVNKqqrZpuyZOHqK2CwHSvpGuyt/UNNvaIjEd8X5IFGp4Mh+Ie1IHJQ== + +create-hash@^1.1.0, create-hash@^1.1.2, create-hash@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/create-hash/-/create-hash-1.2.0.tgz#889078af11a63756bcfb59bd221996be3a9ef196" + integrity sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg== + dependencies: + cipher-base "^1.0.1" + inherits "^2.0.1" + md5.js "^1.3.4" + ripemd160 "^2.0.1" + sha.js "^2.4.0" + +create-hmac@^1.1.4, create-hmac@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/create-hmac/-/create-hmac-1.1.7.tgz#69170c78b3ab957147b2b8b04572e47ead2243ff" + integrity sha512-MJG9liiZ+ogc4TzUwuvbER1JRdgvUFSB5+VR/g5h82fGaIRWMWddtKBHi7/sVhfjQZ6SehlyhvQYrcYkaUIpLg== + dependencies: + cipher-base "^1.0.3" + create-hash "^1.1.0" + inherits "^2.0.1" + ripemd160 "^2.0.0" + safe-buffer "^5.0.1" + sha.js "^2.4.8" + +create-require@^1.1.0: + version "1.1.1" + resolved "https://registry.yarnpkg.com/create-require/-/create-require-1.1.1.tgz#c1d7e8f1e5f6cfc9ff65f9cd352d37348756c333" + integrity sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ== + +cross-spawn@^7.0.2: + version "7.0.3" + resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.3.tgz#f73a85b9d5d41d045551c177e2882d4ac85728a6" + integrity sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w== + dependencies: + path-key "^3.1.0" + shebang-command "^2.0.0" + which "^2.0.1" + +cssesc@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/cssesc/-/cssesc-3.0.0.tgz#37741919903b868565e1c09ea747445cd18983ee" + integrity sha512-/Tb/JcjK111nNScGob5MNtsntNM1aCNUDipB/TkwZFhyDrrE47SOx/18wF2bbjgc3ZzCSKW1T5nt5EbFoAz/Vg== + +debug@4, debug@4.3.4, debug@^4.1.1, debug@^4.3.2, debug@^4.3.3, debug@^4.3.4: + version "4.3.4" + resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.4.tgz#1319f6579357f2338d3337d2cdd4914bb5dcc865" + integrity sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ== + dependencies: + ms "2.1.2" + +debug@^3.2.6, debug@^3.2.7: + version "3.2.7" + resolved "https://registry.yarnpkg.com/debug/-/debug-3.2.7.tgz#72580b7e9145fb39b6676f9c5e5fb100b934179a" + integrity sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ== + dependencies: + ms "^2.1.1" + +decamelize@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-4.0.0.tgz#aa472d7bf660eb15f3494efd531cab7f2a709837" + integrity sha512-9iE1PgSik9HeIIw2JO94IidnE3eBoQrFJ3w7sFuzSX4DpmZ3v5sZpUiV5Swcf6mQEF+Y0ru8Neo+p+nyh2J+hQ== + +deep-eql@^4.1.3: + version "4.1.3" + resolved "https://registry.yarnpkg.com/deep-eql/-/deep-eql-4.1.3.tgz#7c7775513092f7df98d8df9996dd085eb668cc6d" + integrity sha512-WaEtAOpRA1MQ0eohqZjpGD8zdI0Ovsm8mmFhaDN8dvDZzyoUMcYDnf5Y6iu7HTXxf8JDS23qWa4a+hKCDyOPzw== + dependencies: + type-detect "^4.0.0" + +deep-is@^0.1.3: + version "0.1.4" + resolved "https://registry.yarnpkg.com/deep-is/-/deep-is-0.1.4.tgz#a6f2dce612fadd2ef1f519b73551f17e85199831" + integrity sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ== + +define-data-property@^1.0.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/define-data-property/-/define-data-property-1.1.1.tgz#c35f7cd0ab09883480d12ac5cb213715587800b3" + integrity sha512-E7uGkTzkk1d0ByLeSc6ZsFS79Axg+m1P/VsgYsxHgiuc3tFSj+MjMIwe90FC4lOAZzNBdY7kkO2P2wKdsQ1vgQ== + dependencies: + get-intrinsic "^1.2.1" + gopd "^1.0.1" + has-property-descriptors "^1.0.0" + +define-properties@^1.1.3, define-properties@^1.1.4, define-properties@^1.2.0: + version "1.2.1" + resolved "https://registry.yarnpkg.com/define-properties/-/define-properties-1.2.1.tgz#10781cc616eb951a80a034bafcaa7377f6af2b6c" + integrity sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg== + dependencies: + define-data-property "^1.0.1" + has-property-descriptors "^1.0.0" + object-keys "^1.1.1" + +depd@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/depd/-/depd-2.0.0.tgz#b696163cc757560d09cf22cc8fad1571b79e76df" + integrity sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw== + +diff@5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/diff/-/diff-5.0.0.tgz#7ed6ad76d859d030787ec35855f5b1daf31d852b" + integrity sha512-/VTCrvm5Z0JGty/BWHljh+BAiw3IK+2j87NGMu8Nwc/f48WoDAC395uomO9ZD117ZOBaHmkX1oyLvkVM/aIT3w== + +diff@^4.0.1: + version "4.0.2" + resolved "https://registry.yarnpkg.com/diff/-/diff-4.0.2.tgz#60f3aecb89d5fae520c11aa19efc2bb982aade7d" + integrity sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A== + +dir-glob@^3.0.1: + version "3.0.1" + resolved "https://registry.yarnpkg.com/dir-glob/-/dir-glob-3.0.1.tgz#56dbf73d992a4a93ba1584f4534063fd2e41717f" + integrity sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA== + dependencies: + path-type "^4.0.0" + +docker-modem@^1.0.8: + version "1.0.9" + resolved "https://registry.yarnpkg.com/docker-modem/-/docker-modem-1.0.9.tgz#a1f13e50e6afb6cf3431b2d5e7aac589db6aaba8" + integrity sha512-lVjqCSCIAUDZPAZIeyM125HXfNvOmYYInciphNrLrylUtKyW66meAjSPXWchKVzoIYZx69TPnAepVSSkeawoIw== + dependencies: + JSONStream "1.3.2" + debug "^3.2.6" + readable-stream "~1.0.26-4" + split-ca "^1.0.0" + +docker-modem@^3.0.0: + version "3.0.8" + resolved "https://registry.yarnpkg.com/docker-modem/-/docker-modem-3.0.8.tgz#ef62c8bdff6e8a7d12f0160988c295ea8705e77a" + integrity sha512-f0ReSURdM3pcKPNS30mxOHSbaFLcknGmQjwSfmbcdOw1XWKXVhukM3NJHhr7NpY9BIyyWQb0EBo3KQvvuU5egQ== + dependencies: + debug "^4.1.1" + readable-stream "^3.5.0" + split-ca "^1.0.1" + ssh2 "^1.11.0" + +dockerode@^2.5.8: + version "2.5.8" + resolved "https://registry.yarnpkg.com/dockerode/-/dockerode-2.5.8.tgz#1b661e36e1e4f860e25f56e0deabe9f87f1d0acc" + integrity sha512-+7iOUYBeDTScmOmQqpUYQaE7F4vvIt6+gIZNHWhqAQEI887tiPFB9OvXI/HzQYqfUNvukMK+9myLW63oTJPZpw== + dependencies: + concat-stream "~1.6.2" + docker-modem "^1.0.8" + tar-fs "~1.16.3" + +dockerode@^3.3.4: + version "3.3.5" + resolved "https://registry.yarnpkg.com/dockerode/-/dockerode-3.3.5.tgz#7ae3f40f2bec53ae5e9a741ce655fff459745629" + integrity sha512-/0YNa3ZDNeLr/tSckmD69+Gq+qVNhvKfAHNeZJBnp7EOP6RGKV8ORrJHkUn20So5wU+xxT7+1n5u8PjHbfjbSA== + dependencies: + "@balena/dockerignore" "^1.0.2" + docker-modem "^3.0.0" + tar-fs "~2.0.1" + +doctrine@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-2.1.0.tgz#5cd01fc101621b42c4cd7f5d1a66243716d3f39d" + integrity sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw== + dependencies: + esutils "^2.0.2" + +doctrine@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-3.0.0.tgz#addebead72a6574db783639dc87a121773973961" + integrity sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w== + dependencies: + esutils "^2.0.2" + +elliptic@6.5.4, elliptic@^6.5.2, elliptic@^6.5.4: + version "6.5.4" + resolved "https://registry.yarnpkg.com/elliptic/-/elliptic-6.5.4.tgz#da37cebd31e79a1367e941b592ed1fbebd58abbb" + integrity sha512-iLhC6ULemrljPZb+QutR5TQGB+pdW6KGD5RSegS+8sorOZT+rdQFbsQFJgvN3eRqNALqJer4oQ16YvJHlU8hzQ== + dependencies: + bn.js "^4.11.9" + brorand "^1.1.0" + hash.js "^1.0.0" + hmac-drbg "^1.0.1" + inherits "^2.0.4" + minimalistic-assert "^1.0.1" + minimalistic-crypto-utils "^1.0.1" + +emoji-regex@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-8.0.0.tgz#e818fd69ce5ccfcb404594f842963bf53164cc37" + integrity sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A== + +end-of-stream@^1.0.0, end-of-stream@^1.1.0, end-of-stream@^1.4.1: + version "1.4.4" + resolved "https://registry.yarnpkg.com/end-of-stream/-/end-of-stream-1.4.4.tgz#5ae64a5f45057baf3626ec14da0ca5e4b2431eb0" + integrity sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q== + dependencies: + once "^1.4.0" + +enquirer@^2.3.0: + version "2.4.1" + resolved "https://registry.yarnpkg.com/enquirer/-/enquirer-2.4.1.tgz#93334b3fbd74fc7097b224ab4a8fb7e40bf4ae56" + integrity sha512-rRqJg/6gd538VHvR3PSrdRBb/1Vy2YfzHqzvbhGIQpDRKIa4FgV/54b5Q1xYSxOOwKvjXweS26E0Q+nAMwp2pQ== + dependencies: + ansi-colors "^4.1.1" + strip-ansi "^6.0.1" + +env-paths@^2.2.0: + version "2.2.1" + resolved "https://registry.yarnpkg.com/env-paths/-/env-paths-2.2.1.tgz#420399d416ce1fbe9bc0a07c62fa68d67fd0f8f2" + integrity sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A== + +es-abstract@^1.22.1: + version "1.22.2" + resolved "https://registry.yarnpkg.com/es-abstract/-/es-abstract-1.22.2.tgz#90f7282d91d0ad577f505e423e52d4c1d93c1b8a" + integrity sha512-YoxfFcDmhjOgWPWsV13+2RNjq1F6UQnfs+8TftwNqtzlmFzEXvlUwdrNrYeaizfjQzRMxkZ6ElWMOJIFKdVqwA== + dependencies: + array-buffer-byte-length "^1.0.0" + arraybuffer.prototype.slice "^1.0.2" + available-typed-arrays "^1.0.5" + call-bind "^1.0.2" + es-set-tostringtag "^2.0.1" + es-to-primitive "^1.2.1" + function.prototype.name "^1.1.6" + get-intrinsic "^1.2.1" + get-symbol-description "^1.0.0" + globalthis "^1.0.3" + gopd "^1.0.1" + has "^1.0.3" + has-property-descriptors "^1.0.0" + has-proto "^1.0.1" + has-symbols "^1.0.3" + internal-slot "^1.0.5" + is-array-buffer "^3.0.2" + is-callable "^1.2.7" + is-negative-zero "^2.0.2" + is-regex "^1.1.4" + is-shared-array-buffer "^1.0.2" + is-string "^1.0.7" + is-typed-array "^1.1.12" + is-weakref "^1.0.2" + object-inspect "^1.12.3" + object-keys "^1.1.1" + object.assign "^4.1.4" + regexp.prototype.flags "^1.5.1" + safe-array-concat "^1.0.1" + safe-regex-test "^1.0.0" + string.prototype.trim "^1.2.8" + string.prototype.trimend "^1.0.7" + string.prototype.trimstart "^1.0.7" + typed-array-buffer "^1.0.0" + typed-array-byte-length "^1.0.0" + typed-array-byte-offset "^1.0.0" + typed-array-length "^1.0.4" + unbox-primitive "^1.0.2" + which-typed-array "^1.1.11" + +es-set-tostringtag@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/es-set-tostringtag/-/es-set-tostringtag-2.0.1.tgz#338d502f6f674301d710b80c8592de8a15f09cd8" + integrity sha512-g3OMbtlwY3QewlqAiMLI47KywjWZoEytKr8pf6iTC8uJq5bIAH52Z9pnQ8pVL6whrCto53JZDuUIsifGeLorTg== + dependencies: + get-intrinsic "^1.1.3" + has "^1.0.3" + has-tostringtag "^1.0.0" + +es-shim-unscopables@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/es-shim-unscopables/-/es-shim-unscopables-1.0.0.tgz#702e632193201e3edf8713635d083d378e510241" + integrity sha512-Jm6GPcCdC30eMLbZ2x8z2WuRwAws3zTBBKuusffYVUrNj/GVSUAZ+xKMaUpfNDR5IbyNA5LJbaecoUVbmUcB1w== + dependencies: + has "^1.0.3" + +es-to-primitive@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/es-to-primitive/-/es-to-primitive-1.2.1.tgz#e55cd4c9cdc188bcefb03b366c736323fc5c898a" + integrity sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA== + dependencies: + is-callable "^1.1.4" + is-date-object "^1.0.1" + is-symbol "^1.0.2" + +escalade@^3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/escalade/-/escalade-3.1.1.tgz#d8cfdc7000965c5a0174b4a82eaa5c0552742e40" + integrity sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw== + +escape-string-regexp@4.0.0, escape-string-regexp@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz#14ba83a5d373e3d311e5afca29cf5bfad965bf34" + integrity sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA== + +escape-string-regexp@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4" + integrity sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg== + +eslint-config-prettier@^8.3.0: + version "8.10.0" + resolved "https://registry.yarnpkg.com/eslint-config-prettier/-/eslint-config-prettier-8.10.0.tgz#3a06a662130807e2502fc3ff8b4143d8a0658e11" + integrity sha512-SM8AMJdeQqRYT9O9zguiruQZaN7+z+E4eAP9oiLNGKMtomwaB1E9dcgUD6ZAn/eQAb52USbvezbiljfZUhbJcg== + +eslint-config-prettier@^9.0.0: + version "9.0.0" + resolved "https://registry.yarnpkg.com/eslint-config-prettier/-/eslint-config-prettier-9.0.0.tgz#eb25485946dd0c66cd216a46232dc05451518d1f" + integrity sha512-IcJsTkJae2S35pRsRAwoCE+925rJJStOdkKnLVgtE+tEpqU0EVVM7OqrwxqgptKdX29NUwC82I5pXsGFIgSevw== + +eslint-import-resolver-node@^0.3.7: + version "0.3.9" + resolved "https://registry.yarnpkg.com/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.9.tgz#d4eaac52b8a2e7c3cd1903eb00f7e053356118ac" + integrity sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g== + dependencies: + debug "^3.2.7" + is-core-module "^2.13.0" + resolve "^1.22.4" + +eslint-module-utils@^2.8.0: + version "2.8.0" + resolved "https://registry.yarnpkg.com/eslint-module-utils/-/eslint-module-utils-2.8.0.tgz#e439fee65fc33f6bba630ff621efc38ec0375c49" + integrity sha512-aWajIYfsqCKRDgUfjEXNN/JlrzauMuSEy5sbd7WXbtW3EH6A6MpwEh42c7qD+MqQo9QMJ6fWLAeIJynx0g6OAw== + dependencies: + debug "^3.2.7" + +eslint-plugin-import@^2.26.0: + version "2.28.1" + resolved "https://registry.yarnpkg.com/eslint-plugin-import/-/eslint-plugin-import-2.28.1.tgz#63b8b5b3c409bfc75ebaf8fb206b07ab435482c4" + integrity sha512-9I9hFlITvOV55alzoKBI+K9q74kv0iKMeY6av5+umsNwayt59fz692daGyjR+oStBQgx6nwR9rXldDev3Clw+A== + dependencies: + array-includes "^3.1.6" + array.prototype.findlastindex "^1.2.2" + array.prototype.flat "^1.3.1" + array.prototype.flatmap "^1.3.1" + debug "^3.2.7" + doctrine "^2.1.0" + eslint-import-resolver-node "^0.3.7" + eslint-module-utils "^2.8.0" + has "^1.0.3" + is-core-module "^2.13.0" + is-glob "^4.0.3" + minimatch "^3.1.2" + object.fromentries "^2.0.6" + object.groupby "^1.0.0" + object.values "^1.1.6" + semver "^6.3.1" + tsconfig-paths "^3.14.2" + +eslint-plugin-mocha@^10.2.0: + version "10.2.0" + resolved "https://registry.yarnpkg.com/eslint-plugin-mocha/-/eslint-plugin-mocha-10.2.0.tgz#15b05ce5be4b332bb0d76826ec1c5ebf67102ad6" + integrity sha512-ZhdxzSZnd1P9LqDPF0DBcFLpRIGdh1zkF2JHnQklKQOvrQtT73kdP5K9V2mzvbLR+cCAO9OI48NXK/Ax9/ciCQ== + dependencies: + eslint-utils "^3.0.0" + rambda "^7.4.0" + +eslint-plugin-prettier@^4.0.0: + version "4.2.1" + resolved "https://registry.yarnpkg.com/eslint-plugin-prettier/-/eslint-plugin-prettier-4.2.1.tgz#651cbb88b1dab98bfd42f017a12fa6b2d993f94b" + integrity sha512-f/0rXLXUt0oFYs8ra4w49wYZBG5GKZpAYsJSm6rnYL5uVDjd+zowwMwVZHnAjf4edNrKpCDYfXDgmRE/Ak7QyQ== + dependencies: + prettier-linter-helpers "^1.0.0" + +eslint-plugin-vue@^8.6.0: + version "8.7.1" + resolved "https://registry.yarnpkg.com/eslint-plugin-vue/-/eslint-plugin-vue-8.7.1.tgz#f13c53547a0c9d64588a675cc5ecc6ccaf63703f" + integrity sha512-28sbtm4l4cOzoO1LtzQPxfxhQABararUb1JtqusQqObJpWX2e/gmVyeYVfepizPFne0Q5cILkYGiBoV36L12Wg== + dependencies: + eslint-utils "^3.0.0" + natural-compare "^1.4.0" + nth-check "^2.0.1" + postcss-selector-parser "^6.0.9" + semver "^7.3.5" + vue-eslint-parser "^8.0.1" + +eslint-scope@^5.1.1: + version "5.1.1" + resolved "https://registry.yarnpkg.com/eslint-scope/-/eslint-scope-5.1.1.tgz#e786e59a66cb92b3f6c1fb0d508aab174848f48c" + integrity sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw== + dependencies: + esrecurse "^4.3.0" + estraverse "^4.1.1" + +eslint-scope@^7.0.0, eslint-scope@^7.2.2: + version "7.2.2" + resolved "https://registry.yarnpkg.com/eslint-scope/-/eslint-scope-7.2.2.tgz#deb4f92563390f32006894af62a22dba1c46423f" + integrity sha512-dOt21O7lTMhDM+X9mB4GX+DZrZtCUJPL/wlcTqxyrx5IvO0IYtILdtrQGQp+8n5S0gwSVmOf9NQrjMOgfQZlIg== + dependencies: + esrecurse "^4.3.0" + estraverse "^5.2.0" + +eslint-utils@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/eslint-utils/-/eslint-utils-3.0.0.tgz#8aebaface7345bb33559db0a1f13a1d2d48c3672" + integrity sha512-uuQC43IGctw68pJA1RgbQS8/NP7rch6Cwd4j3ZBtgo4/8Flj4eGE7ZYSZRN3iq5pVUv6GPdW5Z1RFleo84uLDA== + dependencies: + eslint-visitor-keys "^2.0.0" + +eslint-visitor-keys@^2.0.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/eslint-visitor-keys/-/eslint-visitor-keys-2.1.0.tgz#f65328259305927392c938ed44eb0a5c9b2bd303" + integrity sha512-0rSmRBzXgDzIsD6mGdJgevzgezI534Cer5L/vyMX0kHzT/jiB43jRhd9YUlMGYLQy2zprNmoT8qasCGtY+QaKw== + +eslint-visitor-keys@^3.1.0, eslint-visitor-keys@^3.3.0, eslint-visitor-keys@^3.4.1, eslint-visitor-keys@^3.4.3: + version "3.4.3" + resolved "https://registry.yarnpkg.com/eslint-visitor-keys/-/eslint-visitor-keys-3.4.3.tgz#0cd72fe8550e3c2eae156a96a4dddcd1c8ac5800" + integrity sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag== + +eslint@^8.48.0: + version "8.51.0" + resolved "https://registry.yarnpkg.com/eslint/-/eslint-8.51.0.tgz#4a82dae60d209ac89a5cff1604fea978ba4950f3" + integrity sha512-2WuxRZBrlwnXi+/vFSJyjMqrNjtJqiasMzehF0shoLaW7DzS3/9Yvrmq5JiT66+pNjiX4UBnLDiKHcWAr/OInA== + dependencies: + "@eslint-community/eslint-utils" "^4.2.0" + "@eslint-community/regexpp" "^4.6.1" + "@eslint/eslintrc" "^2.1.2" + "@eslint/js" "8.51.0" + "@humanwhocodes/config-array" "^0.11.11" + "@humanwhocodes/module-importer" "^1.0.1" + "@nodelib/fs.walk" "^1.2.8" + ajv "^6.12.4" + chalk "^4.0.0" + cross-spawn "^7.0.2" + debug "^4.3.2" + doctrine "^3.0.0" + escape-string-regexp "^4.0.0" + eslint-scope "^7.2.2" + eslint-visitor-keys "^3.4.3" + espree "^9.6.1" + esquery "^1.4.2" + esutils "^2.0.2" + fast-deep-equal "^3.1.3" + file-entry-cache "^6.0.1" + find-up "^5.0.0" + glob-parent "^6.0.2" + globals "^13.19.0" + graphemer "^1.4.0" + ignore "^5.2.0" + imurmurhash "^0.1.4" + is-glob "^4.0.0" + is-path-inside "^3.0.3" + js-yaml "^4.1.0" + json-stable-stringify-without-jsonify "^1.0.1" + levn "^0.4.1" + lodash.merge "^4.6.2" + minimatch "^3.1.2" + natural-compare "^1.4.0" + optionator "^0.9.3" + strip-ansi "^6.0.1" + text-table "^0.2.0" + +espree@^9.0.0, espree@^9.6.0, espree@^9.6.1: + version "9.6.1" + resolved "https://registry.yarnpkg.com/espree/-/espree-9.6.1.tgz#a2a17b8e434690a5432f2f8018ce71d331a48c6f" + integrity sha512-oruZaFkjorTpF32kDSI5/75ViwGeZginGGy2NoOSg3Q9bnwlnmDm4HLnkl0RE3n+njDXR037aY1+x58Z/zFdwQ== + dependencies: + acorn "^8.9.0" + acorn-jsx "^5.3.2" + eslint-visitor-keys "^3.4.1" + +esquery@^1.4.0, esquery@^1.4.2: + version "1.5.0" + resolved "https://registry.yarnpkg.com/esquery/-/esquery-1.5.0.tgz#6ce17738de8577694edd7361c57182ac8cb0db0b" + integrity sha512-YQLXUplAwJgCydQ78IMJywZCceoqk1oH01OERdSAJc/7U2AylwjhSCLDEtqwg811idIS/9fIU5GjG73IgjKMVg== + dependencies: + estraverse "^5.1.0" + +esrecurse@^4.3.0: + version "4.3.0" + resolved "https://registry.yarnpkg.com/esrecurse/-/esrecurse-4.3.0.tgz#7ad7964d679abb28bee72cec63758b1c5d2c9921" + integrity sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag== + dependencies: + estraverse "^5.2.0" + +estraverse@^4.1.1: + version "4.3.0" + resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-4.3.0.tgz#398ad3f3c5a24948be7725e83d11a7de28cdbd1d" + integrity sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw== + +estraverse@^5.1.0, estraverse@^5.2.0: + version "5.3.0" + resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-5.3.0.tgz#2eea5290702f26ab8fe5370370ff86c965d21123" + integrity sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA== + +esutils@^2.0.2: + version "2.0.3" + resolved "https://registry.yarnpkg.com/esutils/-/esutils-2.0.3.tgz#74d2eb4de0b8da1293711910d50775b9b710ef64" + integrity sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g== + +ethereum-cryptography@0.1.3, ethereum-cryptography@^0.1.3: + version "0.1.3" + resolved "https://registry.yarnpkg.com/ethereum-cryptography/-/ethereum-cryptography-0.1.3.tgz#8d6143cfc3d74bf79bbd8edecdf29e4ae20dd191" + integrity sha512-w8/4x1SGGzc+tO97TASLja6SLd3fRIK2tLVcV2Gx4IB21hE19atll5Cq9o3d0ZmAYC/8aw0ipieTSiekAea4SQ== + dependencies: + "@types/pbkdf2" "^3.0.0" + "@types/secp256k1" "^4.0.1" + blakejs "^1.1.0" + browserify-aes "^1.2.0" + bs58check "^2.1.2" + create-hash "^1.2.0" + create-hmac "^1.1.7" + hash.js "^1.1.7" + keccak "^3.0.0" + pbkdf2 "^3.0.17" + randombytes "^2.1.0" + safe-buffer "^5.1.2" + scrypt-js "^3.0.0" + secp256k1 "^4.0.1" + setimmediate "^1.0.5" + +ethereum-cryptography@^1.0.3: + version "1.2.0" + resolved "https://registry.yarnpkg.com/ethereum-cryptography/-/ethereum-cryptography-1.2.0.tgz#5ccfa183e85fdaf9f9b299a79430c044268c9b3a" + integrity sha512-6yFQC9b5ug6/17CQpCyE3k9eKBMdhyVjzUy1WkiuY/E4vj/SXDBbCw8QEIaXqf0Mf2SnY6RmpDcwlUmBSS0EJw== + dependencies: + "@noble/hashes" "1.2.0" + "@noble/secp256k1" "1.7.1" + "@scure/bip32" "1.1.5" + "@scure/bip39" "1.1.1" + +ethereumjs-abi@^0.6.8: + version "0.6.8" + resolved "https://registry.yarnpkg.com/ethereumjs-abi/-/ethereumjs-abi-0.6.8.tgz#71bc152db099f70e62f108b7cdfca1b362c6fcae" + integrity sha512-Tx0r/iXI6r+lRsdvkFDlut0N08jWMnKRZ6Gkq+Nmw75lZe4e6o3EkSnkaBP5NF6+m5PTGAr9JP43N3LyeoglsA== + dependencies: + bn.js "^4.11.8" + ethereumjs-util "^6.0.0" + +ethereumjs-util@^6.0.0, ethereumjs-util@^6.2.1: + version "6.2.1" + resolved "https://registry.yarnpkg.com/ethereumjs-util/-/ethereumjs-util-6.2.1.tgz#fcb4e4dd5ceacb9d2305426ab1a5cd93e3163b69" + integrity sha512-W2Ktez4L01Vexijrm5EB6w7dg4n/TgpoYU4avuT5T3Vmnw/eCRtiBrJfQYS/DCSvDIOLn2k57GcHdeBcgVxAqw== + dependencies: + "@types/bn.js" "^4.11.3" + bn.js "^4.11.0" + create-hash "^1.1.2" + elliptic "^6.5.2" + ethereum-cryptography "^0.1.3" + ethjs-util "0.1.6" + rlp "^2.2.3" + +ethers@^5.7.1, ethers@^5.7.2: + version "5.7.2" + resolved "https://registry.yarnpkg.com/ethers/-/ethers-5.7.2.tgz#3a7deeabbb8c030d4126b24f84e525466145872e" + integrity sha512-wswUsmWo1aOK8rR7DIKiWSw9DbLWe6x98Jrn8wcTflTVvaXhAMaB5zGAXy0GYQEQp9iO1iSHWVyARQm11zUtyg== + dependencies: + "@ethersproject/abi" "5.7.0" + "@ethersproject/abstract-provider" "5.7.0" + "@ethersproject/abstract-signer" "5.7.0" + "@ethersproject/address" "5.7.0" + "@ethersproject/base64" "5.7.0" + "@ethersproject/basex" "5.7.0" + "@ethersproject/bignumber" "5.7.0" + "@ethersproject/bytes" "5.7.0" + "@ethersproject/constants" "5.7.0" + "@ethersproject/contracts" "5.7.0" + "@ethersproject/hash" "5.7.0" + "@ethersproject/hdnode" "5.7.0" + "@ethersproject/json-wallets" "5.7.0" + "@ethersproject/keccak256" "5.7.0" + "@ethersproject/logger" "5.7.0" + "@ethersproject/networks" "5.7.1" + "@ethersproject/pbkdf2" "5.7.0" + "@ethersproject/properties" "5.7.0" + "@ethersproject/providers" "5.7.2" + "@ethersproject/random" "5.7.0" + "@ethersproject/rlp" "5.7.0" + "@ethersproject/sha2" "5.7.0" + "@ethersproject/signing-key" "5.7.0" + "@ethersproject/solidity" "5.7.0" + "@ethersproject/strings" "5.7.0" + "@ethersproject/transactions" "5.7.0" + "@ethersproject/units" "5.7.0" + "@ethersproject/wallet" "5.7.0" + "@ethersproject/web" "5.7.1" + "@ethersproject/wordlists" "5.7.0" + +ethjs-util@0.1.6, ethjs-util@^0.1.6: + version "0.1.6" + resolved "https://registry.yarnpkg.com/ethjs-util/-/ethjs-util-0.1.6.tgz#f308b62f185f9fe6237132fb2a9818866a5cd536" + integrity sha512-CUnVOQq7gSpDHZVVrQW8ExxUETWrnrvXYvYz55wOU8Uj4VCgw56XC2B/fVqQN+f7gmrnRHSLVnFAwsCuNwji8w== + dependencies: + is-hex-prefixed "1.0.0" + strip-hex-prefix "1.0.0" + +evp_bytestokey@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/evp_bytestokey/-/evp_bytestokey-1.0.3.tgz#7fcbdb198dc71959432efe13842684e0525acb02" + integrity sha512-/f2Go4TognH/KvCISP7OUsHn85hT9nUkxxA9BEWxFn+Oj9o8ZNLm/40hdlgSLyuOimsrTKLUMEorQexp/aPQeA== + dependencies: + md5.js "^1.3.4" + safe-buffer "^5.1.1" + +fast-deep-equal@^3.1.1, fast-deep-equal@^3.1.3: + version "3.1.3" + resolved "https://registry.yarnpkg.com/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz#3a7d56b559d6cbc3eb512325244e619a65c6c525" + integrity sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q== + +fast-diff@^1.1.2: + version "1.3.0" + resolved "https://registry.yarnpkg.com/fast-diff/-/fast-diff-1.3.0.tgz#ece407fa550a64d638536cd727e129c61616e0f0" + integrity sha512-VxPP4NqbUjj6MaAOafWeUn2cXWLcCtljklUtZf0Ind4XQ+QPtmA0b18zZy0jIQx+ExRVCR/ZQpBmik5lXshNsw== + +fast-glob@^3.2.12, fast-glob@^3.2.9: + version "3.3.1" + resolved "https://registry.yarnpkg.com/fast-glob/-/fast-glob-3.3.1.tgz#784b4e897340f3dbbef17413b3f11acf03c874c4" + integrity sha512-kNFPyjhh5cKjrUltxs+wFx+ZkbRaxxmZ+X0ZU31SOsxCEtP9VPgtq2teZw1DebupL5GmDaNQ6yKMMVcM41iqDg== + dependencies: + "@nodelib/fs.stat" "^2.0.2" + "@nodelib/fs.walk" "^1.2.3" + glob-parent "^5.1.2" + merge2 "^1.3.0" + micromatch "^4.0.4" + +fast-json-stable-stringify@^2.0.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz#874bf69c6f404c2b5d99c481341399fd55892633" + integrity sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw== + +fast-levenshtein@^2.0.6: + version "2.0.6" + resolved "https://registry.yarnpkg.com/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz#3d8a5c66883a16a30ca8643e851f19baa7797917" + integrity sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw== + +fastq@^1.6.0: + version "1.15.0" + resolved "https://registry.yarnpkg.com/fastq/-/fastq-1.15.0.tgz#d04d07c6a2a68fe4599fea8d2e103a937fae6b3a" + integrity sha512-wBrocU2LCXXa+lWBt8RoIRD89Fi8OdABODa/kEnyeyjS5aZO5/GNvI5sEINADqP/h8M29UHTHUb53sUu5Ihqdw== + dependencies: + reusify "^1.0.4" + +file-entry-cache@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/file-entry-cache/-/file-entry-cache-6.0.1.tgz#211b2dd9659cb0394b073e7323ac3c933d522027" + integrity sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg== + dependencies: + flat-cache "^3.0.4" + +fill-range@^7.0.1: + version "7.0.1" + resolved "https://registry.yarnpkg.com/fill-range/-/fill-range-7.0.1.tgz#1919a6a7c75fe38b2c7c77e5198535da9acdda40" + integrity sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ== + dependencies: + to-regex-range "^5.0.1" + +find-up@5.0.0, find-up@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-5.0.0.tgz#4c92819ecb7083561e4f4a240a86be5198f536fc" + integrity sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng== + dependencies: + locate-path "^6.0.0" + path-exists "^4.0.0" + +find-up@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-2.1.0.tgz#45d1b7e506c717ddd482775a2b77920a3c0c57a7" + integrity sha512-NWzkk0jSJtTt08+FBFMvXoeZnOJD+jTtsRmBYbAIzJdX6l7dLgR7CTubCM5/eDdPUBvLCeVasP1brfVR/9/EZQ== + dependencies: + locate-path "^2.0.0" + +flat-cache@^3.0.4: + version "3.1.1" + resolved "https://registry.yarnpkg.com/flat-cache/-/flat-cache-3.1.1.tgz#a02a15fdec25a8f844ff7cc658f03dd99eb4609b" + integrity sha512-/qM2b3LUIaIgviBQovTLvijfyOQXPtSRnRK26ksj2J7rzPIecePUIpJsZ4T02Qg+xiAEKIs5K8dsHEd+VaKa/Q== + dependencies: + flatted "^3.2.9" + keyv "^4.5.3" + rimraf "^3.0.2" + +flat@^5.0.2: + version "5.0.2" + resolved "https://registry.yarnpkg.com/flat/-/flat-5.0.2.tgz#8ca6fe332069ffa9d324c327198c598259ceb241" + integrity sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ== + +flatted@^3.2.9: + version "3.2.9" + resolved "https://registry.yarnpkg.com/flatted/-/flatted-3.2.9.tgz#7eb4c67ca1ba34232ca9d2d93e9886e611ad7daf" + integrity sha512-36yxDn5H7OFZQla0/jFJmbIKTdZAQHngCedGxiMmpNfEZM0sdEeT+WczLQrjK6D7o2aiyLYDnkw0R3JK0Qv1RQ== + +follow-redirects@^1.12.1: + version "1.15.3" + resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.15.3.tgz#fe2f3ef2690afce7e82ed0b44db08165b207123a" + integrity sha512-1VzOtuEM8pC9SFU1E+8KfTjZyMztRsgEfwQl44z8A25uy13jSzTj6dyK2Df52iV0vgHCfBwLhDWevLn95w5v6Q== + +for-each@^0.3.3: + version "0.3.3" + resolved "https://registry.yarnpkg.com/for-each/-/for-each-0.3.3.tgz#69b447e88a0a5d32c3e7084f3f1710034b21376e" + integrity sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw== + dependencies: + is-callable "^1.1.3" + +fp-ts@1.19.3: + version "1.19.3" + resolved "https://registry.yarnpkg.com/fp-ts/-/fp-ts-1.19.3.tgz#261a60d1088fbff01f91256f91d21d0caaaaa96f" + integrity sha512-H5KQDspykdHuztLTg+ajGN0Z2qUjcEf3Ybxc6hLt0k7/zPkn29XnKnxlBPyW2XIddWrGaJBzBl4VLYOtk39yZg== + +fp-ts@^1.0.0: + version "1.19.5" + resolved "https://registry.yarnpkg.com/fp-ts/-/fp-ts-1.19.5.tgz#3da865e585dfa1fdfd51785417357ac50afc520a" + integrity sha512-wDNqTimnzs8QqpldiId9OavWK2NptormjXnRJTQecNjzwfyp6P/8s/zG8e4h3ja3oqkKaY72UlTjQYt/1yXf9A== + +fs-constants@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/fs-constants/-/fs-constants-1.0.0.tgz#6be0de9be998ce16af8afc24497b9ee9b7ccd9ad" + integrity sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow== + +fs-extra@^0.30.0: + version "0.30.0" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-0.30.0.tgz#f233ffcc08d4da7d432daa449776989db1df93f0" + integrity sha512-UvSPKyhMn6LEd/WpUaV9C9t3zATuqoqfWc3QdPhPLb58prN9tqYPlPWi8Krxi44loBoUzlobqZ3+8tGpxxSzwA== + dependencies: + graceful-fs "^4.1.2" + jsonfile "^2.1.0" + klaw "^1.0.0" + path-is-absolute "^1.0.0" + rimraf "^2.2.8" + +fs-extra@^11.1.1: + version "11.1.1" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-11.1.1.tgz#da69f7c39f3b002378b0954bb6ae7efdc0876e2d" + integrity sha512-MGIE4HOvQCeUCzmlHs0vXpih4ysz4wg9qiSAu6cd42lVwPbTM1TjV7RusoyQqMmk/95gdQZX72u+YW+c3eEpFQ== + dependencies: + graceful-fs "^4.2.0" + jsonfile "^6.0.1" + universalify "^2.0.0" + +fs-extra@^7.0.1: + version "7.0.1" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-7.0.1.tgz#4f189c44aa123b895f722804f55ea23eadc348e9" + integrity sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw== + dependencies: + graceful-fs "^4.1.2" + jsonfile "^4.0.0" + universalify "^0.1.0" + +fs.realpath@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f" + integrity sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw== + +fsevents@~2.3.2: + version "2.3.3" + resolved "https://registry.yarnpkg.com/fsevents/-/fsevents-2.3.3.tgz#cac6407785d03675a2a5e1a5305c697b347d90d6" + integrity sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw== + +function-bind@^1.1.1: + version "1.1.2" + resolved "https://registry.yarnpkg.com/function-bind/-/function-bind-1.1.2.tgz#2c02d864d97f3ea6c8830c464cbd11ab6eab7a1c" + integrity sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA== + +function.prototype.name@^1.1.6: + version "1.1.6" + resolved "https://registry.yarnpkg.com/function.prototype.name/-/function.prototype.name-1.1.6.tgz#cdf315b7d90ee77a4c6ee216c3c3362da07533fd" + integrity sha512-Z5kx79swU5P27WEayXM1tBi5Ze/lbIyiNgU3qyXUOf9b2rgXYyF9Dy9Cx+IQv/Lc8WCG6L82zwUPpSS9hGehIg== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + functions-have-names "^1.2.3" + +functional-red-black-tree@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz#1b0ab3bd553b2a0d6399d29c0e3ea0b252078327" + integrity sha512-dsKNQNdj6xA3T+QlADDA7mOSlX0qiMINjn0cgr+eGHGsbSHzTabcIogz2+p/iqP1Xs6EP/sS2SbqH+brGTbq0g== + +functions-have-names@^1.2.3: + version "1.2.3" + resolved "https://registry.yarnpkg.com/functions-have-names/-/functions-have-names-1.2.3.tgz#0404fe4ee2ba2f607f0e0ec3c80bae994133b834" + integrity sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ== + +get-caller-file@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/get-caller-file/-/get-caller-file-2.0.5.tgz#4f94412a82db32f36e3b0b9741f8a97feb031f7e" + integrity sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg== + +get-func-name@^2.0.0, get-func-name@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/get-func-name/-/get-func-name-2.0.2.tgz#0d7cf20cd13fda808669ffa88f4ffc7a3943fc41" + integrity sha512-8vXOvuE167CtIc3OyItco7N/dpRtBbYOsPsXCz7X/PMnlGjYjSGuZJgM1Y7mmew7BKf9BqvLX2tnOVy1BBUsxQ== + +get-intrinsic@^1.0.2, get-intrinsic@^1.1.1, get-intrinsic@^1.1.3, get-intrinsic@^1.2.0, get-intrinsic@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/get-intrinsic/-/get-intrinsic-1.2.1.tgz#d295644fed4505fc9cde952c37ee12b477a83d82" + integrity sha512-2DcsyfABl+gVHEfCOaTrWgyt+tb6MSEGmKq+kI5HwLbIYgjgmMcV8KQ41uaKz1xxUcn9tJtgFbQUEVcEbd0FYw== + dependencies: + function-bind "^1.1.1" + has "^1.0.3" + has-proto "^1.0.1" + has-symbols "^1.0.3" + +get-symbol-description@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/get-symbol-description/-/get-symbol-description-1.0.0.tgz#7fdb81c900101fbd564dd5f1a30af5aadc1e58d6" + integrity sha512-2EmdH1YvIQiZpltCNgkuiUnyukzxM/R6NDJX31Ke3BG1Nq5b0S2PhX59UKi9vZpPDQVdqn+1IcaAwnzTT5vCjw== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.1.1" + +glob-parent@^5.1.2, glob-parent@~5.1.2: + version "5.1.2" + resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-5.1.2.tgz#869832c58034fe68a4093c17dc15e8340d8401c4" + integrity sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow== + dependencies: + is-glob "^4.0.1" + +glob-parent@^6.0.2: + version "6.0.2" + resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-6.0.2.tgz#6d237d99083950c79290f24c7642a3de9a28f9e3" + integrity sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A== + dependencies: + is-glob "^4.0.3" + +glob@7.2.0: + version "7.2.0" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.0.tgz#d15535af7732e02e948f4c41628bd910293f6023" + integrity sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.0.4" + once "^1.3.0" + path-is-absolute "^1.0.0" + +glob@^7.1.3: + version "7.2.3" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.3.tgz#b8df0fb802bbfa8e89bd1d938b4e16578ed44f2b" + integrity sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.1.1" + once "^1.3.0" + path-is-absolute "^1.0.0" + +globals@^13.19.0: + version "13.23.0" + resolved "https://registry.yarnpkg.com/globals/-/globals-13.23.0.tgz#ef31673c926a0976e1f61dab4dca57e0c0a8af02" + integrity sha512-XAmF0RjlrjY23MA51q3HltdlGxUpXPvg0GioKiD9X6HD28iMjo2dKC8Vqwm7lne4GNr78+RHTfliktR6ZH09wA== + dependencies: + type-fest "^0.20.2" + +globalthis@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/globalthis/-/globalthis-1.0.3.tgz#5852882a52b80dc301b0660273e1ed082f0b6ccf" + integrity sha512-sFdI5LyBiNTHjRd7cGPWapiHWMOXKyuBNX/cWJ3NfzrZQVa8GI/8cofCl74AOVqq9W5kNmguTIzJ/1s2gyI9wA== + dependencies: + define-properties "^1.1.3" + +globby@^11.1.0: + version "11.1.0" + resolved "https://registry.yarnpkg.com/globby/-/globby-11.1.0.tgz#bd4be98bb042f83d796f7e3811991fbe82a0d34b" + integrity sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g== + dependencies: + array-union "^2.1.0" + dir-glob "^3.0.1" + fast-glob "^3.2.9" + ignore "^5.2.0" + merge2 "^1.4.1" + slash "^3.0.0" + +gopd@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/gopd/-/gopd-1.0.1.tgz#29ff76de69dac7489b7c0918a5788e56477c332c" + integrity sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA== + dependencies: + get-intrinsic "^1.1.3" + +graceful-fs@^4.1.2, graceful-fs@^4.1.6, graceful-fs@^4.1.9, graceful-fs@^4.2.0, graceful-fs@^4.2.4: + version "4.2.11" + resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.11.tgz#4183e4e8bf08bb6e05bbb2f7d2e0c8f712ca40e3" + integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ== + +graphemer@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/graphemer/-/graphemer-1.4.0.tgz#fb2f1d55e0e3a1849aeffc90c4fa0dd53a0e66c6" + integrity sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag== + +hardhat@^2.12.4: + version "2.18.1" + resolved "https://registry.yarnpkg.com/hardhat/-/hardhat-2.18.1.tgz#6339d656dbf0510b51457b0f0746e5b9cc7a1756" + integrity sha512-b55rW7Ka+fvJeg6oWuBTXoYQEUurevCCankjGNTwczwD3GnkhV9GEei7KUT+9IKmWx3lC+zyxlFxeDbg0gUoHw== + dependencies: + "@ethersproject/abi" "^5.1.2" + "@metamask/eth-sig-util" "^4.0.0" + "@nomicfoundation/ethereumjs-block" "5.0.2" + "@nomicfoundation/ethereumjs-blockchain" "7.0.2" + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-evm" "2.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-statemanager" "2.0.2" + "@nomicfoundation/ethereumjs-trie" "6.0.2" + "@nomicfoundation/ethereumjs-tx" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + "@nomicfoundation/ethereumjs-vm" "7.0.2" + "@nomicfoundation/solidity-analyzer" "^0.1.0" + "@sentry/node" "^5.18.1" + "@types/bn.js" "^5.1.0" + "@types/lru-cache" "^5.1.0" + adm-zip "^0.4.16" + aggregate-error "^3.0.0" + ansi-escapes "^4.3.0" + chalk "^2.4.2" + chokidar "^3.4.0" + ci-info "^2.0.0" + debug "^4.1.1" + enquirer "^2.3.0" + env-paths "^2.2.0" + ethereum-cryptography "^1.0.3" + ethereumjs-abi "^0.6.8" + find-up "^2.1.0" + fp-ts "1.19.3" + fs-extra "^7.0.1" + glob "7.2.0" + immutable "^4.0.0-rc.12" + io-ts "1.10.4" + keccak "^3.0.2" + lodash "^4.17.11" + mnemonist "^0.38.0" + mocha "^10.0.0" + p-map "^4.0.0" + raw-body "^2.4.1" + resolve "1.17.0" + semver "^6.3.0" + solc "0.7.3" + source-map-support "^0.5.13" + stacktrace-parser "^0.1.10" + tsort "0.0.1" + undici "^5.14.0" + uuid "^8.3.2" + ws "^7.4.6" + +has-bigints@^1.0.1, has-bigints@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/has-bigints/-/has-bigints-1.0.2.tgz#0871bd3e3d51626f6ca0966668ba35d5602d6eaa" + integrity sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ== + +has-flag@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd" + integrity sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw== + +has-flag@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-4.0.0.tgz#944771fd9c81c81265c4d6941860da06bb59479b" + integrity sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ== + +has-property-descriptors@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/has-property-descriptors/-/has-property-descriptors-1.0.0.tgz#610708600606d36961ed04c196193b6a607fa861" + integrity sha512-62DVLZGoiEBDHQyqG4w9xCuZ7eJEwNmJRWw2VY84Oedb7WFcA27fiEVe8oUQx9hAUJ4ekurquucTGwsyO1XGdQ== + dependencies: + get-intrinsic "^1.1.1" + +has-proto@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/has-proto/-/has-proto-1.0.1.tgz#1885c1305538958aff469fef37937c22795408e0" + integrity sha512-7qE+iP+O+bgF9clE5+UoBFzE65mlBiVj3tKCrlNQ0Ogwm0BjpT/gK4SlLYDMybDh5I3TCTKnPPa0oMG7JDYrhg== + +has-symbols@^1.0.2, has-symbols@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/has-symbols/-/has-symbols-1.0.3.tgz#bb7b2c4349251dce87b125f7bdf874aa7c8b39f8" + integrity sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A== + +has-tostringtag@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/has-tostringtag/-/has-tostringtag-1.0.0.tgz#7e133818a7d394734f941e73c3d3f9291e658b25" + integrity sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ== + dependencies: + has-symbols "^1.0.2" + +has@^1.0.3: + version "1.0.4" + resolved "https://registry.yarnpkg.com/has/-/has-1.0.4.tgz#2eb2860e000011dae4f1406a86fe80e530fb2ec6" + integrity sha512-qdSAmqLF6209RFj4VVItywPMbm3vWylknmB3nvNiUIs72xAimcM8nVYxYr7ncvZq5qzk9MKIZR8ijqD/1QuYjQ== + +hash-base@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/hash-base/-/hash-base-3.1.0.tgz#55c381d9e06e1d2997a883b4a3fddfe7f0d3af33" + integrity sha512-1nmYp/rhMDiE7AYkDw+lLwlAzz0AntGIe51F3RfFfEqyQ3feY2eI/NcwC6umIQVOASPMsWJLJScWKSSvzL9IVA== + dependencies: + inherits "^2.0.4" + readable-stream "^3.6.0" + safe-buffer "^5.2.0" + +hash.js@1.1.7, hash.js@^1.0.0, hash.js@^1.0.3, hash.js@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/hash.js/-/hash.js-1.1.7.tgz#0babca538e8d4ee4a0f8988d68866537a003cf42" + integrity sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA== + dependencies: + inherits "^2.0.3" + minimalistic-assert "^1.0.1" + +he@1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/he/-/he-1.2.0.tgz#84ae65fa7eafb165fddb61566ae14baf05664f0f" + integrity sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw== + +hmac-drbg@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/hmac-drbg/-/hmac-drbg-1.0.1.tgz#d2745701025a6c775a6c545793ed502fc0c649a1" + integrity sha512-Tti3gMqLdZfhOQY1Mzf/AanLiqh1WTiJgEj26ZuYQ9fbkLomzGchCws4FyrSd4VkpBfiNhaE1On+lOz894jvXg== + dependencies: + hash.js "^1.0.3" + minimalistic-assert "^1.0.0" + minimalistic-crypto-utils "^1.0.1" + +http-errors@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/http-errors/-/http-errors-2.0.0.tgz#b7774a1486ef73cf7667ac9ae0858c012c57b9d3" + integrity sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ== + dependencies: + depd "2.0.0" + inherits "2.0.4" + setprototypeof "1.2.0" + statuses "2.0.1" + toidentifier "1.0.1" + +https-proxy-agent@^5.0.0: + version "5.0.1" + resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz#c59ef224a04fe8b754f3db0063a25ea30d0005d6" + integrity sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA== + dependencies: + agent-base "6" + debug "4" + +iconv-lite@0.4.24: + version "0.4.24" + resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b" + integrity sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA== + dependencies: + safer-buffer ">= 2.1.2 < 3" + +ieee754@^1.1.13, ieee754@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/ieee754/-/ieee754-1.2.1.tgz#8eb7a10a63fff25d15a57b001586d177d1b0d352" + integrity sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA== + +ignore@^5.2.0, ignore@^5.2.4: + version "5.2.4" + resolved "https://registry.yarnpkg.com/ignore/-/ignore-5.2.4.tgz#a291c0c6178ff1b960befe47fcdec301674a6324" + integrity sha512-MAb38BcSbH0eHNBxn7ql2NH/kX33OkB3lZ1BNdh7ENeRChHTYsTvWrMubiIAMNS2llXEEgZ1MUOBtXChP3kaFQ== + +immutable@^4.0.0-rc.12: + version "4.3.4" + resolved "https://registry.yarnpkg.com/immutable/-/immutable-4.3.4.tgz#2e07b33837b4bb7662f288c244d1ced1ef65a78f" + integrity sha512-fsXeu4J4i6WNWSikpI88v/PcVflZz+6kMhUfIwc5SY+poQRPnaf5V7qds6SUyUN3cVxEzuCab7QIoLOQ+DQ1wA== + +import-fresh@^3.2.1: + version "3.3.0" + resolved "https://registry.yarnpkg.com/import-fresh/-/import-fresh-3.3.0.tgz#37162c25fcb9ebaa2e6e53d5b4d88ce17d9e0c2b" + integrity sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw== + dependencies: + parent-module "^1.0.0" + resolve-from "^4.0.0" + +imurmurhash@^0.1.4: + version "0.1.4" + resolved "https://registry.yarnpkg.com/imurmurhash/-/imurmurhash-0.1.4.tgz#9218b9b2b928a238b13dc4fb6b6d576f231453ea" + integrity sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA== + +indent-string@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/indent-string/-/indent-string-4.0.0.tgz#624f8f4497d619b2d9768531d58f4122854d7251" + integrity sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg== + +inflight@^1.0.4: + version "1.0.6" + resolved "https://registry.yarnpkg.com/inflight/-/inflight-1.0.6.tgz#49bd6331d7d02d0c09bc910a1075ba8165b56df9" + integrity sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA== + dependencies: + once "^1.3.0" + wrappy "1" + +inherits@2, inherits@2.0.4, inherits@^2.0.1, inherits@^2.0.3, inherits@^2.0.4, inherits@~2.0.1, inherits@~2.0.3: + version "2.0.4" + resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.4.tgz#0fa2c64f932917c3433a0ded55363aae37416b7c" + integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== + +internal-slot@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/internal-slot/-/internal-slot-1.0.5.tgz#f2a2ee21f668f8627a4667f309dc0f4fb6674986" + integrity sha512-Y+R5hJrzs52QCG2laLn4udYVnxsfny9CpOhNhUvk/SSSVyF6T27FzRbF0sroPidSu3X8oEAkOn2K804mjpt6UQ== + dependencies: + get-intrinsic "^1.2.0" + has "^1.0.3" + side-channel "^1.0.4" + +io-ts@1.10.4: + version "1.10.4" + resolved "https://registry.yarnpkg.com/io-ts/-/io-ts-1.10.4.tgz#cd5401b138de88e4f920adbcb7026e2d1967e6e2" + integrity sha512-b23PteSnYXSONJ6JQXRAlvJhuw8KOtkqa87W4wDtvMrud/DTJd5X+NpOOI+O/zZwVq6v0VLAaJ+1EDViKEuN9g== + dependencies: + fp-ts "^1.0.0" + +is-array-buffer@^3.0.1, is-array-buffer@^3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/is-array-buffer/-/is-array-buffer-3.0.2.tgz#f2653ced8412081638ecb0ebbd0c41c6e0aecbbe" + integrity sha512-y+FyyR/w8vfIRq4eQcM1EYgSTnmHXPqaF+IgzgraytCFq5Xh8lllDVmAZolPJiZttZLeFSINPYMaEJ7/vWUa1w== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.2.0" + is-typed-array "^1.1.10" + +is-bigint@^1.0.1: + version "1.0.4" + resolved "https://registry.yarnpkg.com/is-bigint/-/is-bigint-1.0.4.tgz#08147a1875bc2b32005d41ccd8291dffc6691df3" + integrity sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg== + dependencies: + has-bigints "^1.0.1" + +is-binary-path@~2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-2.1.0.tgz#ea1f7f3b80f064236e83470f86c09c254fb45b09" + integrity sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw== + dependencies: + binary-extensions "^2.0.0" + +is-boolean-object@^1.1.0: + version "1.1.2" + resolved "https://registry.yarnpkg.com/is-boolean-object/-/is-boolean-object-1.1.2.tgz#5c6dc200246dd9321ae4b885a114bb1f75f63719" + integrity sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA== + dependencies: + call-bind "^1.0.2" + has-tostringtag "^1.0.0" + +is-buffer@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/is-buffer/-/is-buffer-2.0.5.tgz#ebc252e400d22ff8d77fa09888821a24a658c191" + integrity sha512-i2R6zNFDwgEHJyQUtJEk0XFi1i0dPFn/oqjK3/vPCcDeJvW5NQ83V8QbicfF1SupOaB0h8ntgBC2YiE7dfyctQ== + +is-callable@^1.1.3, is-callable@^1.1.4, is-callable@^1.2.7: + version "1.2.7" + resolved "https://registry.yarnpkg.com/is-callable/-/is-callable-1.2.7.tgz#3bc2a85ea742d9e36205dcacdd72ca1fdc51b055" + integrity sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA== + +is-core-module@^2.13.0: + version "2.13.0" + resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.13.0.tgz#bb52aa6e2cbd49a30c2ba68c42bf3435ba6072db" + integrity sha512-Z7dk6Qo8pOCp3l4tsX2C5ZVas4V+UxwQodwZhLopL91TX8UyyHEXafPcyoeeWuLrwzHcr3igO78wNLwHJHsMCQ== + dependencies: + has "^1.0.3" + +is-date-object@^1.0.1: + version "1.0.5" + resolved "https://registry.yarnpkg.com/is-date-object/-/is-date-object-1.0.5.tgz#0841d5536e724c25597bf6ea62e1bd38298df31f" + integrity sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ== + dependencies: + has-tostringtag "^1.0.0" + +is-extglob@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2" + integrity sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ== + +is-fullwidth-code-point@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz#f116f8064fe90b3f7844a38997c0b75051269f1d" + integrity sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg== + +is-glob@^4.0.0, is-glob@^4.0.1, is-glob@^4.0.3, is-glob@~4.0.1: + version "4.0.3" + resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-4.0.3.tgz#64f61e42cbbb2eec2071a9dac0b28ba1e65d5084" + integrity sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg== + dependencies: + is-extglob "^2.1.1" + +is-hex-prefixed@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz#7d8d37e6ad77e5d127148913c573e082d777f554" + integrity sha512-WvtOiug1VFrE9v1Cydwm+FnXd3+w9GaeVUss5W4v/SLy3UW00vP+6iNF2SdnfiBoLy4bTqVdkftNGTUeOFVsbA== + +is-negative-zero@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/is-negative-zero/-/is-negative-zero-2.0.2.tgz#7bf6f03a28003b8b3965de3ac26f664d765f3150" + integrity sha512-dqJvarLawXsFbNDeJW7zAz8ItJ9cd28YufuuFzh0G8pNHjJMnY08Dv7sYX2uF5UpQOwieAeOExEYAWWfu7ZZUA== + +is-number-object@^1.0.4: + version "1.0.7" + resolved "https://registry.yarnpkg.com/is-number-object/-/is-number-object-1.0.7.tgz#59d50ada4c45251784e9904f5246c742f07a42fc" + integrity sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ== + dependencies: + has-tostringtag "^1.0.0" + +is-number@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/is-number/-/is-number-7.0.0.tgz#7535345b896734d5f80c4d06c50955527a14f12b" + integrity sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng== + +is-path-inside@^3.0.3: + version "3.0.3" + resolved "https://registry.yarnpkg.com/is-path-inside/-/is-path-inside-3.0.3.tgz#d231362e53a07ff2b0e0ea7fed049161ffd16283" + integrity sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ== + +is-plain-obj@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/is-plain-obj/-/is-plain-obj-2.1.0.tgz#45e42e37fccf1f40da8e5f76ee21515840c09287" + integrity sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA== + +is-regex@^1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/is-regex/-/is-regex-1.1.4.tgz#eef5663cd59fa4c0ae339505323df6854bb15958" + integrity sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg== + dependencies: + call-bind "^1.0.2" + has-tostringtag "^1.0.0" + +is-shared-array-buffer@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/is-shared-array-buffer/-/is-shared-array-buffer-1.0.2.tgz#8f259c573b60b6a32d4058a1a07430c0a7344c79" + integrity sha512-sqN2UDu1/0y6uvXyStCOzyhAjCSlHceFoMKJW8W9EU9cvic/QdsZ0kEU93HEy3IUEFZIiH/3w+AH/UQbPHNdhA== + dependencies: + call-bind "^1.0.2" + +is-string@^1.0.4, is-string@^1.0.5, is-string@^1.0.7: + version "1.0.7" + resolved "https://registry.yarnpkg.com/is-string/-/is-string-1.0.7.tgz#0dd12bf2006f255bb58f695110eff7491eebc0fd" + integrity sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg== + dependencies: + has-tostringtag "^1.0.0" + +is-symbol@^1.0.2, is-symbol@^1.0.3: + version "1.0.4" + resolved "https://registry.yarnpkg.com/is-symbol/-/is-symbol-1.0.4.tgz#a6dac93b635b063ca6872236de88910a57af139c" + integrity sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg== + dependencies: + has-symbols "^1.0.2" + +is-typed-array@^1.1.10, is-typed-array@^1.1.12, is-typed-array@^1.1.9: + version "1.1.12" + resolved "https://registry.yarnpkg.com/is-typed-array/-/is-typed-array-1.1.12.tgz#d0bab5686ef4a76f7a73097b95470ab199c57d4a" + integrity sha512-Z14TF2JNG8Lss5/HMqt0//T9JeHXttXy5pH/DBU4vi98ozO2btxzq9MwYDZYnKwU8nRsz/+GVFVRDq3DkVuSPg== + dependencies: + which-typed-array "^1.1.11" + +is-unicode-supported@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz#3f26c76a809593b52bfa2ecb5710ed2779b522a7" + integrity sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw== + +is-weakref@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/is-weakref/-/is-weakref-1.0.2.tgz#9529f383a9338205e89765e0392efc2f100f06f2" + integrity sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ== + dependencies: + call-bind "^1.0.2" + +isarray@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/isarray/-/isarray-0.0.1.tgz#8a18acfca9a8f4177e09abfc6038939b05d1eedf" + integrity sha512-D2S+3GLxWH+uhrNEcoh/fnmYeP8E8/zHl644d/jdA0g2uyXvy3sb0qxotE+ne0LtccHknQzWwZEzhak7oJ0COQ== + +isarray@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/isarray/-/isarray-2.0.5.tgz#8af1e4c1221244cc62459faf38940d4e644a5723" + integrity sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw== + +isarray@~1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11" + integrity sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ== + +isexe@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/isexe/-/isexe-2.0.0.tgz#e8fbf374dc556ff8947a10dcb0572d633f2cfa10" + integrity sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw== + +js-sdsl@^4.1.4: + version "4.4.2" + resolved "https://registry.yarnpkg.com/js-sdsl/-/js-sdsl-4.4.2.tgz#2e3c031b1f47d3aca8b775532e3ebb0818e7f847" + integrity sha512-dwXFwByc/ajSV6m5bcKAPwe4yDDF6D614pxmIi5odytzxRlwqF6nwoiCek80Ixc7Cvma5awClxrzFtxCQvcM8w== + +js-sha3@0.8.0: + version "0.8.0" + resolved "https://registry.yarnpkg.com/js-sha3/-/js-sha3-0.8.0.tgz#b9b7a5da73afad7dedd0f8c463954cbde6818840" + integrity sha512-gF1cRrHhIzNfToc802P800N8PpXS+evLLXfsVpowqmAFR9uwbi89WvXg2QspOmXL8QL86J4T1EpFu+yUkwJY3Q== + +js-yaml@4.1.0, js-yaml@^4.1.0: + version "4.1.0" + resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-4.1.0.tgz#c1fb65f8f5017901cdd2c951864ba18458a10602" + integrity sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA== + dependencies: + argparse "^2.0.1" + +json-buffer@3.0.1: + version "3.0.1" + resolved "https://registry.yarnpkg.com/json-buffer/-/json-buffer-3.0.1.tgz#9338802a30d3b6605fbe0613e094008ca8c05a13" + integrity sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ== + +json-schema-traverse@^0.4.1: + version "0.4.1" + resolved "https://registry.yarnpkg.com/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz#69f6a87d9513ab8bb8fe63bdb0979c448e684660" + integrity sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg== + +json-stable-stringify-without-jsonify@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz#9db7b59496ad3f3cfef30a75142d2d930ad72651" + integrity sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw== + +json5@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/json5/-/json5-1.0.2.tgz#63d98d60f21b313b77c4d6da18bfa69d80e1d593" + integrity sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA== + dependencies: + minimist "^1.2.0" + +jsonfile@^2.1.0: + version "2.4.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-2.4.0.tgz#3736a2b428b87bbda0cc83b53fa3d633a35c2ae8" + integrity sha512-PKllAqbgLgxHaj8TElYymKCAgrASebJrWpTnEkOaTowt23VKXXN0sUeriJ+eh7y6ufb/CC5ap11pz71/cM0hUw== + optionalDependencies: + graceful-fs "^4.1.6" + +jsonfile@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-4.0.0.tgz#8771aae0799b64076b76640fca058f9c10e33ecb" + integrity sha512-m6F1R3z8jjlf2imQHS2Qez5sjKWQzbuuhuJ/FKYFRZvPE3PuHcSMVZzfsLhGVOkfd20obL5SWEBew5ShlquNxg== + optionalDependencies: + graceful-fs "^4.1.6" + +jsonfile@^6.0.1: + version "6.1.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-6.1.0.tgz#bc55b2634793c679ec6403094eb13698a6ec0aae" + integrity sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ== + dependencies: + universalify "^2.0.0" + optionalDependencies: + graceful-fs "^4.1.6" + +jsonparse@^1.2.0: + version "1.3.1" + resolved "https://registry.yarnpkg.com/jsonparse/-/jsonparse-1.3.1.tgz#3f4dae4a91fac315f71062f8521cc239f1366280" + integrity sha512-POQXvpdL69+CluYsillJ7SUhKvytYjW9vG/GKpnf+xP8UWgYEM/RaMzHHofbALDiKbbP1W8UEYmgGl39WkPZsg== + +keccak@^3.0.0, keccak@^3.0.2: + version "3.0.4" + resolved "https://registry.yarnpkg.com/keccak/-/keccak-3.0.4.tgz#edc09b89e633c0549da444432ecf062ffadee86d" + integrity sha512-3vKuW0jV8J3XNTzvfyicFR5qvxrSAGl7KIhvgOu5cmWwM7tZRj3fMbj/pfIf4be7aznbc+prBWGjywox/g2Y6Q== + dependencies: + node-addon-api "^2.0.0" + node-gyp-build "^4.2.0" + readable-stream "^3.6.0" + +keyv@^4.5.3: + version "4.5.4" + resolved "https://registry.yarnpkg.com/keyv/-/keyv-4.5.4.tgz#a879a99e29452f942439f2a405e3af8b31d4de93" + integrity sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw== + dependencies: + json-buffer "3.0.1" + +klaw@^1.0.0: + version "1.3.1" + resolved "https://registry.yarnpkg.com/klaw/-/klaw-1.3.1.tgz#4088433b46b3b1ba259d78785d8e96f73ba02439" + integrity sha512-TED5xi9gGQjGpNnvRWknrwAB1eL5GciPfVFOt3Vk1OJCVDQbzuSfrF3hkUQKlsgKrG1F+0t5W0m+Fje1jIt8rw== + optionalDependencies: + graceful-fs "^4.1.9" + +level-supports@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/level-supports/-/level-supports-4.0.1.tgz#431546f9d81f10ff0fea0e74533a0e875c08c66a" + integrity sha512-PbXpve8rKeNcZ9C1mUicC9auIYFyGpkV9/i6g76tLgANwWhtG2v7I4xNBUlkn3lE2/dZF3Pi0ygYGtLc4RXXdA== + +level-transcoder@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/level-transcoder/-/level-transcoder-1.0.1.tgz#f8cef5990c4f1283d4c86d949e73631b0bc8ba9c" + integrity sha512-t7bFwFtsQeD8cl8NIoQ2iwxA0CL/9IFw7/9gAjOonH0PWTTiRfY7Hq+Ejbsxh86tXobDQ6IOiddjNYIfOBs06w== + dependencies: + buffer "^6.0.3" + module-error "^1.0.1" + +level@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/level/-/level-8.0.0.tgz#41b4c515dabe28212a3e881b61c161ffead14394" + integrity sha512-ypf0jjAk2BWI33yzEaaotpq7fkOPALKAgDBxggO6Q9HGX2MRXn0wbP1Jn/tJv1gtL867+YOjOB49WaUF3UoJNQ== + dependencies: + browser-level "^1.0.1" + classic-level "^1.2.0" + +levn@^0.4.1: + version "0.4.1" + resolved "https://registry.yarnpkg.com/levn/-/levn-0.4.1.tgz#ae4562c007473b932a6200d403268dd2fffc6ade" + integrity sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ== + dependencies: + prelude-ls "^1.2.1" + type-check "~0.4.0" + +locate-path@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-2.0.0.tgz#2b568b265eec944c6d9c0de9c3dbbbca0354cd8e" + integrity sha512-NCI2kiDkyR7VeEKm27Kda/iQHyKJe1Bu0FlTbYp3CqJu+9IFe9bLyAjMxf5ZDDbEg+iMPzB5zYyUTSm8wVTKmA== + dependencies: + p-locate "^2.0.0" + path-exists "^3.0.0" + +locate-path@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-6.0.0.tgz#55321eb309febbc59c4801d931a72452a681d286" + integrity sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw== + dependencies: + p-locate "^5.0.0" + +lodash.merge@^4.6.2: + version "4.6.2" + resolved "https://registry.yarnpkg.com/lodash.merge/-/lodash.merge-4.6.2.tgz#558aa53b43b661e1925a0afdfa36a9a1085fe57a" + integrity sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ== + +lodash.once@^4.1.1: + version "4.1.1" + resolved "https://registry.yarnpkg.com/lodash.once/-/lodash.once-4.1.1.tgz#0dd3971213c7c56df880977d504c88fb471a97ac" + integrity sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg== + +lodash@^4.17.11, lodash@^4.17.21: + version "4.17.21" + resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.21.tgz#679591c564c3bffaae8454cf0b3df370c3d6911c" + integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg== + +log-symbols@4.1.0: + version "4.1.0" + resolved "https://registry.yarnpkg.com/log-symbols/-/log-symbols-4.1.0.tgz#3fbdbb95b4683ac9fc785111e792e558d4abd503" + integrity sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg== + dependencies: + chalk "^4.1.0" + is-unicode-supported "^0.1.0" + +loupe@^2.3.6: + version "2.3.6" + resolved "https://registry.yarnpkg.com/loupe/-/loupe-2.3.6.tgz#76e4af498103c532d1ecc9be102036a21f787b53" + integrity sha512-RaPMZKiMy8/JruncMU5Bt6na1eftNoo++R4Y+N2FrxkDVTrGvcyzFTsaGif4QTeKESheMGegbhw6iUAq+5A8zA== + dependencies: + get-func-name "^2.0.0" + +lru-cache@^5.1.1: + version "5.1.1" + resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-5.1.1.tgz#1da27e6710271947695daf6848e847f01d84b920" + integrity sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w== + dependencies: + yallist "^3.0.2" + +lru-cache@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-6.0.0.tgz#6d6fe6570ebd96aaf90fcad1dafa3b2566db3a94" + integrity sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA== + dependencies: + yallist "^4.0.0" + +lru_map@^0.3.3: + version "0.3.3" + resolved "https://registry.yarnpkg.com/lru_map/-/lru_map-0.3.3.tgz#b5c8351b9464cbd750335a79650a0ec0e56118dd" + integrity sha512-Pn9cox5CsMYngeDbmChANltQl+5pi6XmTrraMSzhPmMBbmgcxmqWry0U3PGapCU1yB4/LqCcom7qhHZiF/jGfQ== + +make-error@^1.1.1: + version "1.3.6" + resolved "https://registry.yarnpkg.com/make-error/-/make-error-1.3.6.tgz#2eb2e37ea9b67c4891f684a1394799af484cf7a2" + integrity sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw== + +mcl-wasm@^0.7.1: + version "0.7.9" + resolved "https://registry.yarnpkg.com/mcl-wasm/-/mcl-wasm-0.7.9.tgz#c1588ce90042a8700c3b60e40efb339fc07ab87f" + integrity sha512-iJIUcQWA88IJB/5L15GnJVnSQJmf/YaxxV6zRavv83HILHaJQb6y0iFyDMdDO0gN8X37tdxmAOrH/P8B6RB8sQ== + +md5.js@^1.3.4: + version "1.3.5" + resolved "https://registry.yarnpkg.com/md5.js/-/md5.js-1.3.5.tgz#b5d07b8e3216e3e27cd728d72f70d1e6a342005f" + integrity sha512-xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg== + dependencies: + hash-base "^3.0.0" + inherits "^2.0.1" + safe-buffer "^5.1.2" + +memory-level@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/memory-level/-/memory-level-1.0.0.tgz#7323c3fd368f9af2f71c3cd76ba403a17ac41692" + integrity sha512-UXzwewuWeHBz5krr7EvehKcmLFNoXxGcvuYhC41tRnkrTbJohtS7kVn9akmgirtRygg+f7Yjsfi8Uu5SGSQ4Og== + dependencies: + abstract-level "^1.0.0" + functional-red-black-tree "^1.0.1" + module-error "^1.0.1" + +memorystream@^0.3.1: + version "0.3.1" + resolved "https://registry.yarnpkg.com/memorystream/-/memorystream-0.3.1.tgz#86d7090b30ce455d63fbae12dda51a47ddcaf9b2" + integrity sha512-S3UwM3yj5mtUSEfP41UZmt/0SCoVYUcU1rkXv+BQ5Ig8ndL4sPoJNBUJERafdPb5jjHJGuMgytgKvKIf58XNBw== + +merge2@^1.3.0, merge2@^1.4.1: + version "1.4.1" + resolved "https://registry.yarnpkg.com/merge2/-/merge2-1.4.1.tgz#4368892f885e907455a6fd7dc55c0c9d404990ae" + integrity sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg== + +micromatch@^4.0.4: + version "4.0.5" + resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-4.0.5.tgz#bc8999a7cbbf77cdc89f132f6e467051b49090c6" + integrity sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA== + dependencies: + braces "^3.0.2" + picomatch "^2.3.1" + +minimalistic-assert@^1.0.0, minimalistic-assert@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz#2e194de044626d4a10e7f7fbc00ce73e83e4d5c7" + integrity sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A== + +minimalistic-crypto-utils@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz#f6c00c1c0b082246e5c4d99dfb8c7c083b2b582a" + integrity sha512-JIYlbt6g8i5jKfJ3xz7rF0LXmv2TkDxBLUkiBeZ7bAx4GnnNMr8xFpGnOxn6GhTEHx3SjRrZEoU+j04prX1ktg== + +minimatch@5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.0.1.tgz#fb9022f7528125187c92bd9e9b6366be1cf3415b" + integrity sha512-nLDxIFRyhDblz3qMuq+SoRZED4+miJ/G+tdDrjkkkRnjAsBexeGpgjLEQ0blJy7rHhR2b93rhQY4SvyWu9v03g== + dependencies: + brace-expansion "^2.0.1" + +minimatch@^3.0.4, minimatch@^3.0.5, minimatch@^3.1.1, minimatch@^3.1.2: + version "3.1.2" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.1.2.tgz#19cd194bfd3e428f049a70817c038d89ab4be35b" + integrity sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw== + dependencies: + brace-expansion "^1.1.7" + +minimatch@^7.4.3: + version "7.4.6" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-7.4.6.tgz#845d6f254d8f4a5e4fd6baf44d5f10c8448365fb" + integrity sha512-sBz8G/YjVniEz6lKPNpKxXwazJe4c19fEfV2GDMX6AjFz+MX9uDWIZW8XreVhkFW3fkIdTv/gxWr/Kks5FFAVw== + dependencies: + brace-expansion "^2.0.1" + +minimist@^1.2.0, minimist@^1.2.6: + version "1.2.8" + resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.8.tgz#c1a464e7693302e082a075cee0c057741ac4772c" + integrity sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA== + +mkdirp-classic@^0.5.2: + version "0.5.3" + resolved "https://registry.yarnpkg.com/mkdirp-classic/-/mkdirp-classic-0.5.3.tgz#fa10c9115cc6d8865be221ba47ee9bed78601113" + integrity sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A== + +mkdirp@^0.5.1: + version "0.5.6" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-0.5.6.tgz#7def03d2432dcae4ba1d611445c48396062255f6" + integrity sha512-FP+p8RB8OWpF3YZBCrP5gtADmtXApB5AMLn+vdyA+PyxCjrCs00mjyUozssO33cwDeT3wNGdLxJ5M//YqtHAJw== + dependencies: + minimist "^1.2.6" + +mkdirp@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-1.0.4.tgz#3eb5ed62622756d79a5f0e2a221dfebad75c2f7e" + integrity sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw== + +mkdirp@^2.1.6: + version "2.1.6" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-2.1.6.tgz#964fbcb12b2d8c5d6fbc62a963ac95a273e2cc19" + integrity sha512-+hEnITedc8LAtIP9u3HJDFIdcLV2vXP33sqLLIzkv1Db1zO/1OxbvYf0Y1OC/S/Qo5dxHXepofhmxL02PsKe+A== + +mnemonist@^0.38.0: + version "0.38.5" + resolved "https://registry.yarnpkg.com/mnemonist/-/mnemonist-0.38.5.tgz#4adc7f4200491237fe0fa689ac0b86539685cade" + integrity sha512-bZTFT5rrPKtPJxj8KSV0WkPyNxl72vQepqqVUAW2ARUpUSF2qXMB6jZj7hW5/k7C1rtpzqbD/IIbJwLXUjCHeg== + dependencies: + obliterator "^2.0.0" + +mocha-multi@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/mocha-multi/-/mocha-multi-1.1.7.tgz#0f94d00c22ae39d20c253545d8eee0d2c4420205" + integrity sha512-SXZRgHy0XiRTASyOp0p6fjOkdj+R62L6cqutnYyQOvIjNznJuUwzykxctypeRiOwPd+gfn4yt3NRulMQyI8Tzg== + dependencies: + debug "^4.1.1" + is-string "^1.0.4" + lodash.once "^4.1.1" + mkdirp "^1.0.4" + object-assign "^4.1.1" + +mocha@^10.0.0, mocha@^10.2.0: + version "10.2.0" + resolved "https://registry.yarnpkg.com/mocha/-/mocha-10.2.0.tgz#1fd4a7c32ba5ac372e03a17eef435bd00e5c68b8" + integrity sha512-IDY7fl/BecMwFHzoqF2sg/SHHANeBoMMXFlS9r0OXKDssYE1M5O43wUY/9BVPeIvfH2zmEbBfseqN9gBQZzXkg== + dependencies: + ansi-colors "4.1.1" + browser-stdout "1.3.1" + chokidar "3.5.3" + debug "4.3.4" + diff "5.0.0" + escape-string-regexp "4.0.0" + find-up "5.0.0" + glob "7.2.0" + he "1.2.0" + js-yaml "4.1.0" + log-symbols "4.1.0" + minimatch "5.0.1" + ms "2.1.3" + nanoid "3.3.3" + serialize-javascript "6.0.0" + strip-json-comments "3.1.1" + supports-color "8.1.1" + workerpool "6.2.1" + yargs "16.2.0" + yargs-parser "20.2.4" + yargs-unparser "2.0.0" + +module-error@^1.0.1, module-error@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/module-error/-/module-error-1.0.2.tgz#8d1a48897ca883f47a45816d4fb3e3c6ba404d86" + integrity sha512-0yuvsqSCv8LbaOKhnsQ/T5JhyFlCYLPXK3U2sgV10zoKQwzs/MyfuQUOZQ1V/6OCOJsK/TRgNVrPuPDqtdMFtA== + +ms@2.1.2: + version "2.1.2" + resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.2.tgz#d09d1f357b443f493382a8eb3ccd183872ae6009" + integrity sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w== + +ms@2.1.3, ms@^2.1.1: + version "2.1.3" + resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.3.tgz#574c8138ce1d2b5861f0b44579dbadd60c6615b2" + integrity sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA== + +nan@^2.17.0: + version "2.18.0" + resolved "https://registry.yarnpkg.com/nan/-/nan-2.18.0.tgz#26a6faae7ffbeb293a39660e88a76b82e30b7554" + integrity sha512-W7tfG7vMOGtD30sHoZSSc/JVYiyDPEyQVso/Zz+/uQd0B0L46gtC+pHha5FFMRpil6fm/AoEcRWyOVi4+E/f8w== + +nanoid@3.3.3: + version "3.3.3" + resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.3.3.tgz#fd8e8b7aa761fe807dba2d1b98fb7241bb724a25" + integrity sha512-p1sjXuopFs0xg+fPASzQ28agW1oHD7xDsd9Xkf3T15H3c/cifrFHVwrh74PdoklAPi+i7MdRsE47vm2r6JoB+w== + +napi-macros@^2.2.2: + version "2.2.2" + resolved "https://registry.yarnpkg.com/napi-macros/-/napi-macros-2.2.2.tgz#817fef20c3e0e40a963fbf7b37d1600bd0201044" + integrity sha512-hmEVtAGYzVQpCKdbQea4skABsdXW4RUh5t5mJ2zzqowJS2OyXZTU1KhDVFhx+NlWZ4ap9mqR9TcDO3LTTttd+g== + +natural-compare-lite@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/natural-compare-lite/-/natural-compare-lite-1.4.0.tgz#17b09581988979fddafe0201e931ba933c96cbb4" + integrity sha512-Tj+HTDSJJKaZnfiuw+iaF9skdPpTo2GtEly5JHnWV/hfv2Qj/9RKsGISQtLh2ox3l5EAGw487hnBee0sIJ6v2g== + +natural-compare@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/natural-compare/-/natural-compare-1.4.0.tgz#4abebfeed7541f2c27acfb29bdbbd15c8d5ba4f7" + integrity sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw== + +node-addon-api@^2.0.0: + version "2.0.2" + resolved "https://registry.yarnpkg.com/node-addon-api/-/node-addon-api-2.0.2.tgz#432cfa82962ce494b132e9d72a15b29f71ff5d32" + integrity sha512-Ntyt4AIXyaLIuMHF6IOoTakB3K+RWxwtsHNRxllEoA6vPwP9o4866g6YWDLUdnucilZhmkxiHwHr11gAENw+QA== + +node-fetch@^2.6.0: + version "2.7.0" + resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.7.0.tgz#d0f0fa6e3e2dc1d27efcd8ad99d550bda94d187d" + integrity sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A== + dependencies: + whatwg-url "^5.0.0" + +node-gyp-build@^4.2.0, node-gyp-build@^4.3.0: + version "4.6.1" + resolved "https://registry.yarnpkg.com/node-gyp-build/-/node-gyp-build-4.6.1.tgz#24b6d075e5e391b8d5539d98c7fc5c210cac8a3e" + integrity sha512-24vnklJmyRS8ViBNI8KbtK/r/DmXQMRiOMXTNz2nrTnAYUwjmEEbnnpB/+kt+yWRv73bPsSPRFddrcIbAxSiMQ== + +normalize-path@^3.0.0, normalize-path@~3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/normalize-path/-/normalize-path-3.0.0.tgz#0dcd69ff23a1c9b11fd0978316644a0388216a65" + integrity sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA== + +nth-check@^2.0.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/nth-check/-/nth-check-2.1.1.tgz#c9eab428effce36cd6b92c924bdb000ef1f1ed1d" + integrity sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w== + dependencies: + boolbase "^1.0.0" + +object-assign@^4.1.1: + version "4.1.1" + resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863" + integrity sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg== + +object-inspect@^1.12.3, object-inspect@^1.9.0: + version "1.12.3" + resolved "https://registry.yarnpkg.com/object-inspect/-/object-inspect-1.12.3.tgz#ba62dffd67ee256c8c086dfae69e016cd1f198b9" + integrity sha512-geUvdk7c+eizMNUDkRpW1wJwgfOiOeHbxBR/hLXK1aT6zmVSO0jsQcs7fj6MGw89jC/cjGfLcNOrtMYtGqm81g== + +object-keys@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/object-keys/-/object-keys-1.1.1.tgz#1c47f272df277f3b1daf061677d9c82e2322c60e" + integrity sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA== + +object.assign@^4.1.4: + version "4.1.4" + resolved "https://registry.yarnpkg.com/object.assign/-/object.assign-4.1.4.tgz#9673c7c7c351ab8c4d0b516f4343ebf4dfb7799f" + integrity sha512-1mxKf0e58bvyjSCtKYY4sRe9itRk3PJpquJOjeIkz885CczcI4IvJJDLPS72oowuSh+pBxUFROpX+TU++hxhZQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.1.4" + has-symbols "^1.0.3" + object-keys "^1.1.1" + +object.fromentries@^2.0.6: + version "2.0.7" + resolved "https://registry.yarnpkg.com/object.fromentries/-/object.fromentries-2.0.7.tgz#71e95f441e9a0ea6baf682ecaaf37fa2a8d7e616" + integrity sha512-UPbPHML6sL8PI/mOqPwsH4G6iyXcCGzLin8KvEPenOZN5lpCNBZZQ+V62vdjB1mQHrmqGQt5/OJzemUA+KJmEA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + +object.groupby@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/object.groupby/-/object.groupby-1.0.1.tgz#d41d9f3c8d6c778d9cbac86b4ee9f5af103152ee" + integrity sha512-HqaQtqLnp/8Bn4GL16cj+CUYbnpe1bh0TtEaWvybszDG4tgxCJuRpV8VGuvNaI1fAnI4lUJzDG55MXcOH4JZcQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + get-intrinsic "^1.2.1" + +object.values@^1.1.6: + version "1.1.7" + resolved "https://registry.yarnpkg.com/object.values/-/object.values-1.1.7.tgz#617ed13272e7e1071b43973aa1655d9291b8442a" + integrity sha512-aU6xnDFYT3x17e/f0IiiwlGPTy2jzMySGfUB4fq6z7CV8l85CWHDk5ErhyhpfDHhrOMwGFhSQkhMGHaIotA6Ng== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + +obliterator@^2.0.0: + version "2.0.4" + resolved "https://registry.yarnpkg.com/obliterator/-/obliterator-2.0.4.tgz#fa650e019b2d075d745e44f1effeb13a2adbe816" + integrity sha512-lgHwxlxV1qIg1Eap7LgIeoBWIMFibOjbrYPIPJZcI1mmGAI2m3lNYpK12Y+GBdPQ0U1hRwSord7GIaawz962qQ== + +once@^1.3.0, once@^1.3.1, once@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1" + integrity sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w== + dependencies: + wrappy "1" + +optionator@^0.9.3: + version "0.9.3" + resolved "https://registry.yarnpkg.com/optionator/-/optionator-0.9.3.tgz#007397d44ed1872fdc6ed31360190f81814e2c64" + integrity sha512-JjCoypp+jKn1ttEFExxhetCKeJt9zhAgAve5FXHixTvFDW/5aEktX9bufBKLRRMdU7bNtpLfcGu94B3cdEJgjg== + dependencies: + "@aashutoshrathi/word-wrap" "^1.2.3" + deep-is "^0.1.3" + fast-levenshtein "^2.0.6" + levn "^0.4.1" + prelude-ls "^1.2.1" + type-check "^0.4.0" + +os-tmpdir@~1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/os-tmpdir/-/os-tmpdir-1.0.2.tgz#bbe67406c79aa85c5cfec766fe5734555dfa1274" + integrity sha512-D2FR03Vir7FIu45XBY20mTb+/ZSWB00sjU9jdQXt83gDrI4Ztz5Fs7/yy74g2N5SVQY4xY1qDr4rNddwYRVX0g== + +p-limit@^1.1.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-1.3.0.tgz#b86bd5f0c25690911c7590fcbfc2010d54b3ccb8" + integrity sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q== + dependencies: + p-try "^1.0.0" + +p-limit@^3.0.2: + version "3.1.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-3.1.0.tgz#e1daccbe78d0d1388ca18c64fea38e3e57e3706b" + integrity sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ== + dependencies: + yocto-queue "^0.1.0" + +p-locate@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-2.0.0.tgz#20a0103b222a70c8fd39cc2e580680f3dde5ec43" + integrity sha512-nQja7m7gSKuewoVRen45CtVfODR3crN3goVQ0DDZ9N3yHxgpkuBhZqsaiotSQRrADUrne346peY7kT3TSACykg== + dependencies: + p-limit "^1.1.0" + +p-locate@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-5.0.0.tgz#83c8315c6785005e3bd021839411c9e110e6d834" + integrity sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw== + dependencies: + p-limit "^3.0.2" + +p-map@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/p-map/-/p-map-4.0.0.tgz#bb2f95a5eda2ec168ec9274e06a747c3e2904d2b" + integrity sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ== + dependencies: + aggregate-error "^3.0.0" + +p-try@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/p-try/-/p-try-1.0.0.tgz#cbc79cdbaf8fd4228e13f621f2b1a237c1b207b3" + integrity sha512-U1etNYuMJoIz3ZXSrrySFjsXQTWOx2/jdi86L+2pRvph/qMKL6sbcCYdH23fqsbm8TH2Gn0OybpT4eSFlCVHww== + +parent-module@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/parent-module/-/parent-module-1.0.1.tgz#691d2709e78c79fae3a156622452d00762caaaa2" + integrity sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g== + dependencies: + callsites "^3.0.0" + +path-browserify@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/path-browserify/-/path-browserify-1.0.1.tgz#d98454a9c3753d5790860f16f68867b9e46be1fd" + integrity sha512-b7uo2UCUOYZcnF/3ID0lulOJi/bafxa1xPe7ZPsammBSpjSWQkjNxlt635YGS2MiR9GjvuXCtz2emr3jbsz98g== + +path-exists@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-3.0.0.tgz#ce0ebeaa5f78cb18925ea7d810d7b59b010fd515" + integrity sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ== + +path-exists@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-4.0.0.tgz#513bdbe2d3b95d7762e8c1137efa195c6c61b5b3" + integrity sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w== + +path-is-absolute@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f" + integrity sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg== + +path-key@^3.1.0: + version "3.1.1" + resolved "https://registry.yarnpkg.com/path-key/-/path-key-3.1.1.tgz#581f6ade658cbba65a0d3380de7753295054f375" + integrity sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q== + +path-parse@^1.0.6, path-parse@^1.0.7: + version "1.0.7" + resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.7.tgz#fbc114b60ca42b30d9daf5858e4bd68bbedb6735" + integrity sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw== + +path-type@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/path-type/-/path-type-4.0.0.tgz#84ed01c0a7ba380afe09d90a8c180dcd9d03043b" + integrity sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw== + +pathval@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/pathval/-/pathval-1.1.1.tgz#8534e77a77ce7ac5a2512ea21e0fdb8fcf6c3d8d" + integrity sha512-Dp6zGqpTdETdR63lehJYPeIOqpiNBNtc7BpWSLrOje7UaIsE5aY92r/AunQA7rsXvet3lrJ3JnZX29UPTKXyKQ== + +pbkdf2@^3.0.17: + version "3.1.2" + resolved "https://registry.yarnpkg.com/pbkdf2/-/pbkdf2-3.1.2.tgz#dd822aa0887580e52f1a039dc3eda108efae3075" + integrity sha512-iuh7L6jA7JEGu2WxDwtQP1ddOpaJNC4KlDEFfdQajSGgGPNi4OyDc2R7QnbY2bR9QjBVGwgvTdNJZoE7RaxUMA== + dependencies: + create-hash "^1.1.2" + create-hmac "^1.1.4" + ripemd160 "^2.0.1" + safe-buffer "^5.0.1" + sha.js "^2.4.8" + +picomatch@^2.0.4, picomatch@^2.2.1, picomatch@^2.3.1: + version "2.3.1" + resolved "https://registry.yarnpkg.com/picomatch/-/picomatch-2.3.1.tgz#3ba3833733646d9d3e4995946c1365a67fb07a42" + integrity sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA== + +postcss-selector-parser@^6.0.9: + version "6.0.13" + resolved "https://registry.yarnpkg.com/postcss-selector-parser/-/postcss-selector-parser-6.0.13.tgz#d05d8d76b1e8e173257ef9d60b706a8e5e99bf1b" + integrity sha512-EaV1Gl4mUEV4ddhDnv/xtj7sxwrwxdetHdWUGnT4VJQf+4d05v6lHYZr8N573k5Z0BViss7BDhfWtKS3+sfAqQ== + dependencies: + cssesc "^3.0.0" + util-deprecate "^1.0.2" + +prelude-ls@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/prelude-ls/-/prelude-ls-1.2.1.tgz#debc6489d7a6e6b0e7611888cec880337d316396" + integrity sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g== + +prettier-linter-helpers@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/prettier-linter-helpers/-/prettier-linter-helpers-1.0.0.tgz#d23d41fe1375646de2d0104d3454a3008802cf7b" + integrity sha512-GbK2cP9nraSSUF9N2XwUwqfzlAFlMNYYl+ShE/V+H8a9uNl/oUqB1w2EL54Jh0OlyRSd8RfWYJ3coVS4TROP2w== + dependencies: + fast-diff "^1.1.2" + +prettier@^3.0.3: + version "3.0.3" + resolved "https://registry.yarnpkg.com/prettier/-/prettier-3.0.3.tgz#432a51f7ba422d1469096c0fdc28e235db8f9643" + integrity sha512-L/4pUDMxcNa8R/EthV08Zt42WBO4h1rarVtK0K+QJG0X187OLo7l699jWw0GKuwzkPQ//jMFA/8Xm6Fh3J/DAg== + +process-nextick-args@~2.0.0: + version "2.0.1" + resolved "https://registry.yarnpkg.com/process-nextick-args/-/process-nextick-args-2.0.1.tgz#7820d9b16120cc55ca9ae7792680ae7dba6d7fe2" + integrity sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag== + +proper-lockfile@^4.1.2: + version "4.1.2" + resolved "https://registry.yarnpkg.com/proper-lockfile/-/proper-lockfile-4.1.2.tgz#c8b9de2af6b2f1601067f98e01ac66baa223141f" + integrity sha512-TjNPblN4BwAWMXU8s9AEz4JmQxnD1NNL7bNOY/AKUzyamc379FWASUhc/K1pL2noVb+XmZKLL68cjzLsiOAMaA== + dependencies: + graceful-fs "^4.2.4" + retry "^0.12.0" + signal-exit "^3.0.2" + +pump@^1.0.0: + version "1.0.3" + resolved "https://registry.yarnpkg.com/pump/-/pump-1.0.3.tgz#5dfe8311c33bbf6fc18261f9f34702c47c08a954" + integrity sha512-8k0JupWme55+9tCVE+FS5ULT3K6AbgqrGa58lTT49RpyfwwcGedHqaC5LlQNdEAumn/wFsu6aPwkuPMioy8kqw== + dependencies: + end-of-stream "^1.1.0" + once "^1.3.1" + +pump@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/pump/-/pump-3.0.0.tgz#b4a2116815bde2f4e1ea602354e8c75565107a64" + integrity sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww== + dependencies: + end-of-stream "^1.1.0" + once "^1.3.1" + +punycode@^2.1.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.3.0.tgz#f67fa67c94da8f4d0cfff981aee4118064199b8f" + integrity sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA== + +queue-microtask@^1.2.2, queue-microtask@^1.2.3: + version "1.2.3" + resolved "https://registry.yarnpkg.com/queue-microtask/-/queue-microtask-1.2.3.tgz#4929228bbc724dfac43e0efb058caf7b6cfb6243" + integrity sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A== + +rambda@^7.4.0: + version "7.5.0" + resolved "https://registry.yarnpkg.com/rambda/-/rambda-7.5.0.tgz#1865044c59bc0b16f63026c6e5a97e4b1bbe98fe" + integrity sha512-y/M9weqWAH4iopRd7EHDEQQvpFPHj1AA3oHozE9tfITHUtTR7Z9PSlIRRG2l1GuW7sefC1cXFfIcF+cgnShdBA== + +randombytes@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/randombytes/-/randombytes-2.1.0.tgz#df6f84372f0270dc65cdf6291349ab7a473d4f2a" + integrity sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ== + dependencies: + safe-buffer "^5.1.0" + +raw-body@^2.4.1: + version "2.5.2" + resolved "https://registry.yarnpkg.com/raw-body/-/raw-body-2.5.2.tgz#99febd83b90e08975087e8f1f9419a149366b68a" + integrity sha512-8zGqypfENjCIqGhgXToC8aB2r7YrBX+AQAfIPs/Mlk+BtPTztOvTS01NRW/3Eh60J+a48lt8qsCzirQ6loCVfA== + dependencies: + bytes "3.1.2" + http-errors "2.0.0" + iconv-lite "0.4.24" + unpipe "1.0.0" + +readable-stream@^2.2.2, readable-stream@^2.3.0, readable-stream@^2.3.5: + version "2.3.8" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.3.8.tgz#91125e8042bba1b9887f49345f6277027ce8be9b" + integrity sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA== + dependencies: + core-util-is "~1.0.0" + inherits "~2.0.3" + isarray "~1.0.0" + process-nextick-args "~2.0.0" + safe-buffer "~5.1.1" + string_decoder "~1.1.1" + util-deprecate "~1.0.1" + +readable-stream@^3.1.1, readable-stream@^3.4.0, readable-stream@^3.5.0, readable-stream@^3.6.0: + version "3.6.2" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-3.6.2.tgz#56a9b36ea965c00c5a93ef31eb111a0f11056967" + integrity sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA== + dependencies: + inherits "^2.0.3" + string_decoder "^1.1.1" + util-deprecate "^1.0.1" + +readable-stream@~1.0.26-4: + version "1.0.34" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-1.0.34.tgz#125820e34bc842d2f2aaafafe4c2916ee32c157c" + integrity sha512-ok1qVCJuRkNmvebYikljxJA/UEsKwLl2nI1OmaqAu4/UE+h0wKCHok4XkL/gvi39OacXvw59RJUOFUkDib2rHg== + dependencies: + core-util-is "~1.0.0" + inherits "~2.0.1" + isarray "0.0.1" + string_decoder "~0.10.x" + +readdirp@~3.6.0: + version "3.6.0" + resolved "https://registry.yarnpkg.com/readdirp/-/readdirp-3.6.0.tgz#74a370bd857116e245b29cc97340cd431a02a6c7" + integrity sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA== + dependencies: + picomatch "^2.2.1" + +regexp.prototype.flags@^1.5.1: + version "1.5.1" + resolved "https://registry.yarnpkg.com/regexp.prototype.flags/-/regexp.prototype.flags-1.5.1.tgz#90ce989138db209f81492edd734183ce99f9677e" + integrity sha512-sy6TXMN+hnP/wMy+ISxg3krXx7BAtWVO4UouuCN/ziM9UEne0euamVNafDfvC83bRNr95y0V5iijeDQFUNpvrg== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + set-function-name "^2.0.0" + +require-directory@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/require-directory/-/require-directory-2.1.1.tgz#8c64ad5fd30dab1c976e2344ffe7f792a6a6df42" + integrity sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q== + +require-from-string@^2.0.0: + version "2.0.2" + resolved "https://registry.yarnpkg.com/require-from-string/-/require-from-string-2.0.2.tgz#89a7fdd938261267318eafe14f9c32e598c36909" + integrity sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw== + +resolve-from@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/resolve-from/-/resolve-from-4.0.0.tgz#4abcd852ad32dd7baabfe9b40e00a36db5f392e6" + integrity sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g== + +resolve@1.17.0: + version "1.17.0" + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.17.0.tgz#b25941b54968231cc2d1bb76a79cb7f2c0bf8444" + integrity sha512-ic+7JYiV8Vi2yzQGFWOkiZD5Z9z7O2Zhm9XMaTxdJExKasieFCr+yXZ/WmXsckHiKl12ar0y6XiXDx3m4RHn1w== + dependencies: + path-parse "^1.0.6" + +resolve@^1.22.4: + version "1.22.8" + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.22.8.tgz#b6c87a9f2aa06dfab52e3d70ac8cde321fa5a48d" + integrity sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw== + dependencies: + is-core-module "^2.13.0" + path-parse "^1.0.7" + supports-preserve-symlinks-flag "^1.0.0" + +retry@^0.12.0: + version "0.12.0" + resolved "https://registry.yarnpkg.com/retry/-/retry-0.12.0.tgz#1b42a6266a21f07421d1b0b54b7dc167b01c013b" + integrity sha512-9LkiTwjUh6rT555DtE9rTX+BKByPfrMzEAtnlEtdEwr3Nkffwiihqe2bWADg+OQRjt9gl6ICdmB/ZFDCGAtSow== + +reusify@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/reusify/-/reusify-1.0.4.tgz#90da382b1e126efc02146e90845a88db12925d76" + integrity sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw== + +rimraf@^2.2.8: + version "2.7.1" + resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.7.1.tgz#35797f13a7fdadc566142c29d4f07ccad483e3ec" + integrity sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w== + dependencies: + glob "^7.1.3" + +rimraf@^3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-3.0.2.tgz#f1a5402ba6220ad52cc1282bac1ae3aa49fd061a" + integrity sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA== + dependencies: + glob "^7.1.3" + +ripemd160@^2.0.0, ripemd160@^2.0.1: + version "2.0.2" + resolved "https://registry.yarnpkg.com/ripemd160/-/ripemd160-2.0.2.tgz#a1c1a6f624751577ba5d07914cbc92850585890c" + integrity sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA== + dependencies: + hash-base "^3.0.0" + inherits "^2.0.1" + +rlp@^2.2.3: + version "2.2.7" + resolved "https://registry.yarnpkg.com/rlp/-/rlp-2.2.7.tgz#33f31c4afac81124ac4b283e2bd4d9720b30beaf" + integrity sha512-d5gdPmgQ0Z+AklL2NVXr/IoSjNZFfTVvQWzL/AM2AOcSzYP2xjlb0AC8YyCLc41MSNf6P6QVtjgPdmVtzb+4lQ== + dependencies: + bn.js "^5.2.0" + +run-parallel-limit@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/run-parallel-limit/-/run-parallel-limit-1.1.0.tgz#be80e936f5768623a38a963262d6bef8ff11e7ba" + integrity sha512-jJA7irRNM91jaKc3Hcl1npHsFLOXOoTkPCUL1JEa1R82O2miplXXRaGdjW/KM/98YQWDhJLiSs793CnXfblJUw== + dependencies: + queue-microtask "^1.2.2" + +run-parallel@^1.1.9: + version "1.2.0" + resolved "https://registry.yarnpkg.com/run-parallel/-/run-parallel-1.2.0.tgz#66d1368da7bdf921eb9d95bd1a9229e7f21a43ee" + integrity sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA== + dependencies: + queue-microtask "^1.2.2" + +rustbn.js@~0.2.0: + version "0.2.0" + resolved "https://registry.yarnpkg.com/rustbn.js/-/rustbn.js-0.2.0.tgz#8082cb886e707155fd1cb6f23bd591ab8d55d0ca" + integrity sha512-4VlvkRUuCJvr2J6Y0ImW7NvTCriMi7ErOAqWk1y69vAdoNIzCF3yPmgeNzx+RQTLEDFq5sHfscn1MwHxP9hNfA== + +safe-array-concat@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/safe-array-concat/-/safe-array-concat-1.0.1.tgz#91686a63ce3adbea14d61b14c99572a8ff84754c" + integrity sha512-6XbUAseYE2KtOuGueyeobCySj9L4+66Tn6KQMOPQJrAJEowYKW/YR/MGJZl7FdydUdaFu4LYyDZjxf4/Nmo23Q== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.2.1" + has-symbols "^1.0.3" + isarray "^2.0.5" + +safe-buffer@^5.0.1, safe-buffer@^5.1.0, safe-buffer@^5.1.1, safe-buffer@^5.1.2, safe-buffer@^5.2.0, safe-buffer@~5.2.0: + version "5.2.1" + resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6" + integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ== + +safe-buffer@~5.1.0, safe-buffer@~5.1.1: + version "5.1.2" + resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.1.2.tgz#991ec69d296e0313747d59bdfd2b745c35f8828d" + integrity sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g== + +safe-regex-test@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/safe-regex-test/-/safe-regex-test-1.0.0.tgz#793b874d524eb3640d1873aad03596db2d4f2295" + integrity sha512-JBUUzyOgEwXQY1NuPtvcj/qcBDbDmEvWufhlnXZIm75DEHp+afM1r1ujJpJsV/gSM4t59tpDyPi1sd6ZaPFfsA== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.1.3" + is-regex "^1.1.4" + +"safer-buffer@>= 2.1.2 < 3", safer-buffer@~2.1.0: + version "2.1.2" + resolved "https://registry.yarnpkg.com/safer-buffer/-/safer-buffer-2.1.2.tgz#44fa161b0187b9549dd84bb91802f9bd8385cd6a" + integrity sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg== + +scrypt-js@3.0.1, scrypt-js@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/scrypt-js/-/scrypt-js-3.0.1.tgz#d314a57c2aef69d1ad98a138a21fe9eafa9ee312" + integrity sha512-cdwTTnqPu0Hyvf5in5asVdZocVDTNRmR7XEcJuIzMjJeSHybHl7vpB66AzwTaIg6CLSbtjcxc8fqcySfnTkccA== + +secp256k1@^4.0.1: + version "4.0.3" + resolved "https://registry.yarnpkg.com/secp256k1/-/secp256k1-4.0.3.tgz#c4559ecd1b8d3c1827ed2d1b94190d69ce267303" + integrity sha512-NLZVf+ROMxwtEj3Xa562qgv2BK5e2WNmXPiOdVIPLgs6lyTzMvBq0aWTYMI5XCP9jZMVKOcqZLw/Wc4vDkuxhA== + dependencies: + elliptic "^6.5.4" + node-addon-api "^2.0.0" + node-gyp-build "^4.2.0" + +semver@^5.5.0: + version "5.7.2" + resolved "https://registry.yarnpkg.com/semver/-/semver-5.7.2.tgz#48d55db737c3287cd4835e17fa13feace1c41ef8" + integrity sha512-cBznnQ9KjJqU67B52RMC65CMarK2600WFnbkcaiwWq3xy/5haFJlshgnpjovMVJ+Hff49d8GEn0b87C5pDQ10g== + +semver@^6.3.0, semver@^6.3.1: + version "6.3.1" + resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.1.tgz#556d2ef8689146e46dcea4bfdd095f3434dffcb4" + integrity sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA== + +semver@^7.3.5, semver@^7.3.7, semver@^7.5.1, semver@^7.5.4: + version "7.5.4" + resolved "https://registry.yarnpkg.com/semver/-/semver-7.5.4.tgz#483986ec4ed38e1c6c48c34894a9182dbff68a6e" + integrity sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA== + dependencies: + lru-cache "^6.0.0" + +serialize-javascript@6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/serialize-javascript/-/serialize-javascript-6.0.0.tgz#efae5d88f45d7924141da8b5c3a7a7e663fefeb8" + integrity sha512-Qr3TosvguFt8ePWqsvRfrKyQXIiW+nGbYpy8XK24NQHE83caxWt+mIymTT19DGFbNWNLfEwsrkSmN64lVWB9ag== + dependencies: + randombytes "^2.1.0" + +set-function-name@^2.0.0: + version "2.0.1" + resolved "https://registry.yarnpkg.com/set-function-name/-/set-function-name-2.0.1.tgz#12ce38b7954310b9f61faa12701620a0c882793a" + integrity sha512-tMNCiqYVkXIZgc2Hnoy2IvC/f8ezc5koaRFkCjrpWzGpCd3qbZXPzVy9MAZzK1ch/X0jvSkojys3oqJN0qCmdA== + dependencies: + define-data-property "^1.0.1" + functions-have-names "^1.2.3" + has-property-descriptors "^1.0.0" + +setimmediate@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/setimmediate/-/setimmediate-1.0.5.tgz#290cbb232e306942d7d7ea9b83732ab7856f8285" + integrity sha512-MATJdZp8sLqDl/68LfQmbP8zKPLQNV6BIZoIgrscFDQ+RsvK/BxeDQOgyxKKoh0y/8h3BqVFnCqQ/gd+reiIXA== + +setprototypeof@1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/setprototypeof/-/setprototypeof-1.2.0.tgz#66c9a24a73f9fc28cbe66b09fed3d33dcaf1b424" + integrity sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw== + +sha.js@^2.4.0, sha.js@^2.4.8: + version "2.4.11" + resolved "https://registry.yarnpkg.com/sha.js/-/sha.js-2.4.11.tgz#37a5cf0b81ecbc6943de109ba2960d1b26584ae7" + integrity sha512-QMEp5B7cftE7APOjk5Y6xgrbWu+WkLVQwk8JNjZ8nKRciZaByEW6MubieAiToS7+dwvrjGhH8jRXz3MVd0AYqQ== + dependencies: + inherits "^2.0.1" + safe-buffer "^5.0.1" + +shebang-command@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/shebang-command/-/shebang-command-2.0.0.tgz#ccd0af4f8835fbdc265b82461aaf0c36663f34ea" + integrity sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA== + dependencies: + shebang-regex "^3.0.0" + +shebang-regex@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/shebang-regex/-/shebang-regex-3.0.0.tgz#ae16f1644d873ecad843b0307b143362d4c42172" + integrity sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A== + +side-channel@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/side-channel/-/side-channel-1.0.4.tgz#efce5c8fdc104ee751b25c58d4290011fa5ea2cf" + integrity sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw== + dependencies: + call-bind "^1.0.0" + get-intrinsic "^1.0.2" + object-inspect "^1.9.0" + +signal-exit@^3.0.2: + version "3.0.7" + resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.7.tgz#a9a1767f8af84155114eaabd73f99273c8f59ad9" + integrity sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ== + +slash@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/slash/-/slash-3.0.0.tgz#6539be870c165adbd5240220dbe361f1bc4d4634" + integrity sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q== + +solc@0.7.3: + version "0.7.3" + resolved "https://registry.yarnpkg.com/solc/-/solc-0.7.3.tgz#04646961bd867a744f63d2b4e3c0701ffdc7d78a" + integrity sha512-GAsWNAjGzIDg7VxzP6mPjdurby3IkGCjQcM8GFYZT6RyaoUZKmMU6Y7YwG+tFGhv7dwZ8rmR4iwFDrrD99JwqA== + dependencies: + command-exists "^1.2.8" + commander "3.0.2" + follow-redirects "^1.12.1" + fs-extra "^0.30.0" + js-sha3 "0.8.0" + memorystream "^0.3.1" + require-from-string "^2.0.0" + semver "^5.5.0" + tmp "0.0.33" + +source-map-support@^0.5.13: + version "0.5.21" + resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.5.21.tgz#04fe7c7f9e1ed2d662233c28cb2b35b9f63f6e4f" + integrity sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w== + dependencies: + buffer-from "^1.0.0" + source-map "^0.6.0" + +source-map@^0.6.0: + version "0.6.1" + resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.6.1.tgz#74722af32e9614e9c287a8d0bbde48b5e2f1a263" + integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g== + +split-ca@^1.0.0, split-ca@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/split-ca/-/split-ca-1.0.1.tgz#6c83aff3692fa61256e0cd197e05e9de157691a6" + integrity sha512-Q5thBSxp5t8WPTTJQS59LrGqOZqOsrhDGDVm8azCqIBjSBd7nd9o2PM+mDulQQkh8h//4U6hFZnc/mul8t5pWQ== + +ssh2@^1.11.0: + version "1.14.0" + resolved "https://registry.yarnpkg.com/ssh2/-/ssh2-1.14.0.tgz#8f68440e1b768b66942c9e4e4620b2725b3555bb" + integrity sha512-AqzD1UCqit8tbOKoj6ztDDi1ffJZ2rV2SwlgrVVrHPkV5vWqGJOVp5pmtj18PunkPJAuKQsnInyKV+/Nb2bUnA== + dependencies: + asn1 "^0.2.6" + bcrypt-pbkdf "^1.0.2" + optionalDependencies: + cpu-features "~0.0.8" + nan "^2.17.0" + +stacktrace-parser@^0.1.10: + version "0.1.10" + resolved "https://registry.yarnpkg.com/stacktrace-parser/-/stacktrace-parser-0.1.10.tgz#29fb0cae4e0d0b85155879402857a1639eb6051a" + integrity sha512-KJP1OCML99+8fhOHxwwzyWrlUuVX5GQ0ZpJTd1DFXhdkrvg1szxfHhawXUZ3g9TkXORQd4/WG68jMlQZ2p8wlg== + dependencies: + type-fest "^0.7.1" + +statuses@2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/statuses/-/statuses-2.0.1.tgz#55cb000ccf1d48728bd23c685a063998cf1a1b63" + integrity sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ== + +string-width@^4.1.0, string-width@^4.2.0: + version "4.2.3" + resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010" + integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g== + dependencies: + emoji-regex "^8.0.0" + is-fullwidth-code-point "^3.0.0" + strip-ansi "^6.0.1" + +string.prototype.trim@^1.2.8: + version "1.2.8" + resolved "https://registry.yarnpkg.com/string.prototype.trim/-/string.prototype.trim-1.2.8.tgz#f9ac6f8af4bd55ddfa8895e6aea92a96395393bd" + integrity sha512-lfjY4HcixfQXOfaqCvcBuOIapyaroTXhbkfJN3gcB1OtyupngWK4sEET9Knd0cXd28kTUqu/kHoV4HKSJdnjiQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + +string.prototype.trimend@^1.0.7: + version "1.0.7" + resolved "https://registry.yarnpkg.com/string.prototype.trimend/-/string.prototype.trimend-1.0.7.tgz#1bb3afc5008661d73e2dc015cd4853732d6c471e" + integrity sha512-Ni79DqeB72ZFq1uH/L6zJ+DKZTkOtPIHovb3YZHQViE+HDouuU4mBrLOLDn5Dde3RF8qw5qVETEjhu9locMLvA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + +string.prototype.trimstart@^1.0.7: + version "1.0.7" + resolved "https://registry.yarnpkg.com/string.prototype.trimstart/-/string.prototype.trimstart-1.0.7.tgz#d4cdb44b83a4737ffbac2d406e405d43d0184298" + integrity sha512-NGhtDFu3jCEm7B4Fy0DpLewdJQOZcQ0rGbwQ/+stjnrp2i+rlKeCvos9hOIeCmqwratM47OBxY7uFZzjxHXmrg== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + +string_decoder@^1.1.1: + version "1.3.0" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.3.0.tgz#42f114594a46cf1a8e30b0a84f56c78c3edac21e" + integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA== + dependencies: + safe-buffer "~5.2.0" + +string_decoder@~0.10.x: + version "0.10.31" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-0.10.31.tgz#62e203bc41766c6c28c9fc84301dab1c5310fa94" + integrity sha512-ev2QzSzWPYmy9GuqfIVildA4OdcGLeFZQrq5ys6RtiuF+RQQiZWr8TZNyAcuVXyQRYfEO+MsoB/1BuQVhOJuoQ== + +string_decoder@~1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.1.1.tgz#9cf1611ba62685d7030ae9e4ba34149c3af03fc8" + integrity sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg== + dependencies: + safe-buffer "~5.1.0" + +strip-ansi@^6.0.0, strip-ansi@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9" + integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A== + dependencies: + ansi-regex "^5.0.1" + +strip-bom@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/strip-bom/-/strip-bom-3.0.0.tgz#2334c18e9c759f7bdd56fdef7e9ae3d588e68ed3" + integrity sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA== + +strip-hex-prefix@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/strip-hex-prefix/-/strip-hex-prefix-1.0.0.tgz#0c5f155fef1151373377de9dbb588da05500e36f" + integrity sha512-q8d4ue7JGEiVcypji1bALTos+0pWtyGlivAWyPuTkHzuTCJqrK9sWxYQZUq6Nq3cuyv3bm734IhHvHtGGURU6A== + dependencies: + is-hex-prefixed "1.0.0" + +strip-json-comments@3.1.1, strip-json-comments@^3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz#31f1281b3832630434831c310c01cccda8cbe006" + integrity sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig== + +supports-color@8.1.1: + version "8.1.1" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-8.1.1.tgz#cd6fc17e28500cff56c1b86c0a7fd4a54a73005c" + integrity sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q== + dependencies: + has-flag "^4.0.0" + +supports-color@^5.3.0: + version "5.5.0" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-5.5.0.tgz#e2e69a44ac8772f78a1ec0b35b689df6530efc8f" + integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow== + dependencies: + has-flag "^3.0.0" + +supports-color@^7.1.0: + version "7.2.0" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-7.2.0.tgz#1b7dcdcb32b8138801b3e478ba6a51caa89648da" + integrity sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw== + dependencies: + has-flag "^4.0.0" + +supports-preserve-symlinks-flag@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz#6eda4bd344a3c94aea376d4cc31bc77311039e09" + integrity sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w== + +tar-fs@~1.16.3: + version "1.16.3" + resolved "https://registry.yarnpkg.com/tar-fs/-/tar-fs-1.16.3.tgz#966a628841da2c4010406a82167cbd5e0c72d509" + integrity sha512-NvCeXpYx7OsmOh8zIOP/ebG55zZmxLE0etfWRbWok+q2Qo8x/vOR/IJT1taADXPe+jsiu9axDb3X4B+iIgNlKw== + dependencies: + chownr "^1.0.1" + mkdirp "^0.5.1" + pump "^1.0.0" + tar-stream "^1.1.2" + +tar-fs@~2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/tar-fs/-/tar-fs-2.0.1.tgz#e44086c1c60d31a4f0cf893b1c4e155dabfae9e2" + integrity sha512-6tzWDMeroL87uF/+lin46k+Q+46rAJ0SyPGz7OW7wTgblI273hsBqk2C1j0/xNadNLKDTUL9BukSjB7cwgmlPA== + dependencies: + chownr "^1.1.1" + mkdirp-classic "^0.5.2" + pump "^3.0.0" + tar-stream "^2.0.0" + +tar-stream@^1.1.2: + version "1.6.2" + resolved "https://registry.yarnpkg.com/tar-stream/-/tar-stream-1.6.2.tgz#8ea55dab37972253d9a9af90fdcd559ae435c555" + integrity sha512-rzS0heiNf8Xn7/mpdSVVSMAWAoy9bfb1WOTYC78Z0UQKeKa/CWS8FOq0lKGNa8DWKAn9gxjCvMLYc5PGXYlK2A== + dependencies: + bl "^1.0.0" + buffer-alloc "^1.2.0" + end-of-stream "^1.0.0" + fs-constants "^1.0.0" + readable-stream "^2.3.0" + to-buffer "^1.1.1" + xtend "^4.0.0" + +tar-stream@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/tar-stream/-/tar-stream-2.2.0.tgz#acad84c284136b060dc3faa64474aa9aebd77287" + integrity sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ== + dependencies: + bl "^4.0.3" + end-of-stream "^1.4.1" + fs-constants "^1.0.0" + inherits "^2.0.3" + readable-stream "^3.1.1" + +text-table@^0.2.0: + version "0.2.0" + resolved "https://registry.yarnpkg.com/text-table/-/text-table-0.2.0.tgz#7f5ee823ae805207c00af2df4a84ec3fcfa570b4" + integrity sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw== + +"through@>=2.2.7 <3": + version "2.3.8" + resolved "https://registry.yarnpkg.com/through/-/through-2.3.8.tgz#0dd4c9ffaabc357960b1b724115d7e0e86a2e1f5" + integrity sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg== + +tmp@0.0.33: + version "0.0.33" + resolved "https://registry.yarnpkg.com/tmp/-/tmp-0.0.33.tgz#6d34335889768d21b2bcda0aa277ced3b1bfadf9" + integrity sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw== + dependencies: + os-tmpdir "~1.0.2" + +to-buffer@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/to-buffer/-/to-buffer-1.1.1.tgz#493bd48f62d7c43fcded313a03dcadb2e1213a80" + integrity sha512-lx9B5iv7msuFYE3dytT+KE5tap+rNYw+K4jVkb9R/asAb+pbBSM17jtunHplhBe6RRJdZx3Pn2Jph24O32mOVg== + +to-regex-range@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/to-regex-range/-/to-regex-range-5.0.1.tgz#1648c44aae7c8d988a326018ed72f5b4dd0392e4" + integrity sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ== + dependencies: + is-number "^7.0.0" + +toidentifier@1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/toidentifier/-/toidentifier-1.0.1.tgz#3be34321a88a820ed1bd80dfaa33e479fbb8dd35" + integrity sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA== + +tr46@~0.0.3: + version "0.0.3" + resolved "https://registry.yarnpkg.com/tr46/-/tr46-0.0.3.tgz#8184fd347dac9cdc185992f3a6622e14b9d9ab6a" + integrity sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw== + +ts-api-utils@^1.0.1: + version "1.0.3" + resolved "https://registry.yarnpkg.com/ts-api-utils/-/ts-api-utils-1.0.3.tgz#f12c1c781d04427313dbac808f453f050e54a331" + integrity sha512-wNMeqtMz5NtwpT/UZGY5alT+VoKdSsOOP/kqHFcUW1P/VRhH2wJ48+DN2WwUliNbQ976ETwDL0Ifd2VVvgonvg== + +ts-morph@^19.0.0: + version "19.0.0" + resolved "https://registry.yarnpkg.com/ts-morph/-/ts-morph-19.0.0.tgz#43e95fb0156c3fe3c77c814ac26b7d0be2f93169" + integrity sha512-D6qcpiJdn46tUqV45vr5UGM2dnIEuTGNxVhg0sk5NX11orcouwj6i1bMqZIz2mZTZB1Hcgy7C3oEVhAT+f6mbQ== + dependencies: + "@ts-morph/common" "~0.20.0" + code-block-writer "^12.0.0" + +ts-node@^10.9.1: + version "10.9.1" + resolved "https://registry.yarnpkg.com/ts-node/-/ts-node-10.9.1.tgz#e73de9102958af9e1f0b168a6ff320e25adcff4b" + integrity sha512-NtVysVPkxxrwFGUUxGYhfux8k78pQB3JqYBXlLRZgdGUqTO5wU/UyHop5p70iEbGhB7q5KmiZiU0Y3KlJrScEw== + dependencies: + "@cspotcode/source-map-support" "^0.8.0" + "@tsconfig/node10" "^1.0.7" + "@tsconfig/node12" "^1.0.7" + "@tsconfig/node14" "^1.0.0" + "@tsconfig/node16" "^1.0.2" + acorn "^8.4.1" + acorn-walk "^8.1.1" + arg "^4.1.0" + create-require "^1.1.0" + diff "^4.0.1" + make-error "^1.1.1" + v8-compile-cache-lib "^3.0.1" + yn "3.1.1" + +tsconfig-paths@^3.14.2: + version "3.14.2" + resolved "https://registry.yarnpkg.com/tsconfig-paths/-/tsconfig-paths-3.14.2.tgz#6e32f1f79412decd261f92d633a9dc1cfa99f088" + integrity sha512-o/9iXgCYc5L/JxCHPe3Hvh8Q/2xm5Z+p18PESBU6Ff33695QnCHBEjcytY2q19ua7Mbl/DavtBOLq+oG0RCL+g== + dependencies: + "@types/json5" "^0.0.29" + json5 "^1.0.2" + minimist "^1.2.6" + strip-bom "^3.0.0" + +tslib@^1.8.1, tslib@^1.9.3: + version "1.14.1" + resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.14.1.tgz#cf2d38bdc34a134bcaf1091c41f6619e2f672d00" + integrity sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg== + +tsort@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/tsort/-/tsort-0.0.1.tgz#e2280f5e817f8bf4275657fd0f9aebd44f5a2786" + integrity sha512-Tyrf5mxF8Ofs1tNoxA13lFeZ2Zrbd6cKbuH3V+MQ5sb6DtBj5FjrXVsRWT8YvNAQTqNoz66dz1WsbigI22aEnw== + +tsutils@^3.21.0: + version "3.21.0" + resolved "https://registry.yarnpkg.com/tsutils/-/tsutils-3.21.0.tgz#b48717d394cea6c1e096983eed58e9d61715b623" + integrity sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA== + dependencies: + tslib "^1.8.1" + +tweetnacl-util@^0.15.1: + version "0.15.1" + resolved "https://registry.yarnpkg.com/tweetnacl-util/-/tweetnacl-util-0.15.1.tgz#b80fcdb5c97bcc508be18c44a4be50f022eea00b" + integrity sha512-RKJBIj8lySrShN4w6i/BonWp2Z/uxwC3h4y7xsRrpP59ZboCd0GpEVsOnMDYLMmKBpYhb5TgHzZXy7wTfYFBRw== + +tweetnacl@^0.14.3: + version "0.14.5" + resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-0.14.5.tgz#5ae68177f192d4456269d108afa93ff8743f4f64" + integrity sha512-KXXFFdAbFXY4geFIwoyNK+f5Z1b7swfXABfL7HXCmoIWMKU3dmS26672A4EeQtDzLKy7SXmfBu51JolvEKwtGA== + +tweetnacl@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-1.0.3.tgz#ac0af71680458d8a6378d0d0d050ab1407d35596" + integrity sha512-6rt+RN7aOi1nGMyC4Xa5DdYiukl2UWCbcJft7YhxReBGQD7OAM8Pbxw6YMo4r2diNEA8FEmu32YOn9rhaiE5yw== + +type-check@^0.4.0, type-check@~0.4.0: + version "0.4.0" + resolved "https://registry.yarnpkg.com/type-check/-/type-check-0.4.0.tgz#07b8203bfa7056c0657050e3ccd2c37730bab8f1" + integrity sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew== + dependencies: + prelude-ls "^1.2.1" + +type-detect@^4.0.0, type-detect@^4.0.8: + version "4.0.8" + resolved "https://registry.yarnpkg.com/type-detect/-/type-detect-4.0.8.tgz#7646fb5f18871cfbb7749e69bd39a6388eb7450c" + integrity sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g== + +type-fest@^0.20.2: + version "0.20.2" + resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.20.2.tgz#1bf207f4b28f91583666cb5fbd327887301cd5f4" + integrity sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ== + +type-fest@^0.21.3: + version "0.21.3" + resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.21.3.tgz#d260a24b0198436e133fa26a524a6d65fa3b2e37" + integrity sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w== + +type-fest@^0.7.1: + version "0.7.1" + resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.7.1.tgz#8dda65feaf03ed78f0a3f9678f1869147f7c5c48" + integrity sha512-Ne2YiiGN8bmrmJJEuTWTLJR32nh/JdL1+PSicowtNb0WFpn59GK8/lfD61bVtzguz7b3PBt74nxpv/Pw5po5Rg== + +typed-array-buffer@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/typed-array-buffer/-/typed-array-buffer-1.0.0.tgz#18de3e7ed7974b0a729d3feecb94338d1472cd60" + integrity sha512-Y8KTSIglk9OZEr8zywiIHG/kmQ7KWyjseXs1CbSo8vC42w7hg2HgYTxSWwP0+is7bWDc1H+Fo026CpHFwm8tkw== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.2.1" + is-typed-array "^1.1.10" + +typed-array-byte-length@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/typed-array-byte-length/-/typed-array-byte-length-1.0.0.tgz#d787a24a995711611fb2b87a4052799517b230d0" + integrity sha512-Or/+kvLxNpeQ9DtSydonMxCx+9ZXOswtwJn17SNLvhptaXYDJvkFFP5zbfU/uLmvnBJlI4yrnXRxpdWH/M5tNA== + dependencies: + call-bind "^1.0.2" + for-each "^0.3.3" + has-proto "^1.0.1" + is-typed-array "^1.1.10" + +typed-array-byte-offset@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/typed-array-byte-offset/-/typed-array-byte-offset-1.0.0.tgz#cbbe89b51fdef9cd6aaf07ad4707340abbc4ea0b" + integrity sha512-RD97prjEt9EL8YgAgpOkf3O4IF9lhJFr9g0htQkm0rchFp/Vx7LW5Q8fSXXub7BXAODyUQohRMyOc3faCPd0hg== + dependencies: + available-typed-arrays "^1.0.5" + call-bind "^1.0.2" + for-each "^0.3.3" + has-proto "^1.0.1" + is-typed-array "^1.1.10" + +typed-array-length@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/typed-array-length/-/typed-array-length-1.0.4.tgz#89d83785e5c4098bec72e08b319651f0eac9c1bb" + integrity sha512-KjZypGq+I/H7HI5HlOoGHkWUUGq+Q0TPhQurLbyrVrvnKTBgzLhIJ7j6J/XTQOi0d1RjyZ0wdas8bKs2p0x3Ng== + dependencies: + call-bind "^1.0.2" + for-each "^0.3.3" + is-typed-array "^1.1.9" + +typedarray@^0.0.6: + version "0.0.6" + resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777" + integrity sha512-/aCDEGatGvZ2BIk+HmLf4ifCJFwvKFNb9/JeZPMulfgFracn9QFcAf5GO8B/mweUjSoblS5In0cWhqpfs/5PQA== + +typescript@^4.9.4: + version "4.9.5" + resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.9.5.tgz#095979f9bcc0d09da324d58d03ce8f8374cbe65a" + integrity sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g== + +unbox-primitive@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/unbox-primitive/-/unbox-primitive-1.0.2.tgz#29032021057d5e6cdbd08c5129c226dff8ed6f9e" + integrity sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw== + dependencies: + call-bind "^1.0.2" + has-bigints "^1.0.2" + has-symbols "^1.0.3" + which-boxed-primitive "^1.0.2" + +undici-types@~5.25.1: + version "5.25.3" + resolved "https://registry.yarnpkg.com/undici-types/-/undici-types-5.25.3.tgz#e044115914c85f0bcbb229f346ab739f064998c3" + integrity sha512-Ga1jfYwRn7+cP9v8auvEXN1rX3sWqlayd4HP7OKk4mZWylEmu3KzXDUGrQUN6Ol7qo1gPvB2e5gX6udnyEPgdA== + +undici@^5.14.0: + version "5.26.3" + resolved "https://registry.yarnpkg.com/undici/-/undici-5.26.3.tgz#ab3527b3d5bb25b12f898dfd22165d472dd71b79" + integrity sha512-H7n2zmKEWgOllKkIUkLvFmsJQj062lSm3uA4EYApG8gLuiOM0/go9bIoC3HVaSnfg4xunowDE2i9p8drkXuvDw== + dependencies: + "@fastify/busboy" "^2.0.0" + +universalify@^0.1.0: + version "0.1.2" + resolved "https://registry.yarnpkg.com/universalify/-/universalify-0.1.2.tgz#b646f69be3942dabcecc9d6639c80dc105efaa66" + integrity sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg== + +universalify@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/universalify/-/universalify-2.0.0.tgz#75a4984efedc4b08975c5aeb73f530d02df25717" + integrity sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ== + +unpipe@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/unpipe/-/unpipe-1.0.0.tgz#b2bf4ee8514aae6165b4817829d21b2ef49904ec" + integrity sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ== + +uri-js@^4.2.2: + version "4.4.1" + resolved "https://registry.yarnpkg.com/uri-js/-/uri-js-4.4.1.tgz#9b1a52595225859e55f669d928f88c6c57f2a77e" + integrity sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg== + dependencies: + punycode "^2.1.0" + +util-deprecate@^1.0.1, util-deprecate@^1.0.2, util-deprecate@~1.0.1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" + integrity sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw== + +uuid@^8.3.2: + version "8.3.2" + resolved "https://registry.yarnpkg.com/uuid/-/uuid-8.3.2.tgz#80d5b5ced271bb9af6c445f21a1a04c606cefbe2" + integrity sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg== + +v8-compile-cache-lib@^3.0.1: + version "3.0.1" + resolved "https://registry.yarnpkg.com/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz#6336e8d71965cb3d35a1bbb7868445a7c05264bf" + integrity sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg== + +vue-eslint-parser@^8.0.0, vue-eslint-parser@^8.0.1: + version "8.3.0" + resolved "https://registry.yarnpkg.com/vue-eslint-parser/-/vue-eslint-parser-8.3.0.tgz#5d31129a1b3dd89c0069ca0a1c88f970c360bd0d" + integrity sha512-dzHGG3+sYwSf6zFBa0Gi9ZDshD7+ad14DGOdTLjruRVgZXe2J+DcZ9iUhyR48z5g1PqRa20yt3Njna/veLJL/g== + dependencies: + debug "^4.3.2" + eslint-scope "^7.0.0" + eslint-visitor-keys "^3.1.0" + espree "^9.0.0" + esquery "^1.4.0" + lodash "^4.17.21" + semver "^7.3.5" + +webidl-conversions@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/webidl-conversions/-/webidl-conversions-3.0.1.tgz#24534275e2a7bc6be7bc86611cc16ae0a5654871" + integrity sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ== + +whatwg-url@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/whatwg-url/-/whatwg-url-5.0.0.tgz#966454e8765462e37644d3626f6742ce8b70965d" + integrity sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw== + dependencies: + tr46 "~0.0.3" + webidl-conversions "^3.0.0" + +which-boxed-primitive@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/which-boxed-primitive/-/which-boxed-primitive-1.0.2.tgz#13757bc89b209b049fe5d86430e21cf40a89a8e6" + integrity sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg== + dependencies: + is-bigint "^1.0.1" + is-boolean-object "^1.1.0" + is-number-object "^1.0.4" + is-string "^1.0.5" + is-symbol "^1.0.3" + +which-typed-array@^1.1.11: + version "1.1.11" + resolved "https://registry.yarnpkg.com/which-typed-array/-/which-typed-array-1.1.11.tgz#99d691f23c72aab6768680805a271b69761ed61a" + integrity sha512-qe9UWWpkeG5yzZ0tNYxDmd7vo58HDBc39mZ0xWWpolAGADdFOzkfamWLDxkOWcvHQKVmdTyQdLD4NOfjLWTKew== + dependencies: + available-typed-arrays "^1.0.5" + call-bind "^1.0.2" + for-each "^0.3.3" + gopd "^1.0.1" + has-tostringtag "^1.0.0" + +which@^2.0.1: + version "2.0.2" + resolved "https://registry.yarnpkg.com/which/-/which-2.0.2.tgz#7c6a8dd0a636a0327e10b59c9286eee93f3f51b1" + integrity sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA== + dependencies: + isexe "^2.0.0" + +workerpool@6.2.1: + version "6.2.1" + resolved "https://registry.yarnpkg.com/workerpool/-/workerpool-6.2.1.tgz#46fc150c17d826b86a008e5a4508656777e9c343" + integrity sha512-ILEIE97kDZvF9Wb9f6h5aXK4swSlKGUcOEGiIYb2OOu/IrDU9iwj0fD//SsA6E5ibwJxpEvhullJY4Sl4GcpAw== + +wrap-ansi@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43" + integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q== + dependencies: + ansi-styles "^4.0.0" + string-width "^4.1.0" + strip-ansi "^6.0.0" + +wrappy@1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" + integrity sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ== + +ws@7.4.6: + version "7.4.6" + resolved "https://registry.yarnpkg.com/ws/-/ws-7.4.6.tgz#5654ca8ecdeee47c33a9a4bf6d28e2be2980377c" + integrity sha512-YmhHDO4MzaDLB+M9ym/mDA5z0naX8j7SIlT8f8z+I0VtzsRbekxEutHSme7NPS2qE8StCYQNUnfWdXta/Yu85A== + +ws@^7.4.6: + version "7.5.9" + resolved "https://registry.yarnpkg.com/ws/-/ws-7.5.9.tgz#54fa7db29f4c7cec68b1ddd3a89de099942bb591" + integrity sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q== + +xtend@^4.0.0: + version "4.0.2" + resolved "https://registry.yarnpkg.com/xtend/-/xtend-4.0.2.tgz#bb72779f5fa465186b1f438f674fa347fdb5db54" + integrity sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ== + +y18n@^5.0.5: + version "5.0.8" + resolved "https://registry.yarnpkg.com/y18n/-/y18n-5.0.8.tgz#7f4934d0f7ca8c56f95314939ddcd2dd91ce1d55" + integrity sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA== + +yallist@^3.0.2: + version "3.1.1" + resolved "https://registry.yarnpkg.com/yallist/-/yallist-3.1.1.tgz#dbb7daf9bfd8bac9ab45ebf602b8cbad0d5d08fd" + integrity sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g== + +yallist@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/yallist/-/yallist-4.0.0.tgz#9bb92790d9c0effec63be73519e11a35019a3a72" + integrity sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A== + +yargs-parser@20.2.4: + version "20.2.4" + resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.4.tgz#b42890f14566796f85ae8e3a25290d205f154a54" + integrity sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA== + +yargs-parser@^20.2.2: + version "20.2.9" + resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.9.tgz#2eb7dc3b0289718fc295f362753845c41a0c94ee" + integrity sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w== + +yargs-unparser@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/yargs-unparser/-/yargs-unparser-2.0.0.tgz#f131f9226911ae5d9ad38c432fe809366c2325eb" + integrity sha512-7pRTIA9Qc1caZ0bZ6RYRGbHJthJWuakf+WmHK0rVeLkNrrGhfoabBNdue6kdINI6r4if7ocq9aD/n7xwKOdzOA== + dependencies: + camelcase "^6.0.0" + decamelize "^4.0.0" + flat "^5.0.2" + is-plain-obj "^2.1.0" + +yargs@16.2.0: + version "16.2.0" + resolved "https://registry.yarnpkg.com/yargs/-/yargs-16.2.0.tgz#1c82bf0f6b6a66eafce7ef30e376f49a12477f66" + integrity sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw== + dependencies: + cliui "^7.0.2" + escalade "^3.1.1" + get-caller-file "^2.0.5" + require-directory "^2.1.1" + string-width "^4.2.0" + y18n "^5.0.5" + yargs-parser "^20.2.2" + +yn@3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/yn/-/yn-3.1.1.tgz#1e87401a09d767c1d5eab26a6e4c185182d2eb50" + integrity sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q== + +yocto-queue@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-0.1.0.tgz#0294eb3dee05028d31ee1a5fa2c556a6aaf10a1b" + integrity sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q== + +zksync-web3@^0.14.3: + version "0.14.3" + resolved "https://registry.yarnpkg.com/zksync-web3/-/zksync-web3-0.14.3.tgz#64ac2a16d597464c3fc4ae07447a8007631c57c9" + integrity sha512-hT72th4AnqyLW1d5Jlv8N2B/qhEnl2NePK2A3org7tAa24niem/UAaHMkEvmWI3SF9waYUPtqAtjpf+yvQ9zvQ== diff --git a/.test-node-subtree/etc/system-contracts/SystemConfig.json b/.test-node-subtree/etc/system-contracts/SystemConfig.json new file mode 100644 index 00000000..827e11b5 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/SystemConfig.json @@ -0,0 +1,17 @@ +{ + "GUARANTEED_PUBDATA_BYTES": 4000, + "MAX_PUBDATA_PER_BATCH": 110000, + "MAX_TRANSACTIONS_IN_BATCH": 1024, + "BATCH_OVERHEAD_L2_GAS": 1200000, + "BATCH_OVERHEAD_L1_GAS": 1000000, + "L2_TX_INTRINSIC_GAS": 14070, + "L2_TX_INTRINSIC_PUBDATA": 0, + "L1_TX_INTRINSIC_L2_GAS": 167157, + "L1_TX_INTRINSIC_PUBDATA": 88, + "MAX_GAS_PER_TRANSACTION": 80000000, + "BOOTLOADER_MEMORY_FOR_TXS": 8740224, + "REFUND_GAS": 7343, + "KECCAK_ROUND_COST_GAS": 40, + "SHA256_ROUND_COST_GAS": 7, + "ECRECOVER_COST_GAS": 1112 +} diff --git a/.test-node-subtree/etc/system-contracts/VERSION.md b/.test-node-subtree/etc/system-contracts/VERSION.md new file mode 100644 index 00000000..675b64d7 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/VERSION.md @@ -0,0 +1,25 @@ +This directory was copied from https://github.com/matter-labs/era-system-contracts. + +The current commit: `a00ab9a11643f3a918ed95cdf8a04edff5499d92`. + +The following directories/files were copied: +- [bootloader](bootloader) +- [contracts](contracts) +- [scripts](scripts) +- [hardhat.config.ts](hardhat.config.ts) +- [package.json](package.json) +- [SystemConfig.json](SystemConfig.json) +- [yarn.lock](yarn.lock) + +The next changes were introduced: +- [bootloader.yul](bootloader/bootloader.yul) + - Debug data, marked as `DEBUG SUPPORT` blocks. + - Impersonating preprocessing mode, blocks `` and at some places added `` condition. +- [process.ts](scripts/process.ts) + - Impersonating preprocessing mode, "For impersonating" blocks. +- [DefaultAccount.sol](contracts/DefaultAccount.sol) + - Return transaction data (empty), marked as `FOUNDRY SUPPORT` blocks. +- [DefaultAccountNoSecurity.sol](contracts/DefaultAccountNoSecurity.sol) + - NEW smart contract, only for Hardhat/Forge testing. +- [IAccount.sol](contracts/interfaces/IAccount.sol) + - Return transaction data (empty), marked as `FOUNDRY SUPPORT` blocks. diff --git a/.test-node-subtree/etc/system-contracts/bootloader/bootloader.yul b/.test-node-subtree/etc/system-contracts/bootloader/bootloader.yul new file mode 100644 index 00000000..dd115490 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/bootloader.yul @@ -0,0 +1,4080 @@ +object "Bootloader" { + code { + } + object "Bootloader_deployed" { + code { + {{CODE_START_PLACEHOLDER}} + + //////////////////////////////////////////////////////////////////////////// + // Function Declarations + //////////////////////////////////////////////////////////////////////////// + + // While we definitely cannot control the gas price on L1, + // we need to check the operator does not provide any absurd numbers there + function MAX_ALLOWED_L1_GAS_PRICE() -> ret { + // 100k gwei + ret := 100000000000000 + } + + function MAX_ALLOWED_FAIR_L2_GAS_PRICE() -> ret { + // 10k gwei + ret := 10000000000000 + } + + /// @dev This method ensures that the prices provided by the operator + /// are not absurdly high + function validateOperatorProvidedPrices(l1GasPrice, fairL2GasPrice) { + if gt(l1GasPrice, MAX_ALLOWED_L1_GAS_PRICE()) { + assertionError("L1 gas price too high") + } + + if gt(fairL2GasPrice, MAX_ALLOWED_FAIR_L2_GAS_PRICE()) { + assertionError("L2 fair gas price too high") + } + } + + /// @dev Returns the baseFee for this batch based on the + /// L1 gas price and the fair L2 gas price. + function getBaseFee(l1GasPrice, fairL2GasPrice) -> baseFee, gasPricePerPubdata { + // By default, we want to provide the fair L2 gas price. + // That it means that the operator controls + // what the value of the baseFee will be. In the future, + // a better system, aided by EIP1559 should be added. + + let pubdataBytePriceETH := safeMul(l1GasPrice, L1_GAS_PER_PUBDATA_BYTE(), "aoa") + + baseFee := max( + fairL2GasPrice, + ceilDiv(pubdataBytePriceETH, MAX_L2_GAS_PER_PUBDATA()) + ) + gasPricePerPubdata := ceilDiv(pubdataBytePriceETH, baseFee) + } + + /// @dev It should be always possible to submit a transaction + /// that consumes such amount of public data. + function GUARANTEED_PUBDATA_PER_TX() -> ret { + ret := {{GUARANTEED_PUBDATA_BYTES}} + } + + /// @dev The maximal gasPerPubdata, which allows users to still be + /// able to send `GUARANTEED_PUBDATA_PER_TX` onchain. + function MAX_L2_GAS_PER_PUBDATA() -> ret { + ret := div(MAX_GAS_PER_TRANSACTION(), GUARANTEED_PUBDATA_PER_TX()) + } + + /// @dev The computational overhead for a batch. + /// It includes the combined price for 1 instance of all the circuits + /// (since they might be partially filled), the price for running + /// the common parts of the bootloader as well as general maintainance of the system. + function BATCH_OVERHEAD_L2_GAS() -> ret { + ret := {{BATCH_OVERHEAD_L2_GAS}} + } + + /// @dev The overhead for the interaction with L1. + /// It should cover proof verification as well as other minor + /// overheads for committing/executing a transaction in a batch. + function BATCH_OVERHEAD_L1_GAS() -> ret { + ret := {{BATCH_OVERHEAD_L1_GAS}} + } + + /// @dev The maximal number of gas available to the transaction + function MAX_GAS_PER_TRANSACTION() -> ret { + ret := {{MAX_GAS_PER_TRANSACTION}} + } + + /// @dev The number of L1 gas needed to be spent for + /// L1 byte. While a single pubdata byte costs `16` gas, + /// we demand at least 17 to cover up for the costs of additional + /// hashing of it, etc. + function L1_GAS_PER_PUBDATA_BYTE() -> ret { + ret := 17 + } + + /// @dev The size of the bootloader memory that is to spent by the transaction's + /// encodings. + function BOOTLOADER_MEMORY_FOR_TXS() -> ret { + ret := {{BOOTLOADER_MEMORY_FOR_TXS}} + } + + /// @dev Whether the batch is allowed to accept transactions with + /// gasPerPubdataByteLimit = 0. On mainnet, this is forbidden for safety reasons. + function FORBID_ZERO_GAS_PER_PUBDATA() -> ret { + ret := {{FORBID_ZERO_GAS_PER_PUBDATA}} + } + + /// @dev The maximum number of transactions per L1 batch. + function MAX_TRANSACTIONS_IN_BATCH() -> ret { + ret := {{MAX_TRANSACTIONS_IN_BATCH}} + } + + /// @dev The slot from which the scratch space starts. + /// Scatch space is used for various temporary values + function SCRATCH_SPACE_BEGIN_SLOT() -> ret { + ret := 8 + } + + /// @dev The byte from which the scratch space starts. + /// Scratch space is used for various temporary values + function SCRATCH_SPACE_BEGIN_BYTE() -> ret { + ret := mul(SCRATCH_SPACE_BEGIN_SLOT(), 32) + } + + /// @dev The first 32 slots are reserved for event emitting for the + /// debugging purposes + function SCRATCH_SPACE_SLOTS() -> ret { + ret := 32 + } + + /// @dev Slots reserved for saving the paymaster context + /// @dev The paymasters are allowed to consume at most + /// 32 slots (1024 bytes) for their context. + /// The 33 slots are required since the first one stores the length of the calldata. + function PAYMASTER_CONTEXT_SLOTS() -> ret { + ret := 33 + } + + /// @dev Bytes reserved for saving the paymaster context + function PAYMASTER_CONTEXT_BYTES() -> ret { + ret := mul(PAYMASTER_CONTEXT_SLOTS(), 32) + } + + /// @dev Slot from which the paymaster context starts + function PAYMASTER_CONTEXT_BEGIN_SLOT() -> ret { + ret := add(SCRATCH_SPACE_BEGIN_SLOT(), SCRATCH_SPACE_SLOTS()) + } + + /// @dev The byte from which the paymaster context starts + function PAYMASTER_CONTEXT_BEGIN_BYTE() -> ret { + ret := mul(PAYMASTER_CONTEXT_BEGIN_SLOT(), 32) + } + + /// @dev Each tx must have at least this amount of unused bytes before them to be able to + /// encode the postOp operation correctly. + function MAX_POSTOP_SLOTS() -> ret { + // Before the actual transaction encoding, the postOp contains 6 slots: + // 1. Context offset + // 2. Transaction offset + // 3. Transaction hash + // 4. Suggested signed hash + // 5. Transaction result + // 6. Maximum refunded gas + // And one more slot for the padding selector + ret := add(PAYMASTER_CONTEXT_SLOTS(), 7) + } + + /// @dev Slots needed to store the canonical and signed hash for the current L2 transaction. + function CURRENT_L2_TX_HASHES_RESERVED_SLOTS() -> ret { + ret := 2 + } + + /// @dev Slot from which storing of the current canonical and signed hashes begins + function CURRENT_L2_TX_HASHES_BEGIN_SLOT() -> ret { + ret := add(PAYMASTER_CONTEXT_BEGIN_SLOT(), PAYMASTER_CONTEXT_SLOTS()) + } + + /// @dev The byte from which storing of the current canonical and signed hashes begins + function CURRENT_L2_TX_HASHES_BEGIN_BYTE() -> ret { + ret := mul(CURRENT_L2_TX_HASHES_BEGIN_SLOT(), 32) + } + + /// @dev The maximum number of new factory deps that are allowed in a transaction + function MAX_NEW_FACTORY_DEPS() -> ret { + ret := 32 + } + + /// @dev Besides the factory deps themselves, we also need another 4 slots for: + /// selector, marker of whether the user should pay for the pubdata, + /// the offset for the encoding of the array as well as the length of the array. + function NEW_FACTORY_DEPS_RESERVED_SLOTS() -> ret { + ret := add(MAX_NEW_FACTORY_DEPS(), 4) + } + + /// @dev The slot starting from which the factory dependencies are stored + function NEW_FACTORY_DEPS_BEGIN_SLOT() -> ret { + ret := add(CURRENT_L2_TX_HASHES_BEGIN_SLOT(), CURRENT_L2_TX_HASHES_RESERVED_SLOTS()) + } + + /// @dev The byte starting from which the factory dependencies are stored + function NEW_FACTORY_DEPS_BEGIN_BYTE() -> ret { + ret := mul(NEW_FACTORY_DEPS_BEGIN_SLOT(), 32) + } + + /// @dev The slot starting from which the refunds provided by the operator are stored + function TX_OPERATOR_REFUND_BEGIN_SLOT() -> ret { + ret := add(NEW_FACTORY_DEPS_BEGIN_SLOT(), NEW_FACTORY_DEPS_RESERVED_SLOTS()) + } + + /// @dev The byte starting from which the refunds provided by the operator are stored + function TX_OPERATOR_REFUND_BEGIN_BYTE() -> ret { + ret := mul(TX_OPERATOR_REFUND_BEGIN_SLOT(), 32) + } + + /// @dev The number of slots dedicated for the refunds for the transactions. + /// It is equal to the number of transactions in the batch. + function TX_OPERATOR_REFUNDS_SLOTS() -> ret { + ret := MAX_TRANSACTIONS_IN_BATCH() + } + + /// @dev The slot starting from which the overheads proposed by the operator will be stored + function TX_SUGGESTED_OVERHEAD_BEGIN_SLOT() -> ret { + ret := add(TX_OPERATOR_REFUND_BEGIN_SLOT(), TX_OPERATOR_REFUNDS_SLOTS()) + } + + /// @dev The byte starting from which the overheads proposed by the operator will be stored + function TX_SUGGESTED_OVERHEAD_BEGIN_BYTE() -> ret { + ret := mul(TX_SUGGESTED_OVERHEAD_BEGIN_SLOT(), 32) + } + + /// @dev The number of slots dedicated for the overheads for the transactions. + /// It is equal to the number of transactions in the batch. + function TX_SUGGESTED_OVERHEAD_SLOTS() -> ret { + ret := MAX_TRANSACTIONS_IN_BATCH() + } + + /// @dev The slot starting from which the maximum number of gas that the operator "trusts" + /// the transaction to use for its execution is stored. Sometimes, the operator may know that + /// a certain transaction can be allowed more gas that what the protocol-level worst-case allows. + function TX_OPERATOR_TRUSTED_GAS_LIMIT_BEGIN_SLOT() -> ret { + ret := add(TX_SUGGESTED_OVERHEAD_BEGIN_SLOT(), TX_SUGGESTED_OVERHEAD_SLOTS()) + } + + /// @dev byte starting from which the maximum number of gas that the operator "trusts" + /// the transaction to use for its execution is stored. + function TX_OPERATOR_TRUSTED_GAS_LIMIT_BEGIN_BYTE() -> ret { + ret := mul(TX_OPERATOR_TRUSTED_GAS_LIMIT_BEGIN_SLOT(), 32) + } + + /// @dev The number of slots dedicated for the trusted gas limits for the transactions. + /// It is equal to the number of transactions in the batch. + function TX_OPERATOR_TRUSTED_GAS_LIMIT_SLOTS() -> ret { + ret := MAX_TRANSACTIONS_IN_BATCH() + } + + /// @dev The slot starting from the L2 block information for transactions is stored. + function TX_OPERATOR_L2_BLOCK_INFO_BEGIN_SLOT() -> ret { + ret := add(TX_OPERATOR_TRUSTED_GAS_LIMIT_BEGIN_SLOT(), TX_OPERATOR_TRUSTED_GAS_LIMIT_SLOTS()) + } + + /// @dev The byte starting from which the L2 block information for transactions is stored. + function TX_OPERATOR_L2_BLOCK_INFO_BEGIN_BYTE() -> ret { + ret := mul(TX_OPERATOR_L2_BLOCK_INFO_BEGIN_SLOT(), 32) + } + + /// @dev The size of each of the L2 block information. Each L2 block information contains four fields: + /// - number of the block + /// - timestamp of the block + /// - hash of the previous block + /// - the maximal number of virtual blocks to create + function TX_OPERATOR_L2_BLOCK_INFO_SLOT_SIZE() -> ret { + ret := 4 + } + + /// @dev The size of each of the L2 block information in bytes. + function TX_OPERATOR_L2_BLOCK_INFO_SIZE_BYTES() -> ret { + ret := mul(TX_OPERATOR_L2_BLOCK_INFO_SLOT_SIZE(), 32) + } + + /// @dev The number of slots dedicated for the L2 block information for the transactions. + /// Note, that an additional slot is required for the fictive L2 block at the end of the batch. + /// For technical reasons inside the sequencer implementation, + /// each batch ends with a fictive block with no transactions. + function TX_OPERATOR_L2_BLOCK_INFO_SLOTS() -> ret { + ret := mul(add(MAX_TRANSACTIONS_IN_BATCH(), 1), TX_OPERATOR_L2_BLOCK_INFO_SLOT_SIZE()) + } + + /// @dev The slot starting from which the compressed bytecodes are located in the bootloader's memory. + /// Each compressed bytecode is provided in the following format: + /// - 32 byte formatted bytecode hash + /// - 32 byte of zero (it will be replaced within the code with left-padded selector of the `publishCompressedBytecode`). + /// - ABI-encoding of the parameters of the `publishCompressedBytecode` method. + /// + /// At the slot `TX_OPERATOR_TRUSTED_GAS_LIMIT_BEGIN_SLOT()` the pointer to the currently processed compressed bytecode + /// is stored, i.e. this pointer will be increased once the current bytecode which the pointer points to is published. + /// At the start of the bootloader, the value stored at the `TX_OPERATOR_TRUSTED_GAS_LIMIT_BEGIN_SLOT` is equal to + /// `TX_OPERATOR_TRUSTED_GAS_LIMIT_BEGIN_SLOT + 32`, where the hash of the first compressed bytecode to publish should be stored. + function COMPRESSED_BYTECODES_BEGIN_SLOT() -> ret { + ret := add(TX_OPERATOR_L2_BLOCK_INFO_BEGIN_SLOT(), TX_OPERATOR_L2_BLOCK_INFO_SLOTS()) + } + + /// @dev The byte starting from which the compressed bytecodes are located in the bootloader's memory. + function COMPRESSED_BYTECODES_BEGIN_BYTE() -> ret { + ret := mul(COMPRESSED_BYTECODES_BEGIN_SLOT(), 32) + } + + /// @dev The number of slots dedicated to the compressed bytecodes. + function COMPRESSED_BYTECODES_SLOTS() -> ret { + ret := {{COMPRESSED_BYTECODES_SLOTS}} + } + + /// @dev The slot right after the last slot of the compressed bytecodes memory area. + function COMPRESSED_BYTECODES_END_SLOT() -> ret { + ret := add(COMPRESSED_BYTECODES_BEGIN_SLOT(), COMPRESSED_BYTECODES_SLOTS()) + } + + /// @dev The first byte in memory right after the compressed bytecodes memory area. + function COMPRESSED_BYTECODES_END_BYTE() -> ret { + ret := mul(COMPRESSED_BYTECODES_END_SLOT(), 32) + } + + /// @dev Slots needed to store priority txs L1 data (`chainedPriorityTxsHash` and `numberOfLayer1Txs`). + function PRIORITY_TXS_L1_DATA_RESERVED_SLOTS() -> ret { + ret := 2 + } + + /// @dev Slot from which storing of the priority txs L1 data begins. + function PRIORITY_TXS_L1_DATA_BEGIN_SLOT() -> ret { + ret := add(COMPRESSED_BYTECODES_BEGIN_SLOT(), COMPRESSED_BYTECODES_SLOTS()) + } + + /// @dev The byte from which storing of the priority txs L1 data begins. + function PRIORITY_TXS_L1_DATA_BEGIN_BYTE() -> ret { + ret := mul(PRIORITY_TXS_L1_DATA_BEGIN_SLOT(), 32) + } + + /// @dev Slot from which storing of the L1 Messenger pubdata begins. + function OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_BEGIN_SLOT() -> ret { + ret := add(PRIORITY_TXS_L1_DATA_BEGIN_SLOT(), PRIORITY_TXS_L1_DATA_RESERVED_SLOTS()) + } + + /// @dev The byte storing of the L1 Messenger pubdata begins. + function OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_BEGIN_BYTE() -> ret { + ret := mul(OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_BEGIN_SLOT(), 32) + } + + /// @dev Slots needed to store L1 Messenger pubdata. + /// @dev Note that are many more these than the maximal pubdata in batch, since + /// it needs to also accomodate uncompressed state diffs that are required for the state diff + /// compression verification. + function OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_SLOTS() -> ret { + ret := {{OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_SLOTS}} + } + + /// @dev The slot right after the last slot of the L1 Messenger pubdata memory area. + function OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_END_SLOT() -> ret { + ret := add(OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_BEGIN_SLOT(), OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_SLOTS()) + } + + /// @dev The slot from which the bootloader transactions' descriptions begin + function TX_DESCRIPTION_BEGIN_SLOT() -> ret { + ret := OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_END_SLOT() + } + + /// @dev The byte from which the bootloader transactions' descriptions begin + function TX_DESCRIPTION_BEGIN_BYTE() -> ret { + ret := mul(TX_DESCRIPTION_BEGIN_SLOT(), 32) + } + + // Each tx description has the following structure + // + // struct BootloaderTxDescription { + // uint256 txMeta; + // uint256 txDataOffset; + // } + // + // `txMeta` contains flags to manipulate the transaction execution flow. + // For playground batches: + // It can have the following information (0 byte is LSB and 31 byte is MSB): + // 0 byte: `execute`, bool. Denotes whether transaction should be executed by the bootloader. + // 31 byte: server-side tx execution mode + // For proved batches: + // It can simply denotes whether to execute the transaction (0 to stop executing the batch, 1 to continue) + // + // Each such encoded struct consumes 2 words + function TX_DESCRIPTION_SIZE() -> ret { + ret := 64 + } + + /// @dev The byte right after the basic description of bootloader transactions + function TXS_IN_BATCH_LAST_PTR() -> ret { + ret := add(TX_DESCRIPTION_BEGIN_BYTE(), mul(MAX_TRANSACTIONS_IN_BATCH(), TX_DESCRIPTION_SIZE())) + } + + /// @dev The memory page consists of 2^19 VM words. + /// Each execution result is a single boolean, but + /// for the sake of simplicity we will spend 32 bytes on each + /// of those for now. + function MAX_MEM_SIZE() -> ret { + ret := 0x1000000 // 2^24 bytes + } + + function L1_TX_INTRINSIC_L2_GAS() -> ret { + ret := {{L1_TX_INTRINSIC_L2_GAS}} + } + + function L1_TX_INTRINSIC_PUBDATA() -> ret { + ret := {{L1_TX_INTRINSIC_PUBDATA}} + } + + function L2_TX_INTRINSIC_GAS() -> ret { + ret := {{L2_TX_INTRINSIC_GAS}} + } + + function L2_TX_INTRINSIC_PUBDATA() -> ret { + ret := {{L2_TX_INTRINSIC_PUBDATA}} + } + + /// @dev The byte from which the pointers on the result of transactions are stored + function RESULT_START_PTR() -> ret { + ret := sub(MAX_MEM_SIZE(), mul(MAX_TRANSACTIONS_IN_BATCH(), 32)) + } + + + /// + /// DEBUG SUPPORT START + /// + + /// Position of the first byte that can be used for debugging. + function DEBUG_BEGIN_BYTE() -> ret { + ret := sub(VM_HOOK_PARAMS_OFFSET(), mul(MAX_DEBUG_SLOTS(), 32) + } + + /// @dev Number of debug slots to use (each one has 32 bytes) + function MAX_DEBUG_SLOTS() -> ret { + ret := 32 + } + + /// + /// DEBUG SUPPORT END. + /// + + /// @dev The pointer writing to which invokes the VM hooks + function VM_HOOK_PTR() -> ret { + ret := sub(RESULT_START_PTR(), 32) + } + + /// @dev The maximum number the VM hooks may accept + function VM_HOOK_PARAMS() -> ret { + ret := 2 + } + + /// @dev The offset starting from which the parameters for VM hooks are located + function VM_HOOK_PARAMS_OFFSET() -> ret { + ret := sub(VM_HOOK_PTR(), mul(VM_HOOK_PARAMS(), 32)) + } + + function LAST_FREE_SLOT() -> ret { + // The slot right before the vm hooks is the last slot that + // can be used for transaction's descriptions + /// DEBUG SUPPORT: use DEBUG_BEGIN_BYTE (as we reserve some bytes at the end of memory). + ret := sub(VM_HOOK_PARAMS_OFFSET(), 32) + } + + /// @dev The formal address of the bootloader + function BOOTLOADER_FORMAL_ADDR() -> ret { + ret := 0x0000000000000000000000000000000000008001 + } + + function MAX_SYSTEM_CONTRACT_ADDR() -> ret { + ret := 0x000000000000000000000000000000000000ffff + } + + function ACCOUNT_CODE_STORAGE_ADDR() -> ret { + ret := 0x0000000000000000000000000000000000008002 + } + + function NONCE_HOLDER_ADDR() -> ret { + ret := 0x0000000000000000000000000000000000008003 + } + + function KNOWN_CODES_CONTRACT_ADDR() -> ret { + ret := 0x0000000000000000000000000000000000008004 + } + + function CONTRACT_DEPLOYER_ADDR() -> ret { + ret := 0x0000000000000000000000000000000000008006 + } + + function FORCE_DEPLOYER() -> ret { + ret := 0x0000000000000000000000000000000000008007 + } + + function MSG_VALUE_SIMULATOR_ADDR() -> ret { + ret := 0x0000000000000000000000000000000000008009 + } + + function ETH_L2_TOKEN_ADDR() -> ret { + ret := 0x000000000000000000000000000000000000800a + } + + function SYSTEM_CONTEXT_ADDR() -> ret { + ret := 0x000000000000000000000000000000000000800b + } + + function BOOTLOADER_UTILITIES() -> ret { + ret := 0x000000000000000000000000000000000000800c + } + + function BYTECODE_COMPRESSOR_ADDR() -> ret { + ret := 0x000000000000000000000000000000000000800e + } + + function L1_MESSENGER_ADDR() -> ret { + ret := 0x0000000000000000000000000000000000008008 + } + + /// @dev The minimal allowed distance in bytes between the pointer to the compressed data + /// and the end of the area dedicated for the compressed bytecodes. + /// In fact, only distance of 192 should be sufficient: there it would be possible to insert + /// the hash of the bytecode, the 32 bytes buffer for selector and 2 offsets of the calldata, + /// but we keep it at 512 just in case. + function MIN_ALLOWED_OFFSET_FOR_COMPRESSED_BYTES_POINTER() -> ret { + ret := 512 + } + + /// @dev Whether the bootloader should enforce that accounts have returned the correct + /// magic value for signature. This value is enforced to be "true" on the main proved batch, but + /// we need the ability to ignore invalid signature results during fee estimation, + /// where the signature for the transaction is usually not known beforehand. + function SHOULD_ENSURE_CORRECT_RETURNED_MAGIC() -> ret { + ret := {{ENSURE_RETURNED_MAGIC}} + } + + /// @notice The type of the transaction used for system upgrades. + function UPGRADE_TRANSACTION_TX_TYPE() -> ret { + ret := 254 + } + + /// @notice The type of every non-upgrade transaction that comes from L1. + function L1_TX_TYPE() -> ret { + ret := 255 + } + + /// @dev The overhead in gas that will be used when checking whether the context has enough gas, i.e. + /// when checking for X gas, the context should have at least X+CHECK_ENOUGH_GAS_OVERHEAD() gas. + function CHECK_ENOUGH_GAS_OVERHEAD() -> ret { + ret := 1000000 + } + + /// @dev Ceil division of integers + function ceilDiv(x, y) -> ret { + switch or(eq(x, 0), eq(y, 0)) + case 0 { + // (x + y - 1) / y can overflow on addition, so we distribute. + ret := add(div(sub(x, 1), y), 1) + } + default { + ret := 0 + } + } + + /// @dev Calculates the length of a given number of bytes rounded up to the nearest multiple of 32. + function lengthRoundedByWords(len) -> ret { + let neededWords := div(add(len, 31), 32) + ret := safeMul(neededWords, 32, "xv") + } + + /// @dev Function responsible for processing the transaction + /// @param txDataOffset The offset to the ABI-encoding of the structure + /// @param resultPtr The pointer at which the result of the transaction's execution should be stored + /// @param transactionIndex The index of the transaction in the batch + /// @param isETHCall Whether the call is an ethCall. + /// @param gasPerPubdata The number of L2 gas to charge users for each byte of pubdata + /// On proved batch this value should always be zero + function processTx( + txDataOffset, + resultPtr, + transactionIndex, + isETHCall, + gasPerPubdata + ) { + // We set the L2 block info for this particular transaction + setL2Block(transactionIndex) + + let innerTxDataOffset := add(txDataOffset, 32) + + // By default we assume that the transaction has failed. + mstore(resultPtr, 0) + + let userProvidedPubdataPrice := getGasPerPubdataByteLimit(innerTxDataOffset) + debugLog("userProvidedPubdataPrice:", userProvidedPubdataPrice) + + debugLog("gasPerPubdata:", gasPerPubdata) + + switch getTxType(innerTxDataOffset) + case 254 { + // This is an upgrade transaction. + // Protocol upgrade transactions are processed totally in the same manner as the normal L1->L2 transactions, + // the only difference are: + // - They must be the first one in the batch + // - They have a different type to prevent tx hash collisions and preserve the expectation that the + // L1->L2 transactions have priorityTxId inside them. + if transactionIndex { + assertionError("Protocol upgrade tx not first") + } + + // This is to be called in the event that the L1 Transaction is a protocol upgrade txn. + // Since this is upgrade transactions, we are okay that the gasUsed by the transaction will + // not cover this additional hash computation + let canonicalL1TxHash := getCanonicalL1TxHash(txDataOffset) + sendToL1Native(true, protocolUpgradeTxHashKey(), canonicalL1TxHash) + + processL1Tx(txDataOffset, resultPtr, transactionIndex, userProvidedPubdataPrice, false) + } + case 255 { + // This is an L1->L2 transaction. + processL1Tx(txDataOffset, resultPtr, transactionIndex, userProvidedPubdataPrice, true) + } + default { + // The user has not agreed to this pubdata price + if lt(userProvidedPubdataPrice, gasPerPubdata) { + revertWithReason(UNACCEPTABLE_GAS_PRICE_ERR_CODE(), 0) + } + + setPricePerPubdataByte(gasPerPubdata) + + + processL2Tx(txDataOffset, resultPtr, transactionIndex, gasPerPubdata) + + + + switch isETHCall + case 1 { + let gasLimit := getGasLimit(innerTxDataOffset) + let nearCallAbi := getNearCallABI(gasLimit) + checkEnoughGas(gasLimit) + + if iszero(gasLimit) { + // If success is 0, we need to revert + revertWithReason( + ETH_CALL_ERR_CODE(), + 0 + ) + } + + ZKSYNC_NEAR_CALL_ethCall( + nearCallAbi, + txDataOffset, + resultPtr + ) + } + default { + processL2Tx(txDataOffset, resultPtr, transactionIndex, gasPerPubdata) + } + + } + } + + /// @dev Checks whether the code hash of the system context contract is correct and updates it if needed. + /// @dev The L1 contracts expect all the system logs to be present in the first boojum upgrade batch already. + /// However, the old system context did not send the same system logs. Usually we upgrade system context + /// via an upgrade transaction, but in this case the transaction won't be even processed, because of failure to create an L2 block. + function upgradeSystemContextIfNeeded() { + let expectedCodeHash := {{SYSTEM_CONTEXT_EXPECTED_CODE_HASH}} + + let actualCodeHash := extcodehash(SYSTEM_CONTEXT_ADDR()) + if iszero(eq(expectedCodeHash, actualCodeHash)) { + // Preparing the calldata to upgrade the SystemContext contract + {{UPGRADE_SYSTEM_CONTEXT_CALLDATA}} + + // We'll use a mimicCall to simulate the correct sender. + let success := mimicCallOnlyResult( + CONTRACT_DEPLOYER_ADDR(), + FORCE_DEPLOYER(), + 0, + 0, + 0, + 0, + 0, + 0 + ) + + if iszero(success) { + assertionError("system context upgrade fail") + } + } + } + + /// @dev Calculates the canonical hash of the L1->L2 transaction that will be + /// sent to L1 as a message to the L1 contract that a certain operation has been processed. + function getCanonicalL1TxHash(txDataOffset) -> ret { + // Putting the correct value at the `txDataOffset` just in case, since + // the correctness of this value is not part of the system invariants. + // Note, that the correct ABI encoding of the Transaction structure starts with 0x20 + mstore(txDataOffset, 32) + + let innerTxDataOffset := add(txDataOffset, 32) + let dataLength := safeAdd(32, getDataLength(innerTxDataOffset), "qev") + + debugLog("HASH_OFFSET", innerTxDataOffset) + debugLog("DATA_LENGTH", dataLength) + + ret := keccak256(txDataOffset, dataLength) + } + + /// @dev The purpose of this function is to make sure that the operator + /// gets paid for the transaction. Note, that the beneficiary of the payment is + /// bootloader. + /// The operator will be paid at the end of the batch. + function ensurePayment(txDataOffset, gasPrice) { + // Skipping the first 0x20 byte in the encoding of the transaction. + let innerTxDataOffset := add(txDataOffset, 32) + let from := getFrom(innerTxDataOffset) + let requiredETH := safeMul(getGasLimit(innerTxDataOffset), gasPrice, "lal") + + let bootloaderBalanceETH := balance(BOOTLOADER_FORMAL_ADDR()) + let paymaster := getPaymaster(innerTxDataOffset) + + let payer := 0 + + switch paymaster + case 0 { + payer := from + + // There is no paymaster, the user should pay for the execution. + // Calling for the `payForTransaction` method of the account. + setHook(VM_HOOK_ACCOUNT_VALIDATION_ENTERED()) + let res := accountPayForTx(from, txDataOffset) + setHook(VM_HOOK_NO_VALIDATION_ENTERED()) + + + if iszero(res) { + revertWithReason( + PAY_FOR_TX_FAILED_ERR_CODE(), + 1 + ) + } + } + default { + // There is some paymaster present. + payer := paymaster + + // Firstly, the `prepareForPaymaster` method of the user's account is called. + setHook(VM_HOOK_ACCOUNT_VALIDATION_ENTERED()) + let userPrePaymasterResult := accountPrePaymaster(from, txDataOffset) + setHook(VM_HOOK_NO_VALIDATION_ENTERED()) + + if iszero(userPrePaymasterResult) { + revertWithReason( + PRE_PAYMASTER_PREPARATION_FAILED_ERR_CODE(), + 1 + ) + } + + // Then, the paymaster is called. The paymaster should pay us in this method. + setHook(VM_HOOK_PAYMASTER_VALIDATION_ENTERED()) + let paymasterPaymentSuccess := validateAndPayForPaymasterTransaction(paymaster, txDataOffset) + if iszero(paymasterPaymentSuccess) { + revertWithReason( + PAYMASTER_VALIDATION_FAILED_ERR_CODE(), + 1 + ) + } + + storePaymasterContextAndCheckMagic() + setHook(VM_HOOK_NO_VALIDATION_ENTERED()) + } + + let bootloaderReceivedFunds := safeSub(balance(BOOTLOADER_FORMAL_ADDR()), bootloaderBalanceETH, "qsx") + + // If the amount of funds provided to the bootloader is less than the minimum required one + // then this transaction should be rejected. + if lt(bootloaderReceivedFunds, requiredETH) { + revertWithReason( + FAILED_TO_CHARGE_FEE_ERR_CODE(), + 0 + ) + } + + let excessiveFunds := safeSub(bootloaderReceivedFunds, requiredETH, "llm") + + if gt(excessiveFunds, 0) { + // Returning back the excessive funds taken. + directETHTransfer(excessiveFunds, payer) + } + } + + /// @notice Mints ether to the recipient + /// @param to -- the address of the recipient + /// @param amount -- the amount of ETH to mint + /// @param useNearCallPanic -- whether to use nearCallPanic in case of + /// the transaction failing to execute. It is desirable in cases + /// where we want to allow the method fail without reverting the entire bootloader + function mintEther(to, amount, useNearCallPanic) { + mstore(0, {{RIGHT_PADDED_MINT_ETHER_SELECTOR}}) + mstore(4, to) + mstore(36, amount) + let success := call( + gas(), + ETH_L2_TOKEN_ADDR(), + 0, + 0, + 68, + 0, + 0 + ) + if iszero(success) { + switch useNearCallPanic + case 0 { + revertWithReason( + MINT_ETHER_FAILED_ERR_CODE(), + 0 + ) + } + default { + nearCallPanic() + } + } + } + + /// @dev Saves the paymaster context and checks that the paymaster has returned the correct + /// magic value. + /// @dev IMPORTANT: this method should be called right after + /// the validateAndPayForPaymasterTransaction method to keep the `returndata` from that transaction + function storePaymasterContextAndCheckMagic() { + // The paymaster validation step should return context of type "bytes context" + // This means that the returndata is encoded the following way: + // 0x20 || context_len || context_bytes... + let returnlen := returndatasize() + // The minimal allowed returndatasize is 64: magicValue || offset + if lt(returnlen, 64) { + revertWithReason( + PAYMASTER_RETURNED_INVALID_CONTEXT(), + 0 + ) + } + + // Note that it is important to copy the magic even though it is not needed if the + // `SHOULD_ENSURE_CORRECT_RETURNED_MAGIC` is false. It is never false in production + // but it is so in fee estimation and we want to preserve as many operations as + // in the original operation. + { + returndatacopy(0, 0, 32) + let magic := mload(0) + + let isMagicCorrect := eq(magic, {{SUCCESSFUL_PAYMASTER_VALIDATION_MAGIC_VALUE}}) + + if and(iszero(isMagicCorrect), SHOULD_ENSURE_CORRECT_RETURNED_MAGIC()) { + revertWithReason( + PAYMASTER_RETURNED_INVALID_MAGIC_ERR_CODE(), + 0 + ) + } + } + + returndatacopy(0, 32, 32) + let returnedContextOffset := mload(0) + + // Ensuring that the returned offset is not greater than the returndata length + // Note, that we cannot use addition here to prevent an overflow + if gt(returnedContextOffset, returnlen) { + revertWithReason( + PAYMASTER_RETURNED_INVALID_CONTEXT(), + 0 + ) + } + + // Can not read the returned length. + // It is safe to add here due to the previous check. + if gt(add(returnedContextOffset, 32), returnlen) { + revertWithReason( + PAYMASTER_RETURNED_INVALID_CONTEXT(), + 0 + ) + } + + // Reading the length of the context + returndatacopy(0, returnedContextOffset, 32) + let returnedContextLen := mload(0) + + // Ensuring that returnedContextLen is not greater than the length of the paymaster context + // Note, that this check at the same time prevents an overflow in the future operations with returnedContextLen + if gt(returnedContextLen, PAYMASTER_CONTEXT_BYTES()) { + revertWithReason( + PAYMASTER_RETURNED_CONTEXT_IS_TOO_LONG(), + 0 + ) + } + + let roundedContextLen := lengthRoundedByWords(returnedContextLen) + + // The returned context's size should not exceed the maximum length + if gt(add(roundedContextLen, 32), PAYMASTER_CONTEXT_BYTES()) { + revertWithReason( + PAYMASTER_RETURNED_CONTEXT_IS_TOO_LONG(), + 0 + ) + } + + if gt(add(returnedContextOffset, add(32, returnedContextLen)), returnlen) { + revertWithReason( + PAYMASTER_RETURNED_INVALID_CONTEXT(), + 0 + ) + } + + returndatacopy(PAYMASTER_CONTEXT_BEGIN_BYTE(), returnedContextOffset, add(32, returnedContextLen)) + } + + /// @dev The function responsible for processing L1->L2 transactions. + /// @param txDataOffset The offset to the transaction's information + /// @param resultPtr The pointer at which the result of the execution of this transaction + /// @param transactionIndex The index of the transaction + /// @param gasPerPubdata The price per pubdata to be used + /// @param isPriorityOp Whether the transaction is a priority one + /// should be stored. + function processL1Tx( + txDataOffset, + resultPtr, + transactionIndex, + gasPerPubdata, + isPriorityOp + ) { + // For L1->L2 transactions we always use the pubdata price provided by the transaction. + // This is needed to ensure DDoS protection. All the excess expenditure + // will be refunded to the user. + setPricePerPubdataByte(gasPerPubdata) + + // Skipping the first formal 0x20 byte + let innerTxDataOffset := add(txDataOffset, 32) + + let gasLimitForTx, reservedGas := getGasLimitForTx( + innerTxDataOffset, + transactionIndex, + gasPerPubdata, + L1_TX_INTRINSIC_L2_GAS(), + L1_TX_INTRINSIC_PUBDATA() + ) + + let gasUsedOnPreparation := 0 + let canonicalL1TxHash := 0 + + canonicalL1TxHash, gasUsedOnPreparation := l1TxPreparation(txDataOffset) + + let refundGas := 0 + let success := 0 + + // The invariant that the user deposited more than the value needed + // for the transaction must be enforced on L1, but we double check it here + let gasLimit := getGasLimit(innerTxDataOffset) + + // Note, that for now the property of block.base <= tx.maxFeePerGas does not work + // for L1->L2 transactions. For now, these transactions are processed with the same gasPrice + // they were provided on L1. In the future, we may apply a new logic for it. + let gasPrice := getMaxFeePerGas(innerTxDataOffset) + let txInternalCost := safeMul(gasPrice, gasLimit, "poa") + let value := getValue(innerTxDataOffset) + if lt(getReserved0(innerTxDataOffset), safeAdd(value, txInternalCost, "ol")) { + assertionError("deposited eth too low") + } + + if gt(gasLimitForTx, gasUsedOnPreparation) { + let potentialRefund := 0 + + potentialRefund, success := getExecuteL1TxAndGetRefund(txDataOffset, sub(gasLimitForTx, gasUsedOnPreparation)) + + // Asking the operator for refund + askOperatorForRefund(potentialRefund) + + // In case the operator provided smaller refund than the one calculated + // by the bootloader, we return the refund calculated by the bootloader. + refundGas := max(getOperatorRefundForTx(transactionIndex), safeAdd(potentialRefund, reservedGas, "iop")) + } + + if gt(refundGas, gasLimit) { + assertionError("L1: refundGas > gasLimit") + } + + let payToOperator := safeMul(gasPrice, safeSub(gasLimit, refundGas, "lpah"), "mnk") + + // Note, that for now, the L1->L2 transactions are free, i.e. the gasPrice + // for such transactions is always zero, so the `refundGas` is not used anywhere + // except for notifications for the operator for API purposes. + notifyAboutRefund(refundGas) + + // Paying the fee to the operator + mintEther(BOOTLOADER_FORMAL_ADDR(), payToOperator, false) + + let toRefundRecipient + switch success + case 0 { + if iszero(isPriorityOp) { + // Upgrade transactions must always succeed + assertionError("Upgrade tx failed") + } + + // If the transaction reverts, then minting the msg.value to the user has been reverted + // as well, so we can simply mint everything that the user has deposited to + // the refund recipient + toRefundRecipient := safeSub(getReserved0(innerTxDataOffset), payToOperator, "vji") + } + default { + // If the transaction succeeds, then it is assumed that msg.value was transferred correctly. However, the remaining + // ETH deposited will be given to the refund recipient. + + toRefundRecipient := safeSub(getReserved0(innerTxDataOffset), safeAdd(getValue(innerTxDataOffset), payToOperator, "kpa"), "ysl") + } + + if gt(toRefundRecipient, 0) { + let refundRecipient := getReserved1(innerTxDataOffset) + // Zero out the first 12 bytes to be sure that refundRecipient is address. + // In case of an issue in L1 contracts, we still will be able to process tx. + refundRecipient := and(refundRecipient, sub(shl(160, 1), 1)) + mintEther(refundRecipient, toRefundRecipient, false) + } + + mstore(resultPtr, success) + + debugLog("Send message to L1", success) + + // Sending the L2->L1 log so users will be able to prove transaction execution result on L1. + sendL2LogUsingL1Messenger(true, canonicalL1TxHash, success) + + if isPriorityOp { + // Update priority txs L1 data + mstore(0, mload(PRIORITY_TXS_L1_DATA_BEGIN_BYTE())) + mstore(32, canonicalL1TxHash) + mstore(PRIORITY_TXS_L1_DATA_BEGIN_BYTE(), keccak256(0, 64)) + mstore(add(PRIORITY_TXS_L1_DATA_BEGIN_BYTE(), 32), add(mload(add(PRIORITY_TXS_L1_DATA_BEGIN_BYTE(), 32)), 1)) + } + } + + function getExecuteL1TxAndGetRefund(txDataOffset, gasForExecution) -> potentialRefund, success { + debugLog("gasForExecution", gasForExecution) + + let callAbi := getNearCallABI(gasForExecution) + debugLog("callAbi", callAbi) + + checkEnoughGas(gasForExecution) + + let gasBeforeExecution := gas() + success := ZKSYNC_NEAR_CALL_executeL1Tx( + callAbi, + txDataOffset + ) + notifyExecutionResult(success) + let gasSpentOnExecution := sub(gasBeforeExecution, gas()) + + potentialRefund := sub(gasForExecution, gasSpentOnExecution) + if gt(gasSpentOnExecution, gasForExecution) { + potentialRefund := 0 + } + } + + /// @dev The function responsible for doing all the pre-execution operations for L1->L2 transactions. + /// @param txDataOffset The offset to the transaction's information + /// @return canonicalL1TxHash The hash of processed L1->L2 transaction + /// @return gasUsedOnPreparation The number of L2 gas used in the preparation stage + function l1TxPreparation(txDataOffset) -> canonicalL1TxHash, gasUsedOnPreparation { + let innerTxDataOffset := add(txDataOffset, 32) + + let gasBeforePreparation := gas() + debugLog("gasBeforePreparation", gasBeforePreparation) + + // Even though the smart contracts on L1 should make sure that the L1->L2 provide enough gas to generate the hash + // we should still be able to do it even if this protection layer fails. + canonicalL1TxHash := getCanonicalL1TxHash(txDataOffset) + debugLog("l1 hash", canonicalL1TxHash) + + // Appending the transaction's hash to the current L2 block + appendTransactionHash(canonicalL1TxHash, true) + + markFactoryDepsForTx(innerTxDataOffset, true) + + gasUsedOnPreparation := safeSub(gasBeforePreparation, gas(), "xpa") + debugLog("gasUsedOnPreparation", gasUsedOnPreparation) + } + + /// @dev Returns the gas price that should be used by the transaction + /// based on the EIP1559's maxFeePerGas and maxPriorityFeePerGas. + /// The following invariants should hold: + /// maxPriorityFeePerGas <= maxFeePerGas + /// baseFee <= maxFeePerGas + /// While we charge baseFee from the users, the method is mostly used as a method for validating + /// the correctness of the fee parameters + function getGasPrice( + maxFeePerGas, + maxPriorityFeePerGas + ) -> ret { + let baseFee := basefee() + + if gt(maxPriorityFeePerGas, maxFeePerGas) { + revertWithReason( + MAX_PRIORITY_FEE_PER_GAS_GREATER_THAN_MAX_FEE_PER_GAS(), + 0 + ) + } + + if gt(baseFee, maxFeePerGas) { + revertWithReason( + BASE_FEE_GREATER_THAN_MAX_FEE_PER_GAS(), + 0 + ) + } + + // We always use `baseFee` to charge the transaction + ret := baseFee + } + + /// @dev The function responsible for processing L2 transactions. + /// @param txDataOffset The offset to the ABI-encoded Transaction struct. + /// @param resultPtr The pointer at which the result of the execution of this transaction + /// should be stored. + /// @param transactionIndex The index of the current transaction. + /// @param gasPerPubdata The L2 gas to be used for each byte of pubdata published onchain. + /// @dev This function firstly does the validation step and then the execution step in separate near_calls. + /// It is important that these steps are split to avoid rollbacking the state made by the validation step. + function processL2Tx( + txDataOffset, + resultPtr, + transactionIndex, + gasPerPubdata + ) { + let innerTxDataOffset := add(txDataOffset, 32) + + // Firsly, we publish all the bytecodes needed. This is needed to be done separately, since + // bytecodes usually form the bulk of the L2 gas prices. + + let gasLimitForTx, reservedGas := getGasLimitForTx(innerTxDataOffset, transactionIndex, gasPerPubdata, L2_TX_INTRINSIC_GAS(), L2_TX_INTRINSIC_PUBDATA()) + + + /// + /// DEBUG SUPPORT START + /// + + let totalGasLimit := getGasLimit(innerTxDataOffset) + + // Sentinel value for Debug information for the in-memory node. + mstore(DEBUG_BEGIN_BYTE(), 1337) + + // We start with total gas limit from user. + mstore(add(DEBUG_BEGIN_BYTE(), 32), totalGasLimit) + // This is the amount of gas that will never be used. + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 2)), reservedGas) + + // Amount of gas per each pubdata byte. + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 3)), gasPerPubdata) + + // This is the amount of gas that is left after we removed the minimum amount of gas that will be consumed + // by the transaction itself (INTRINSIC GAS). + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 4)), gasLimitForTx) + + /// + /// DEBUG SUPPORT END + /// + + let gasPrice := getGasPrice(getMaxFeePerGas(innerTxDataOffset), getMaxPriorityFeePerGas(innerTxDataOffset)) + + debugLog("gasLimitForTx", gasLimitForTx) + + let gasLeft := l2TxValidation( + txDataOffset, + gasLimitForTx, + gasPrice + ) + + /// + /// DEBUG SUPPORT START + /// + // This is the amount of gas that is left after validation. + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 5)), gasLeft) + /// + /// DEBUG SUPPORT END + /// + + debugLog("validation finished", 0) + + let gasSpentOnExecute := 0 + let success := 0 + success, gasSpentOnExecute := l2TxExecution(txDataOffset, gasLeft) + /// + /// DEBUG SUPPORT START + /// + // Amount of gas spent on execute. + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 6)), gasSpentOnExecute) + /// + /// DEBUG SUPPORT END + /// + + + debugLog("execution finished", 0) + + let refund := 0 + let gasToRefund := sub(gasLeft, gasSpentOnExecute) + if lt(gasLeft, gasSpentOnExecute){ + gasToRefund := 0 + } + /// + /// DEBUG SUPPORT START + /// + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 8)), gasToRefund) + /// + /// DEBUG SUPPORT END + /// + + + // Note, that we pass reservedGas from the refundGas separately as it should not be used + // during the postOp execution. + + refund := refundCurrentL2Transaction( + txDataOffset, + transactionIndex, + success, + gasToRefund, + gasPrice, + reservedGas + ) + + /// + /// DEBUG SUPPORT START + /// + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 9)), refund) + /// + /// DEBUG SUPPORT END + /// + + debugLog("refund", 0) + + notifyAboutRefund(refund) + mstore(resultPtr, success) + } + + /// @dev Calculates the L2 gas limit for the transaction's body, i.e. without intrinsic costs and overhead. + /// @param innerTxDataOffset The offset for the ABI-encoded Transaction struct fields. + /// @param transactionIndex The index of the transaction within the batch. + /// @param gasPerPubdata The price for a pubdata byte in L2 gas. + /// @param intrinsicGas The intrinsic number of L2 gas required for transaction processing. + /// @param intrinsicPubdata The intrinsic number of pubdata bytes required for transaction processing. + /// @return gasLimitForTx The maximum number of L2 gas that can be spent on a transaction. + /// @return reservedGas The number of L2 gas that is beyond the `MAX_GAS_PER_TRANSACTION` and beyond the operator's trust limit, + /// i.e. gas which we cannot allow the transaction to use and will refund. + function getGasLimitForTx( + innerTxDataOffset, + transactionIndex, + gasPerPubdata, + intrinsicGas, + intrinsicPubdata + ) -> gasLimitForTx, reservedGas { + let totalGasLimit := getGasLimit(innerTxDataOffset) + + // `MAX_GAS_PER_TRANSACTION` is the amount of gas each transaction + // is guaranteed to get, so even if the operator does not trust the account enough, + // it is still obligated to provide at least that + let operatorTrustedGasLimit := max(MAX_GAS_PER_TRANSACTION(), getOperatorTrustedGasLimitForTx(transactionIndex)) + + // We remember the amount of gas that is beyond the operator's trust limit to refund it back later. + switch gt(totalGasLimit, operatorTrustedGasLimit) + case 0 { + reservedGas := 0 + } + default { + reservedGas := sub(totalGasLimit, operatorTrustedGasLimit) + totalGasLimit := operatorTrustedGasLimit + } + + let txEncodingLen := safeAdd(32, getDataLength(innerTxDataOffset), "lsh") + + let operatorOverheadForTransaction := getVerifiedOperatorOverheadForTx( + transactionIndex, + totalGasLimit, + gasPerPubdata, + txEncodingLen + ) + gasLimitForTx := safeSub(totalGasLimit, operatorOverheadForTransaction, "qr") + + let intrinsicOverhead := safeAdd( + intrinsicGas, + // the error messages are trimmed to fit into 32 bytes + safeMul(intrinsicPubdata, gasPerPubdata, "qw"), + "fj" + ) + /// + /// DEBUG SUPPORT START + /// + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 11)), operatorOverheadForTransaction) + + // Fixed overhead. + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 10)), intrinsicOverhead) + /// + /// DEBUG SUPPORT END + /// + + + switch lt(gasLimitForTx, intrinsicOverhead) + case 1 { + gasLimitForTx := 0 + } + default { + gasLimitForTx := sub(gasLimitForTx, intrinsicOverhead) + } + } + + /// @dev The function responsible for the L2 transaction validation. + /// @param txDataOffset The offset to the ABI-encoded Transaction struct. + /// @param gasLimitForTx The L2 gas limit for the transaction validation & execution. + /// @param gasPrice The L2 gas price that should be used by the transaction. + /// @return gasLeft The gas left after the validation step. + function l2TxValidation( + txDataOffset, + gasLimitForTx, + gasPrice + ) -> gasLeft { + let gasBeforeValidate := gas() + + debugLog("gasBeforeValidate", gasBeforeValidate) + + // Saving the tx hash and the suggested signed tx hash to memory + saveTxHashes(txDataOffset) + + // Appending the transaction's hash to the current L2 block + appendTransactionHash(mload(CURRENT_L2_TX_HASHES_BEGIN_BYTE()), false) + + checkEnoughGas(gasLimitForTx) + + // Note, that it is assumed that `ZKSYNC_NEAR_CALL_validateTx` will always return true + // unless some error which made the whole bootloader to revert has happened or + // it runs out of gas. + let isValid := 0 + + // Only if the gasLimit for tx is non-zero, we will try to actually run the validation + if gasLimitForTx { + let validateABI := getNearCallABI(gasLimitForTx) + + debugLog("validateABI", validateABI) + + + isValid := ZKSYNC_NEAR_CALL_validateTx(validateABI, txDataOffset, gasPrice) + + + isValid := 1 + + } + + debugLog("isValid", isValid) + + let gasUsedForValidate := sub(gasBeforeValidate, gas()) + debugLog("gasUsedForValidate", gasUsedForValidate) + + gasLeft := sub(gasLimitForTx, gasUsedForValidate) + if lt(gasLimitForTx, gasUsedForValidate) { + gasLeft := 0 + } + + // isValid can only be zero if the validation has failed with out of gas + if or(iszero(gasLeft), iszero(isValid)) { + revertWithReason(TX_VALIDATION_OUT_OF_GAS(), 0) + } + + setHook(VM_HOOK_VALIDATION_STEP_ENDED()) + } + + /// @dev The function responsible for the execution step of the L2 transaction. + /// @param txDataOffset The offset to the ABI-encoded Transaction struct. + /// @param gasLeft The gas left after the validation step. + /// @return success Whether or not the execution step was successful. + /// @return gasSpentOnExecute The gas spent on the transaction execution. + function l2TxExecution( + txDataOffset, + gasLeft, + ) -> success, gasSpentOnExecute { + let newCompressedFactoryDepsPointer := 0 + let gasSpentOnFactoryDeps := 0 + let gasBeforeFactoryDeps := gas() + if gasLeft { + let markingDependenciesABI := getNearCallABI(gasLeft) + checkEnoughGas(gasLeft) + newCompressedFactoryDepsPointer := ZKSYNC_NEAR_CALL_markFactoryDepsL2(markingDependenciesABI, txDataOffset) + gasSpentOnFactoryDeps := sub(gasBeforeFactoryDeps, gas()) + } + + /// + /// DEBUG SUPPORT START + /// + + // Gas spent on fetching and unpacking the bytecodes. + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 7)), gasSpentOnFactoryDeps) + + /// + /// DEBUG SUPPORT END + /// + + // If marking of factory dependencies has been unsuccessful, 0 value is returned. + // Otherwise, all the previous dependencies have been successfully published, so + // we need to move the pointer. + if newCompressedFactoryDepsPointer { + mstore(COMPRESSED_BYTECODES_BEGIN_BYTE(), newCompressedFactoryDepsPointer) + } + + switch gt(gasLeft, gasSpentOnFactoryDeps) + case 0 { + gasSpentOnExecute := gasLeft + gasLeft := 0 + } + default { + // Note, that since gt(gasLeft, gasSpentOnFactoryDeps) = true + // sub(gasLeft, gasSpentOnFactoryDeps) > 0, which is important + // because a nearCall with 0 gas passes on all the gas of the parent frame. + gasLeft := sub(gasLeft, gasSpentOnFactoryDeps) + + let executeABI := getNearCallABI(gasLeft) + checkEnoughGas(gasLeft) + + let gasBeforeExecute := gas() + // for this one, we don't care whether or not it fails. + + success := ZKSYNC_NEAR_CALL_executeL2Tx( + executeABI, + txDataOffset + ) + + + success := ZKSYNC_NEAR_CALL_executeL2TxImpersonating( + executeABI, + txDataOffset + ) + + + gasSpentOnExecute := add(gasSpentOnFactoryDeps, sub(gasBeforeExecute, gas())) + } + + notifyExecutionResult(success) + } + + /// @dev Function responsible for the validation & fee payment step of the transaction. + /// @param abi The nearCall ABI. It is implicitly used as gasLimit for the call of this function. + /// @param txDataOffset The offset to the ABI-encoded Transaction struct. + /// @param gasPrice The gasPrice to be used in this transaction. + function ZKSYNC_NEAR_CALL_validateTx( + abi, + txDataOffset, + gasPrice + ) -> ret { + // For the validation step we always use the bootloader as the tx.origin of the transaction + setTxOrigin(BOOTLOADER_FORMAL_ADDR()) + setGasPrice(gasPrice) + + // Skipping the first 0x20 word of the ABI-encoding + let innerTxDataOffset := add(txDataOffset, 32) + debugLog("Starting validation", 0) + + accountValidateTx(txDataOffset) + debugLog("Tx validation complete", 1) + + ensurePayment(txDataOffset, gasPrice) + + ret := 1 + } + + /// @dev Function responsible for the execution of the L2 transaction. + /// It includes both the call to the `executeTransaction` method of the account + /// and the call to postOp of the account. + /// @param abi The nearCall ABI. It is implicitly used as gasLimit for the call of this function. + /// @param txDataOffset The offset to the ABI-encoded Transaction struct. + function ZKSYNC_NEAR_CALL_executeL2Tx( + abi, + txDataOffset + ) -> success { + // Skipping the first word of the ABI-encoding encoding + let innerTxDataOffset := add(txDataOffset, 32) + let from := getFrom(innerTxDataOffset) + + debugLog("Executing L2 tx", 0) + // The tx.origin can only be an EOA + switch isEOA(from) + case true { + setTxOrigin(from) + } + default { + setTxOrigin(BOOTLOADER_FORMAL_ADDR()) + } + + success := executeL2Tx(txDataOffset, from) + debugLog("Executing L2 ret", success) + } + + + function ZKSYNC_NEAR_CALL_executeL2TxImpersonating( + abi, + txDataOffset + ) -> success { + let innerTxDataOffset := add(txDataOffset, 32) + let to := getTo(innerTxDataOffset) + let from := getFrom(innerTxDataOffset) + let value := getValue(innerTxDataOffset) + let dataPtr := getDataPtr(innerTxDataOffset) + + debugLog("Executing L2 tx", 0) + switch isEOA(from) + case true { + setTxOrigin(from) + } + default { + setTxOrigin(0) + } + + success := msgValueSimulatorMimicCall( + to, + from, + value, + dataPtr + ) + debugLog("Executing L2 ret", success) + } + + + /// @dev Sets factory dependencies for an L2 transaction with possible usage of packed bytecodes. + function ZKSYNC_NEAR_CALL_markFactoryDepsL2( + abi, + txDataOffset + ) -> newDataInfoPtr { + let innerTxDataOffset := add(txDataOffset, 32) + + /// Note, that since it is the near call when it panics it reverts the state changes, but it DOES NOT + /// revert the changes in *memory* of the current frame. That is why we do not change the value under + /// COMPRESSED_BYTECODES_BEGIN_BYTE(), and it is only changed outside of this method. + let dataInfoPtr := mload(COMPRESSED_BYTECODES_BEGIN_BYTE()) + let factoryDepsPtr := getFactoryDepsPtr(innerTxDataOffset) + let factoryDepsLength := mload(factoryDepsPtr) + + let iter := add(factoryDepsPtr, 32) + let endPtr := add(iter, mul(32, factoryDepsLength)) + + for { } lt(iter, endPtr) { iter := add(iter, 32)} { + let bytecodeHash := mload(iter) + + let currentExpectedBytecodeHash := mload(dataInfoPtr) + + if eq(bytecodeHash, currentExpectedBytecodeHash) { + // Here we are making sure that the bytecode is indeed not yet know and needs to be published, + // preveting users from being overcharged by the operator. + let marker := getCodeMarker(bytecodeHash) + + if marker { + assertionError("invalid republish") + } + + dataInfoPtr := sendCompressedBytecode(dataInfoPtr, bytecodeHash) + } + } + + // For all the bytecodes that have not been compressed on purpose or due to the inefficiency + // of compressing the entire preimage of the bytecode will be published. + // For bytecodes published in the previous step, no need pubdata will have to be published + markFactoryDepsForTx(innerTxDataOffset, false) + + newDataInfoPtr := dataInfoPtr + } + + function getCodeMarker(bytecodeHash) -> ret { + mstore(0, {{GET_MARKER_PADDED_SELECTOR}}) + mstore(4, bytecodeHash) + let success := call( + gas(), + KNOWN_CODES_CONTRACT_ADDR(), + 0, + 0, + 36, + 0, + 32 + ) + + if iszero(success) { + nearCallPanic() + } + + ret := mload(0) + } + + + /// @dev Used to refund the current transaction. + /// The gas that this transaction consumes has been already paid in the + /// process of the validation + function refundCurrentL2Transaction( + txDataOffset, + transactionIndex, + success, + gasLeft, + gasPrice, + reservedGas + ) -> finalRefund { + setTxOrigin(BOOTLOADER_FORMAL_ADDR()) + + finalRefund := 0 + + let innerTxDataOffset := add(txDataOffset, 32) + + let paymaster := getPaymaster(innerTxDataOffset) + let refundRecipient := 0 + switch paymaster + case 0 { + // No paymaster means that the sender should receive the refund + refundRecipient := getFrom(innerTxDataOffset) + } + default { + refundRecipient := paymaster + + if gt(gasLeft, 0) { + checkEnoughGas(gasLeft) + let nearCallAbi := getNearCallABI(gasLeft) + let gasBeforePostOp := gas() + pop(ZKSYNC_NEAR_CALL_callPostOp( + // Maximum number of gas that the postOp could spend + nearCallAbi, + paymaster, + txDataOffset, + success, + // Since the paymaster will be refunded with reservedGas, + // it should know about it + safeAdd(gasLeft, reservedGas, "jkl") + )) + let gasSpentByPostOp := sub(gasBeforePostOp, gas()) + + switch gt(gasLeft, gasSpentByPostOp) + case 1 { + gasLeft := sub(gasLeft, gasSpentByPostOp) + } + default { + gasLeft := 0 + } + } + } + + askOperatorForRefund(gasLeft) + + let operatorProvidedRefund := getOperatorRefundForTx(transactionIndex) + + // If the operator provides the value that is lower than the one suggested for + // the bootloader, we will use the one calculated by the bootloader. + let refundInGas := max(operatorProvidedRefund, add(reservedGas, gasLeft)) + + // The operator cannot refund more than the gasLimit for the transaction + if gt(refundInGas, getGasLimit(innerTxDataOffset)) { + assertionError("refundInGas > gasLimit") + } + + if iszero(validateUint32(refundInGas)) { + assertionError("refundInGas is not uint32") + } + + let ethToRefund := safeMul( + refundInGas, + gasPrice, + "fdf" + ) + + directETHTransfer(ethToRefund, refundRecipient) + + finalRefund := refundInGas + } + + /// @notice A function that transfers ETH directly through the L2EthToken system contract. + /// Note, that unlike classical EVM transfers it does NOT call the recipient, but only changes the balance. + function directETHTransfer(amount, recipient) { + let ptr := 0 + mstore(ptr, {{PADDED_TRANSFER_FROM_TO_SELECTOR}}) + mstore(add(ptr, 4), BOOTLOADER_FORMAL_ADDR()) + mstore(add(ptr, 36), recipient) + mstore(add(ptr, 68), amount) + + let transferSuccess := call( + gas(), + ETH_L2_TOKEN_ADDR(), + 0, + 0, + 100, + 0, + 0 + ) + + if iszero(transferSuccess) { + assertionError("Failed to refund") + } + } + + /// @dev Return the operator suggested transaction refund. + function getOperatorRefundForTx(transactionIndex) -> ret { + let refundPtr := add(TX_OPERATOR_REFUND_BEGIN_BYTE(), mul(transactionIndex, 32)) + ret := mload(refundPtr) + } + + /// @dev Return the operator suggested transaction overhead cost. + function getOperatorOverheadForTx(transactionIndex) -> ret { + let txBatchOverheadPtr := add(TX_SUGGESTED_OVERHEAD_BEGIN_BYTE(), mul(transactionIndex, 32)) + ret := mload(txBatchOverheadPtr) + } + + /// @dev Return the operator's "trusted" transaction gas limit + function getOperatorTrustedGasLimitForTx(transactionIndex) -> ret { + let txTrustedGasLimitPtr := add(TX_OPERATOR_TRUSTED_GAS_LIMIT_BEGIN_BYTE(), mul(transactionIndex, 32)) + ret := mload(txTrustedGasLimitPtr) + } + + /// @dev Returns the bytecode hash that is next for being published + function getCurrentCompressedBytecodeHash() -> ret { + let compressionPtr := mload(COMPRESSED_BYTECODES_BEGIN_BYTE()) + + ret := mload(add(COMPRESSED_BYTECODES_BEGIN_BYTE(), compressionPtr)) + } + + function checkOffset(pointer) { + if gt(pointer, sub(COMPRESSED_BYTECODES_END_BYTE(), MIN_ALLOWED_OFFSET_FOR_COMPRESSED_BYTES_POINTER())) { + assertionError("calldataEncoding too big") + } + } + + /// @dev It is expected that the pointer at the COMPRESSED_BYTECODES_BEGIN_BYTE() + /// stores the position of the current bytecodeHash + function sendCompressedBytecode(dataInfoPtr, bytecodeHash) -> ret { + // Storing the right selector, ensuring that the operator cannot manipulate it + mstore(add(dataInfoPtr, 32), {{PUBLISH_COMPRESSED_BYTECODE_SELECTOR}}) + + let calldataPtr := add(dataInfoPtr, 60) + let afterSelectorPtr := add(calldataPtr, 4) + + let originalBytecodeOffset := add(mload(afterSelectorPtr), afterSelectorPtr) + checkOffset(originalBytecodeOffset) + let potentialRawCompressedDataOffset := validateBytes( + originalBytecodeOffset + ) + + let rawCompressedDataOffset := add(mload(add(afterSelectorPtr, 32)), afterSelectorPtr) + checkOffset(rawCompressedDataOffset) + + if iszero(eq(potentialRawCompressedDataOffset, rawCompressedDataOffset)) { + assertionError("Compression calldata incorrect") + } + + let nextAfterCalldata := validateBytes( + rawCompressedDataOffset + ) + checkOffset(nextAfterCalldata) + + let totalLen := safeSub(nextAfterCalldata, calldataPtr, "xqwf") + + // Note, that it is safe because the + let success := call( + gas(), + BYTECODE_COMPRESSOR_ADDR(), + 0, + calldataPtr, + totalLen, + 0, + 32 + ) + + // If the transaction failed, the most likely reason is that there + // was not enough gas. That's why we do the nearCallPanic to stop the near call frame. + if iszero(success) { + debugLog("compressor call failed", 0) + debugReturndata() + nearCallPanic() + } + + let returnedBytecodeHash := mload(0) + + // If the bytecode hash calculated on the bytecode compressor's side + // is not equal to the one provided by the operator means that the operator is + // malicious and we should revert the batch altogether + if iszero(eq(returnedBytecodeHash, bytecodeHash)) { + assertionError("bytecodeHash incorrect") + } + + ret := nextAfterCalldata + } + + /// @dev Get checked for overcharged operator's overhead for the transaction. + /// @param transactionIndex The index of the transaction in the batch + /// @param txTotalGasLimit The total gass limit of the transaction (including the overhead). + /// @param gasPerPubdataByte The price for pubdata byte in gas. + /// @param txEncodeLen The length of the ABI-encoding of the transaction + function getVerifiedOperatorOverheadForTx( + transactionIndex, + txTotalGasLimit, + gasPerPubdataByte, + txEncodeLen + ) -> ret { + let operatorOverheadForTransaction := getOperatorOverheadForTx(transactionIndex) + if gt(operatorOverheadForTransaction, txTotalGasLimit) { + assertionError("Overhead higher than gasLimit") + } + let txGasLimit := min(safeSub(txTotalGasLimit, operatorOverheadForTransaction, "www"), MAX_GAS_PER_TRANSACTION()) + + let requiredOverhead := getTransactionUpfrontOverhead( + txGasLimit, + gasPerPubdataByte, + txEncodeLen + ) + /// + /// DEBUG SUPPORT START + /// + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 12)), requiredOverhead) + /// + /// DEBUG SUPPORT END + /// + + + debugLog("txTotalGasLimit", txTotalGasLimit) + debugLog("requiredOverhead", requiredOverhead) + debugLog("operatorOverheadForTransaction", operatorOverheadForTransaction) + + // The required overhead is less than the overhead that the operator + // has requested from the user, meaning that the operator tried to overcharge the user + if lt(requiredOverhead, operatorOverheadForTransaction) { + assertionError("Operator's overhead too high") + } + + ret := operatorOverheadForTransaction + } + + /// @dev Function responsible for the execution of the L1->L2 transaction. + /// @param abi The nearCall ABI. It is implicitly used as gasLimit for the call of this function. + /// @param txDataOffset The offset to the ABI-encoded Transaction struct. + function ZKSYNC_NEAR_CALL_executeL1Tx( + abi, + txDataOffset + ) -> success { + // Skipping the first word of the ABI encoding of the struct + let innerTxDataOffset := add(txDataOffset, 32) + let from := getFrom(innerTxDataOffset) + let gasPrice := getMaxFeePerGas(innerTxDataOffset) + + debugLog("Executing L1 tx", 0) + debugLog("from", from) + debugLog("gasPrice", gasPrice) + + // We assume that addresses of smart contracts on zkSync and Ethereum + // never overlap, so no need to check whether `from` is an EOA here. + debugLog("setting tx origin", from) + + setTxOrigin(from) + debugLog("setting gas price", gasPrice) + + setGasPrice(gasPrice) + + debugLog("execution itself", 0) + + let value := getValue(innerTxDataOffset) + if value { + mintEther(from, value, true) + } + + success := executeL1Tx(innerTxDataOffset, from) + + debugLog("Executing L1 ret", success) + + // If the success is zero, we will revert in order + // to revert the minting of ether to the user + if iszero(success) { + nearCallPanic() + } + } + + /// @dev Returns the ABI for nearCalls. + /// @param gasLimit The gasLimit for this nearCall + function getNearCallABI(gasLimit) -> ret { + ret := gasLimit + } + + /// @dev Used to panic from the nearCall without reverting the parent frame. + /// If you use `revert(...)`, the error will bubble up from the near call and + /// make the bootloader to revert as well. This method allows to exit the nearCall only. + function nearCallPanic() { + // Here we exhaust all the gas of the current frame. + // This will cause the execution to panic. + // Note, that it will cause only the inner call to panic. + precompileCall(gas()) + } + + /// @dev Executes the `precompileCall` opcode. + /// Since the bootloader has no implicit meaning for this opcode, + /// this method just burns gas. + function precompileCall(gasToBurn) { + // We don't care about the return value, since it is a opcode simulation + // and the return value doesn't have any meaning. + let ret := verbatim_2i_1o("precompile", 0, gasToBurn) + } + + /// @dev Returns the pointer to the latest returndata. + function returnDataPtr() -> ret { + ret := verbatim_0i_1o("get_global::ptr_return_data") + } + + + + function ZKSYNC_NEAR_CALL_ethCall( + abi, + txDataOffset, + resultPtr + ) { + let innerTxDataOffset := add(txDataOffset, 32) + let to := getTo(innerTxDataOffset) + let from := getFrom(innerTxDataOffset) + + debugLog("from: ", from) + debugLog("to: ", to) + + switch isEOA(from) + case true { + setTxOrigin(from) + } + default { + setTxOrigin(0) + } + + let dataPtr := getDataPtr(innerTxDataOffset) + markFactoryDepsForTx(innerTxDataOffset, false) + + let value := getValue(innerTxDataOffset) + + let success := msgValueSimulatorMimicCall( + to, + from, + value, + dataPtr + ) + + if iszero(success) { + // If success is 0, we need to revert + revertWithReason( + ETH_CALL_ERR_CODE(), + 1 + ) + } + + mstore(resultPtr, success) + + // Store results of the call in the memory. + if success { + let returnsize := returndatasize() + returndatacopy(0,0,returnsize) + return(0,returnsize) + } + + } + + + /// @dev Given the callee and the data to be called with, + /// this function returns whether the mimicCall should use the `isSystem` flag. + /// This flag should only be used for contract deployments and nothing else. + /// @param to The callee of the call. + /// @param dataPtr The pointer to the calldata of the transaction. + function shouldMsgValueMimicCallBeSystem(to, dataPtr) -> ret { + let dataLen := mload(dataPtr) + // Note, that this point it is not fully known whether it is indeed the selector + // of the calldata (it might not be the case if the `dataLen` < 4), but it will be checked later on + let selector := shr(224, mload(add(dataPtr, 32))) + + let isSelectorCreate := or( + eq(selector, {{CREATE_SELECTOR}}), + eq(selector, {{CREATE_ACCOUNT_SELECTOR}}) + ) + let isSelectorCreate2 := or( + eq(selector, {{CREATE2_SELECTOR}}), + eq(selector, {{CREATE2_ACCOUNT_SELECTOR}}) + ) + + // Firstly, ensure that the selector is a valid deployment function + ret := or( + isSelectorCreate, + isSelectorCreate2 + ) + // Secondly, ensure that the callee is ContractDeployer + ret := and(ret, eq(to, CONTRACT_DEPLOYER_ADDR())) + // Thirdly, ensure that the calldata is long enough to contain the selector + ret := and(ret, gt(dataLen, 3)) + } + + /// @dev Given the pointer to the calldata, the value and to + /// performs the call through the msg.value simulator. + /// @param to Which contract to call + /// @param from The `msg.sender` of the call. + /// @param value The `value` that will be used in the call. + /// @param dataPtr The pointer to the calldata of the transaction. It must store + /// the length of the calldata and the calldata itself right afterwards. + function msgValueSimulatorMimicCall(to, from, value, dataPtr) -> success { + // Only calls to the deployer system contract are allowed to be system + let isSystem := shouldMsgValueMimicCallBeSystem(to, dataPtr) + + success := mimicCallOnlyResult( + MSG_VALUE_SIMULATOR_ADDR(), + from, + dataPtr, + 0, + 1, + value, + to, + isSystem + ) + } + + /// @dev Checks whether the current frame has enough gas + /// @dev It does not use 63/64 rule and should only be called before nearCalls. + function checkEnoughGas(gasToProvide) { + debugLog("gas()", gas()) + debugLog("gasToProvide", gasToProvide) + + // Using margin of CHECK_ENOUGH_GAS_OVERHEAD gas to make sure that the operation will indeed + // have enough gas + if lt(gas(), safeAdd(gasToProvide, CHECK_ENOUGH_GAS_OVERHEAD(), "cjq")) { + revertWithReason(NOT_ENOUGH_GAS_PROVIDED_ERR_CODE(), 0) + } + } + + /// Returns the batch overhead to be paid, assuming a certain value of gasPerPubdata + function getBatchOverheadGas(gasPerPubdata) -> ret { + let computationOverhead := BATCH_OVERHEAD_L2_GAS() + let l1GasOverhead := BATCH_OVERHEAD_L1_GAS() + let l1GasPerPubdata := L1_GAS_PER_PUBDATA_BYTE() + + // Since the user specifies the amount of gas he is willing to pay for a *byte of pubdata*, + // we need to convert the number of L1 gas needed to process the batch into the equivalent number of + // pubdata to pay for. + // The difference between ceil and floor division here is negligible, + // so we prefer doing the cheaper operation for the end user + let pubdataEquivalentForL1Gas := safeDiv(l1GasOverhead, l1GasPerPubdata, "dd") + + ret := safeAdd( + computationOverhead, + safeMul(gasPerPubdata, pubdataEquivalentForL1Gas, "aa"), + "ab" + ) + } + + /// @dev This method returns the overhead that should be paid upfront by a transaction. + /// The goal of this overhead is to cover the possibility that this transaction may use up a certain + /// limited resource per batch: a single-instance circuit, etc. + /// The transaction needs to be able to pay the same % of the costs for publishing & proving the batch + /// as the % of the batch's limited resources that it can consume. + /// @param txGasLimit The gasLimit for the transaction (note, that this limit should not include the overhead). + /// @param gasPerPubdataByte The price for pubdata byte in gas. + /// @param txEncodeLen The length of the ABI-encoding of the transaction + /// @dev The % following 3 resources is taken into account when calculating the % of the batch's overhead to pay. + /// 1. The % of the maximal gas per transaction. It is assumed that `MAX_GAS_PER_TRANSACTION` gas is enough to consume all + /// the single-instance circuits. Meaning that the transaction should pay at least txGasLimit/MAX_GAS_PER_TRANSACTION part + /// of the overhead. + /// 2. Overhead for taking up the bootloader memory. The bootloader memory has a cap on its length, mainly enforced to keep the RAM requirements + /// for the node smaller. That is, the user needs to pay a share proportional to the length of the ABI encoding of the transaction. + /// 3. Overhead for taking up a slot for the transaction. Since each batch has the limited number of transactions in it, the user must pay + /// at least 1/MAX_TRANSACTIONS_IN_BATCH part of the overhead. + function getTransactionUpfrontOverhead( + txGasLimit, + gasPerPubdataByte, + txEncodeLen + ) -> ret { + ret := 0 + let totalBatchOverhead := getBatchOverheadGas(gasPerPubdataByte) + debugLog("totalBatchOverhead", totalBatchOverhead) + + let overheadForCircuits := ceilDiv( + safeMul(totalBatchOverhead, txGasLimit, "ac"), + MAX_GAS_PER_TRANSACTION() + ) + ret := max(ret, overheadForCircuits) + debugLog("overheadForCircuits", overheadForCircuits) + + + let overheadForLength := ceilDiv( + safeMul(txEncodeLen, totalBatchOverhead, "ad"), + BOOTLOADER_MEMORY_FOR_TXS() + ) + ret := max(ret, overheadForLength) + debugLog("overheadForLength", overheadForLength) + + + let overheadForSlot := ceilDiv( + totalBatchOverhead, + MAX_TRANSACTIONS_IN_BATCH() + ) + ret := max(ret, overheadForSlot) + debugLog("overheadForSlot", overheadForSlot) + + /// + /// DEBUG SUPPORT START + /// + + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 13)), totalBatchOverhead) + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 14)), overheadForCircuits) + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 15)), overheadForLength) + mstore(add(DEBUG_BEGIN_BYTE(), mul(32, 16)), overheadForSlot) + + /// + /// DEBUG SUPPORT END + /// + + // In the proved batch we ensure that the gasPerPubdataByte is not zero + // to avoid the potential edge case of division by zero. In Yul, division by + // zero does not panic, but returns zero. + + if and(iszero(gasPerPubdataByte), FORBID_ZERO_GAS_PER_PUBDATA()) { + assertionError("zero gasPerPubdataByte") + } + + } + + /// @dev A method where all panics in the nearCalls get to. + /// It is needed to prevent nearCall panics from bubbling up. + function ZKSYNC_CATCH_NEAR_CALL() { + debugLog("ZKSYNC_CATCH_NEAR_CALL",0) + setHook(VM_HOOK_CATCH_NEAR_CALL()) + } + + /// @dev Prepends the selector before the txDataOffset, + /// preparing it to be used to call either `verify` or `execute`. + /// Returns the pointer to the calldata. + /// Note, that this overrides 32 bytes before the current transaction: + function prependSelector(txDataOffset, selector) -> ret { + + let calldataPtr := sub(txDataOffset, 4) + // Note, that since `mstore` stores 32 bytes at once, we need to + // actually store the selector in one word starting with the + // (txDataOffset - 32) = (calldataPtr - 28) + mstore(sub(calldataPtr, 28), selector) + + ret := calldataPtr + } + + /// @dev Returns the maximum of two numbers + function max(x, y) -> ret { + ret := y + if gt(x, y) { + ret := x + } + } + + /// @dev Returns the minimum of two numbers + function min(x, y) -> ret { + ret := y + if lt(x, y) { + ret := x + } + } + + /// @dev Returns constant that is equal to `keccak256("")` + function EMPTY_STRING_KECCAK() -> ret { + ret := 0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470 + } + + /// @dev Returns whether x <= y + function lte(x, y) -> ret { + ret := or(lt(x,y), eq(x,y)) + } + + /// @dev Checks whether an address is an account + /// @param addr The address to check + function ensureAccount(addr) { + mstore(0, {{RIGHT_PADDED_GET_ACCOUNT_VERSION_SELECTOR}}) + mstore(4, addr) + + let success := call( + gas(), + CONTRACT_DEPLOYER_ADDR(), + 0, + 0, + 36, + 0, + 32 + ) + + let supportedVersion := mload(0) + + if iszero(success) { + revertWithReason( + FAILED_TO_CHECK_ACCOUNT_ERR_CODE(), + 1 + ) + } + + // This method returns AccountAbstractVersion enum. + // Currently only two versions are supported: 1 or 0, which basically + // mean whether the contract is an account or not. + if iszero(supportedVersion) { + revertWithReason( + FROM_IS_NOT_AN_ACCOUNT_ERR_CODE(), + 0 + ) + } + } + + /// @dev Checks whether an address is an EOA (i.e. has not code deployed on it) + /// @param addr The address to check + function isEOA(addr) -> ret { + mstore(0, {{RIGHT_PADDED_GET_RAW_CODE_HASH_SELECTOR}}) + mstore(4, addr) + let success := call( + gas(), + ACCOUNT_CODE_STORAGE_ADDR(), + 0, + 0, + 36, + 0, + 32 + ) + + if iszero(success) { + // The call to the account code storage should always succeed + nearCallPanic() + } + + let rawCodeHash := mload(0) + + ret := iszero(rawCodeHash) + } + + /// @dev Calls the `payForTransaction` method of an account + function accountPayForTx(account, txDataOffset) -> success { + success := callAccountMethod({{PAY_FOR_TX_SELECTOR}}, account, txDataOffset) + } + + /// @dev Calls the `prepareForPaymaster` method of an account + function accountPrePaymaster(account, txDataOffset) -> success { + success := callAccountMethod({{PRE_PAYMASTER_SELECTOR}}, account, txDataOffset) + } + + /// @dev Calls the `validateAndPayForPaymasterTransaction` method of a paymaster + function validateAndPayForPaymasterTransaction(paymaster, txDataOffset) -> success { + success := callAccountMethod({{VALIDATE_AND_PAY_PAYMASTER}}, paymaster, txDataOffset) + } + + /// @dev Used to call a method with the following signature; + /// someName( + /// bytes32 _txHash, + /// bytes32 _suggestedSignedHash, + /// Transaction calldata _transaction + /// ) + // Note, that this method expects that the current tx hashes are already stored + // in the `CURRENT_L2_TX_HASHES` slots. + function callAccountMethod(selector, account, txDataOffset) -> success { + // Safety invariant: it is safe to override data stored under + // `txDataOffset`, since the account methods are called only using + // `callAccountMethod` or `callPostOp` methods, both of which reformat + // the contents before innerTxDataOffset (i.e. txDataOffset + 32 bytes), + // i.e. make sure that the position at the txDataOffset has valid value. + let txDataWithHashesOffset := sub(txDataOffset, 64) + + // First word contains the canonical tx hash + let currentL2TxHashesPtr := CURRENT_L2_TX_HASHES_BEGIN_BYTE() + mstore(txDataWithHashesOffset, mload(currentL2TxHashesPtr)) + + // Second word contains the suggested tx hash for verifying + // signatures. + currentL2TxHashesPtr := add(currentL2TxHashesPtr, 32) + mstore(add(txDataWithHashesOffset, 32), mload(currentL2TxHashesPtr)) + + // Third word contains the offset of the main tx data (it is always 96 in our case) + mstore(add(txDataWithHashesOffset, 64), 96) + + let calldataPtr := prependSelector(txDataWithHashesOffset, selector) + let innerTxDataOffst := add(txDataOffset, 32) + + let len := getDataLength(innerTxDataOffst) + + // Besides the length of the transaction itself, + // we also require 3 words for hashes and the offset + // of the inner tx data. + let fullLen := add(len, 100) + + // The call itself. + success := call( + gas(), // The number of gas to pass. + account, // The address to call. + 0, // The `value` to pass. + calldataPtr, // The pointer to the calldata. + fullLen, // The size of the calldata, which is 4 for the selector + the actual length of the struct. + 0, // The pointer where the returned data will be written. + 0 // The output has size of 32 (a single bool is expected) + ) + } + + /// @dev Calculates and saves the explorer hash and the suggested signed hash for the transaction. + function saveTxHashes(txDataOffset) { + let calldataPtr := prependSelector(txDataOffset, {{GET_TX_HASHES_SELECTOR}}) + let innerTxDataOffst := add(txDataOffset, 32) + + let len := getDataLength(innerTxDataOffst) + + // The first word is formal, but still required by the ABI + // We also should take into account the selector. + let fullLen := add(len, 36) + + // The call itself. + let success := call( + gas(), // The number of gas to pass. + BOOTLOADER_UTILITIES(), // The address to call. + 0, // The `value` to pass. + calldataPtr, // The pointer to the calldata. + fullLen, // The size of the calldata, which is 4 for the selector + the actual length of the struct. + CURRENT_L2_TX_HASHES_BEGIN_BYTE(), // The pointer where the returned data will be written. + 64 // The output has size of 32 (signed tx hash and explorer tx hash are expected) + ) + + if iszero(success) { + revertWithReason( + ACCOUNT_TX_VALIDATION_ERR_CODE(), + 1 + ) + } + + if iszero(eq(returndatasize(), 64)) { + assertionError("saveTxHashes: returndata invalid") + } + } + + /// @dev Encodes and calls the postOp method of the contract. + /// Note, that it *breaks* the contents of the previous transactions. + /// @param abi The near call ABI of the call + /// @param paymaster The address of the paymaster + /// @param txDataOffset The offset to the ABI-encoded Transaction struct. + /// @param txResult The status of the transaction (1 if succeeded, 0 otherwise). + /// @param maxRefundedGas The maximum number of gas the bootloader can be refunded. + /// This is the `maximum` number because it does not take into account the number of gas that + /// can be spent by the paymaster itself. + function ZKSYNC_NEAR_CALL_callPostOp(abi, paymaster, txDataOffset, txResult, maxRefundedGas) -> success { + // The postOp method has the following signature: + // function postTransaction( + // bytes calldata _context, + // Transaction calldata _transaction, + // bytes32 _txHash, + // bytes32 _suggestedSignedHash, + // ExecutionResult _txResult, + // uint256 _maxRefundedGas + // ) external payable; + // The encoding is the following: + // 1. Offset to the _context's content. (32 bytes) + // 2. Offset to the _transaction's content. (32 bytes) + // 3. _txHash (32 bytes) + // 4. _suggestedSignedHash (32 bytes) + // 5. _txResult (32 bytes) + // 6. _maxRefundedGas (32 bytes) + // 7. _context (note, that the content must be padded to 32 bytes) + // 8. _transaction + + let contextLen := mload(PAYMASTER_CONTEXT_BEGIN_BYTE()) + let paddedContextLen := lengthRoundedByWords(contextLen) + // The length of selector + the first 7 fields (with context len) + context itself. + let preTxLen := add(228, paddedContextLen) + + let innerTxDataOffset := add(txDataOffset, 32) + let calldataPtr := sub(innerTxDataOffset, preTxLen) + + { + let ptr := calldataPtr + + // Selector + mstore(ptr, {{RIGHT_PADDED_POST_TRANSACTION_SELECTOR}}) + ptr := add(ptr, 4) + + // context ptr + mstore(ptr, 192) // The context always starts at 32 * 6 position + ptr := add(ptr, 32) + + // transaction ptr + mstore(ptr, sub(innerTxDataOffset, add(calldataPtr, 4))) + ptr := add(ptr, 32) + + // tx hash + mstore(ptr, mload(CURRENT_L2_TX_HASHES_BEGIN_BYTE())) + ptr := add(ptr, 32) + + // suggested signed hash + mstore(ptr, mload(add(CURRENT_L2_TX_HASHES_BEGIN_BYTE(), 32))) + ptr := add(ptr, 32) + + // tx result + mstore(ptr, txResult) + ptr := add(ptr, 32) + + // maximal refunded gas + mstore(ptr, maxRefundedGas) + ptr := add(ptr, 32) + + // storing context itself + memCopy(PAYMASTER_CONTEXT_BEGIN_BYTE(), ptr, add(32, paddedContextLen)) + ptr := add(ptr, add(32, paddedContextLen)) + + // At this point, the ptr should reach the innerTxDataOffset. + // If not, we have done something wrong here. + if iszero(eq(ptr, innerTxDataOffset)) { + assertionError("postOp: ptr != innerTxDataOffset") + } + + // no need to store the transaction as from the innerTxDataOffset starts + // valid encoding of the transaction + } + + let calldataLen := safeAdd(preTxLen, getDataLength(innerTxDataOffset), "jiq") + + success := call( + gas(), + paymaster, + 0, + calldataPtr, + calldataLen, + 0, + 0 + ) + } + + /// @dev Copies [from..from+len] to [to..to+len] + /// Note, that len must be divisible by 32. + function memCopy(from, to, len) { + // Ensuring that len is always divisible by 32. + if mod(len, 32) { + assertionError("Memcopy with unaligned length") + } + + let finalFrom := safeAdd(from, len, "cka") + + for { } lt(from, finalFrom) { + from := add(from, 32) + to := add(to, 32) + } { + mstore(to, mload(from)) + } + } + + /// @dev Validates the transaction against the senders' account. + /// Besides ensuring that the contract agrees to a transaction, + /// this method also enforces that the nonce has been marked as used. + function accountValidateTx(txDataOffset) { + // Skipping the first 0x20 word of the ABI-encoding of the struct + let innerTxDataOffst := add(txDataOffset, 32) + let from := getFrom(innerTxDataOffst) + ensureAccount(from) + + // The nonce should be unique for each transaction. + let nonce := getNonce(innerTxDataOffst) + // Here we check that this nonce was not available before the validation step + ensureNonceUsage(from, nonce, 0) + + setHook(VM_HOOK_ACCOUNT_VALIDATION_ENTERED()) + debugLog("pre-validate",0) + debugLog("pre-validate",from) + let success := callAccountMethod({{VALIDATE_TX_SELECTOR}}, from, txDataOffset) + setHook(VM_HOOK_NO_VALIDATION_ENTERED()) + + if iszero(success) { + revertWithReason( + ACCOUNT_TX_VALIDATION_ERR_CODE(), + 1 + ) + } + + ensureCorrectAccountMagic() + + // Here we make sure that the nonce is no longer available after the validation step + ensureNonceUsage(from, nonce, 1) + } + + /// @dev Ensures that the magic returned by the validate account method is correct + /// It must be called right after the call of the account validation method to preserve the + /// correct returndatasize + function ensureCorrectAccountMagic() { + // It is expected that the returned value is ABI-encoded bytes4 magic value + // The Solidity always pads such value to 32 bytes and so we expect the magic to be + // of length 32 + if iszero(eq(32, returndatasize())) { + revertWithReason( + ACCOUNT_RETURNED_INVALID_MAGIC_ERR_CODE(), + 0 + ) + } + + // Note that it is important to copy the magic even though it is not needed if the + // `SHOULD_ENSURE_CORRECT_RETURNED_MAGIC` is false. It is never false in production + // but it is so in fee estimation and we want to preserve as many operations as + // in the original operation. + returndatacopy(0, 0, 32) + let returnedValue := mload(0) + let isMagicCorrect := eq(returnedValue, {{SUCCESSFUL_ACCOUNT_VALIDATION_MAGIC_VALUE}}) + + if and(iszero(isMagicCorrect), SHOULD_ENSURE_CORRECT_RETURNED_MAGIC()) { + revertWithReason( + ACCOUNT_RETURNED_INVALID_MAGIC_ERR_CODE(), + 0 + ) + } + } + + /// @dev Calls the KnownCodesStorage system contract to mark the factory dependencies of + /// the transaction as known. + function markFactoryDepsForTx(innerTxDataOffset, isL1Tx) { + debugLog("starting factory deps", 0) + let factoryDepsPtr := getFactoryDepsPtr(innerTxDataOffset) + let factoryDepsLength := mload(factoryDepsPtr) + + if gt(factoryDepsLength, MAX_NEW_FACTORY_DEPS()) { + assertionError("too many factory deps") + } + + let ptr := NEW_FACTORY_DEPS_BEGIN_BYTE() + // Selector + mstore(ptr, {{MARK_BATCH_AS_REPUBLISHED_SELECTOR}}) + ptr := add(ptr, 32) + + // Saving whether the dependencies should be sent on L1 + // There is no need to send them for L1 transactions, since their + // preimages are already available on L1. + mstore(ptr, iszero(isL1Tx)) + ptr := add(ptr, 32) + + // Saving the offset to array (it is always 64) + mstore(ptr, 64) + ptr := add(ptr, 32) + + // Saving the array + + // We also need to include 32 bytes for the length itself + let arrayLengthBytes := safeAdd(32, safeMul(factoryDepsLength, 32, "ag"), "af") + // Copying factory deps array + memCopy(factoryDepsPtr, ptr, arrayLengthBytes) + + let success := call( + gas(), + KNOWN_CODES_CONTRACT_ADDR(), + 0, + // Shifting by 28 to start from the selector + add(NEW_FACTORY_DEPS_BEGIN_BYTE(), 28), + // 4 (selector) + 32 (send to l1 flag) + 32 (factory deps offset)+ 32 (factory deps length) + safeAdd(100, safeMul(factoryDepsLength, 32, "op"), "ae"), + 0, + 0 + ) + + debugLog("factory deps success", success) + + if iszero(success) { + debugReturndata() + switch isL1Tx + case 1 { + revertWithReason( + FAILED_TO_MARK_FACTORY_DEPS(), + 1 + ) + } + default { + // For L2 transactions, we use near call panic + nearCallPanic() + } + } + } + + /// @dev Function responsible for executing the L1->L2 transactions. + function executeL1Tx(innerTxDataOffset, from) -> ret { + let to := getTo(innerTxDataOffset) + debugLog("to", to) + let value := getValue(innerTxDataOffset) + debugLog("value", value) + let dataPtr := getDataPtr(innerTxDataOffset) + + let dataLength := mload(dataPtr) + let data := add(dataPtr, 32) + + ret := msgValueSimulatorMimicCall( + to, + from, + value, + dataPtr + ) + + if iszero(ret) { + debugReturndata() + } + } + + /// @dev Function responsible for the execution of the L2 transaction + /// @dev Returns `true` or `false` depending on whether or not the tx has reverted. + function executeL2Tx(txDataOffset, from) -> ret { + ret := callAccountMethod({{EXECUTE_TX_SELECTOR}}, from, txDataOffset) + + if iszero(ret) { + debugReturndata() + } + } + + /// + /// zkSync-specific utilities: + /// + + /// @dev Returns an ABI that can be used for low-level + /// invocations of calls and mimicCalls + /// @param dataPtr The pointer to the calldata. + /// @param gasPassed The number of gas to be passed with the call. + /// @param shardId The shard id of the callee. Currently only `0` (Rollup) is supported. + /// @param forwardingMode The mode of how the calldata is forwarded + /// It is possible to either pass a pointer, slice of auxheap or heap. For the + /// bootloader purposes using heap (0) is enough. + /// @param isConstructorCall Whether the call should contain the isConstructor flag. + /// @param isSystemCall Whether the call should contain the isSystemCall flag. + /// @return ret The ABI + function getFarCallABI( + dataPtr, + gasPassed, + shardId, + forwardingMode, + isConstructorCall, + isSystemCall + ) -> ret { + let dataStart := add(dataPtr, 32) + let dataLength := mload(dataPtr) + + // Skip dataOffset and memoryPage, because they are always zeros + ret := or(ret, shl(64, dataStart)) + ret := or(ret, shl(96, dataLength)) + + ret := or(ret, shl(192, gasPassed)) + ret := or(ret, shl(224, forwardingMode)) + ret := or(ret, shl(232, shardId)) + ret := or(ret, shl(240, isConstructorCall)) + ret := or(ret, shl(248, isSystemCall)) + } + + /// @dev Does mimicCall without copying the returndata. + /// @param to Who to call + /// @param whoToMimic The `msg.sender` of the call + /// @param data The pointer to the calldata + /// @param isConstructor Whether the call should contain the isConstructor flag + /// @param isSystemCall Whether the call should contain the isSystem flag. + /// @param extraAbi1 The first extraAbiParam + /// @param extraAbi2 The second extraAbiParam + /// @param extraAbi3 The third extraAbiParam + /// @return ret 1 if the call was successful, 0 otherwise. + function mimicCallOnlyResult( + to, + whoToMimic, + data, + isConstructor, + isSystemCall, + extraAbi1, + extraAbi2, + extraAbi3 + ) -> ret { + let farCallAbi := getFarCallABI( + data, + gas(), + // Only rollup is supported for now + 0, + 0, + isConstructor, + isSystemCall + ) + + ret := verbatim_7i_1o("system_mimic_call", to, whoToMimic, farCallAbi, extraAbi1, extraAbi2, extraAbi3, 0) + } + + + // Extracts the required byte from the 32-byte word. + // 31 would mean the MSB, 0 would mean LSB. + function getWordByte(word, byteIdx) -> ret { + // Shift the input to the right so the required byte is LSB + ret := shr(mul(8, byteIdx), word) + // Clean everything else in the word + ret := and(ret, 0xFF) + } + + + + /// @dev Sends a L2->L1 log using L1Messengers' `sendL2ToL1Log`. + /// @param isService The isService flag of the call. + /// @param key The `key` parameter of the log. + /// @param value The `value` parameter of the log. + function sendL2LogUsingL1Messenger(isService, key, value) { + mstore(0, {{RIGHT_PADDED_SEND_L2_TO_L1_LOG_SELECTOR}}) + mstore(4, isService) + mstore(36, key) + mstore(68, value) + + let success := call( + gas(), + L1_MESSENGER_ADDR(), + 0, + 0, + 100, + 0, + 0 + ) + + if iszero(success) { + debugLog("Failed to send L1Messenger L2Log", key) + debugLog("Failed to send L1Messenger L2Log", value) + + revertWithReason(L1_MESSENGER_LOG_SENDING_FAILED_ERR_CODE(), 1) + } + } + + /// @dev Sends a native (VM) L2->L1 log. + /// @param isService The isService flag of the call. + /// @param key The `key` parameter of the log. + /// @param value The `value` parameter of the log. + function sendToL1Native(isService, key, value) { + verbatim_3i_0o("to_l1", isService, key, value) + } + + /// @notice Performs L1 Messenger pubdata "publishing" call. + /// @dev Expected to be used at the end of the batch. + function l1MessengerPublishingCall() { + let ptr := OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_BEGIN_BYTE() + debugLog("Publishing batch data to L1", 0) + // First slot (only last 4 bytes) -- selector + mstore(ptr, {{PUBLISH_PUBDATA_SELECTOR}}) + // Second slot -- offset + mstore(add(ptr, 32), 32) + setHook(VM_HOOK_PUBDATA_REQUESTED()) + // Third slot -- length of pubdata + let len := mload(add(ptr, 64)) + // 4 bytes for selector, 32 bytes for array offset and 32 bytes for array length + let fullLen := add(len, 68) + + // ptr + 28 because the function selector only takes up the last 4 bytes in the first slot. + let success := call( + gas(), + L1_MESSENGER_ADDR(), + 0, + add(ptr, 28), + fullLen, + 0, + 0 + ) + + if iszero(success) { + debugLog("Failed to publish L2Logs data", 0) + + revertWithReason(L1_MESSENGER_PUBLISHING_FAILED_ERR_CODE(), 1) + } + } + + function publishTimestampDataToL1() { + debugLog("Publishing timestamp data to L1", 0) + + mstore(0, {{RIGHT_PADDED_PUBLISH_TIMESTAMP_DATA_TO_L1_SELECTOR}}) + let success := call( + gas(), + SYSTEM_CONTEXT_ADDR(), + 0, + 0, + 4, + 0, + 0 + ) + + if iszero(success) { + debugLog("Failed publish timestamp to L1", 0) + revertWithReason(FAILED_TO_PUBLISH_TIMESTAMP_DATA_TO_L1(), 1) + } + } + + /// @notice Performs a call of a System Context + /// method that have no input parameters + function callSystemContext(paddedSelector) { + mstore(0, paddedSelector) + + let success := call( + gas(), + SYSTEM_CONTEXT_ADDR(), + 0, + 0, + 4, + 0, + 0 + ) + + if iszero(success) { + debugLog("Failed to call System Context", 0) + + revertWithReason(FAILED_TO_CALL_SYSTEM_CONTEXT_ERR_CODE(), 1) + } + } + + /// @dev Increment the number of txs in the batch + function considerNewTx() { + verbatim_0i_0o("increment_tx_counter") + + callSystemContext({{RIGHT_PADDED_INCREMENT_TX_NUMBER_IN_BLOCK_SELECTOR}}) + } + + /// @dev Set the new price per pubdata byte + function setPricePerPubdataByte(newPrice) { + verbatim_1i_0o("set_pubdata_price", newPrice) + } + + /// @dev Set the new value for the tx origin context value + function setTxOrigin(newTxOrigin) { + let success := setContextVal({{RIGHT_PADDED_SET_TX_ORIGIN}}, newTxOrigin) + + if iszero(success) { + debugLog("Failed to set txOrigin", newTxOrigin) + nearCallPanic() + } + } + + /// @dev Set the new value for the gas price value + function setGasPrice(newGasPrice) { + let success := setContextVal({{RIGHT_PADDED_SET_GAS_PRICE}}, newGasPrice) + + if iszero(success) { + debugLog("Failed to set gas price", newGasPrice) + nearCallPanic() + } + } + + /// @notice Sets the context information for the current batch. + /// @dev The SystemContext.sol system contract is responsible for validating + /// the validity of the new batch's data. + function setNewBatch(prevBatchHash, newTimestamp, newBatchNumber, baseFee) { + mstore(0, {{RIGHT_PADDED_SET_NEW_BATCH_SELECTOR}}) + mstore(4, prevBatchHash) + mstore(36, newTimestamp) + mstore(68, newBatchNumber) + mstore(100, baseFee) + + let success := call( + gas(), + SYSTEM_CONTEXT_ADDR(), + 0, + 0, + 132, + 0, + 0 + ) + + if iszero(success) { + debugLog("Failed to set new batch: ", prevBatchHash) + debugLog("Failed to set new batch: ", newTimestamp) + + revertWithReason(FAILED_TO_SET_NEW_BATCH_ERR_CODE(), 1) + } + } + + /// @notice Sets the context information for the current L2 block. + /// @param txId The index of the transaction in the batch for which to get the L2 block information. + function setL2Block(txId) { + let txL2BlockPosition := add(TX_OPERATOR_L2_BLOCK_INFO_BEGIN_BYTE(), mul(TX_OPERATOR_L2_BLOCK_INFO_SIZE_BYTES(), txId)) + + let currentL2BlockNumber := mload(txL2BlockPosition) + let currentL2BlockTimestamp := mload(add(txL2BlockPosition, 32)) + let previousL2BlockHash := mload(add(txL2BlockPosition, 64)) + let virtualBlocksToCreate := mload(add(txL2BlockPosition, 96)) + + let isFirstInBatch := iszero(txId) + + debugLog("Setting new L2 block: ", currentL2BlockNumber) + debugLog("Setting new L2 block: ", currentL2BlockTimestamp) + debugLog("Setting new L2 block: ", previousL2BlockHash) + debugLog("Setting new L2 block: ", virtualBlocksToCreate) + + mstore(0, {{RIGHT_PADDED_SET_L2_BLOCK_SELECTOR}}) + mstore(4, currentL2BlockNumber) + mstore(36, currentL2BlockTimestamp) + mstore(68, previousL2BlockHash) + mstore(100, isFirstInBatch) + mstore(132, virtualBlocksToCreate) + + let success := call( + gas(), + SYSTEM_CONTEXT_ADDR(), + 0, + 0, + 164, + 0, + 0 + ) + + if iszero(success) { + debugLog("Failed to set new L2 block: ", currentL2BlockNumber) + debugLog("Failed to set new L2 block: ", currentL2BlockTimestamp) + debugLog("Failed to set new L2 block: ", previousL2BlockHash) + debugLog("Failed to set new L2 block: ", isFirstInBatch) + + revertWithReason(FAILED_TO_SET_L2_BLOCK(), 1) + } + } + + /// @notice Appends the transaction hash to the current L2 block. + /// @param txHash The hash of the transaction to append. + /// @param isL1Tx Whether the transaction is an L1 transaction. If it is an L1 transaction, + /// and this method fails, then the bootloader execution will be explicitly reverted. + /// Otherwise, the nearCallPanic will be used to implicitly fail the validation of the transaction. + function appendTransactionHash( + txHash, + isL1Tx + ) { + debugLog("Appending tx to L2 block", txHash) + + mstore(0, {{RIGHT_PADDED_APPEND_TRANSACTION_TO_L2_BLOCK_SELECTOR}}) + mstore(4, txHash) + + let success := call( + gas(), + SYSTEM_CONTEXT_ADDR(), + 0, + 0, + 36, + 0, + 0 + ) + + if iszero(success) { + debugReturndata() + switch isL1Tx + case 1 { + revertWithReason( + FAILED_TO_APPEND_TRANSACTION_TO_L2_BLOCK(), + 1 + ) + } + default { + // For L2 transactions, we use near call panic, it will triger the validation + // step of the transaction to fail, returning a consistent error message. + nearCallPanic() + } + } + } + + + /// @notice Arbitrarily overrides the current batch information. + /// @dev It should NOT be available in the proved batch. + function unsafeOverrideBatch(newTimestamp, newBatchNumber, baseFee) { + mstore(0, {{RIGHT_PADDED_OVERRIDE_BATCH_SELECTOR}}) + mstore(4, newTimestamp) + mstore(36, newBatchNumber) + mstore(68, baseFee) + + let success := call( + gas(), + SYSTEM_CONTEXT_ADDR(), + 0, + 0, + 100, + 0, + 0 + ) + + if iszero(success) { + debugLog("Failed to override batch: ", newTimestamp) + debugLog("Failed to override batch: ", newBatchNumber) + + revertWithReason(FAILED_TO_SET_NEW_BATCH_ERR_CODE(), 1) + } + } + + + + // Checks whether the nonce `nonce` have been already used for + // account `from`. Reverts if the nonce has not been used properly. + function ensureNonceUsage(from, nonce, shouldNonceBeUsed) { + // INonceHolder.validateNonceUsage selector + mstore(0, {{RIGHT_PADDED_VALIDATE_NONCE_USAGE_SELECTOR}}) + mstore(4, from) + mstore(36, nonce) + mstore(68, shouldNonceBeUsed) + + let success := call( + gas(), + NONCE_HOLDER_ADDR(), + 0, + 0, + 100, + 0, + 0 + ) + + if iszero(success) { + revertWithReason( + ACCOUNT_TX_VALIDATION_ERR_CODE(), + 1 + ) + } + } + + /// @dev Encodes and performs a call to a method of + /// `SystemContext.sol` system contract of the roughly the following interface: + /// someMethod(uint256 val) + function setContextVal( + selector, + value, + ) -> ret { + mstore(0, selector) + mstore(4, value) + + ret := call( + gas(), + SYSTEM_CONTEXT_ADDR(), + 0, + 0, + 36, + 0, + 0 + ) + } + + // Each of the txs have the following type: + // struct Transaction { + // // The type of the transaction. + // uint256 txType; + // // The caller. + // uint256 from; + // // The callee. + // uint256 to; + // // The gasLimit to pass with the transaction. + // // It has the same meaning as Ethereum's gasLimit. + // uint256 gasLimit; + // // The maximum amount of gas the user is willing to pay for a byte of pubdata. + // uint256 gasPerPubdataByteLimit; + // // The maximum fee per gas that the user is willing to pay. + // // It is akin to EIP1559's maxFeePerGas. + // uint256 maxFeePerGas; + // // The maximum priority fee per gas that the user is willing to pay. + // // It is akin to EIP1559's maxPriorityFeePerGas. + // uint256 maxPriorityFeePerGas; + // // The transaction's paymaster. If there is no paymaster, it is equal to 0. + // uint256 paymaster; + // // The nonce of the transaction. + // uint256 nonce; + // // The value to pass with the transaction. + // uint256 value; + // // In the future, we might want to add some + // // new fields to the struct. The `txData` struct + // // is to be passed to account and any changes to its structure + // // would mean a breaking change to these accounts. In order to prevent this, + // // we should keep some fields as "reserved". + // // It is also recommended that their length is fixed, since + // // it would allow easier proof integration (in case we will need + // // some special circuit for preprocessing transactions). + // uint256[4] reserved; + // // The transaction's calldata. + // bytes data; + // // The signature of the transaction. + // bytes signature; + // // The properly formatted hashes of bytecodes that must be published on L1 + // // with the inclusion of this transaction. Note, that a bytecode has been published + // // before, the user won't pay fees for its republishing. + // bytes32[] factoryDeps; + // // The input to the paymaster. + // bytes paymasterInput; + // // Reserved dynamic type for the future use-case. Using it should be avoided, + // // But it is still here, just in case we want to enable some additional functionality. + // bytes reservedDynamic; + // } + + /// @notice Asserts the equality of two values and reverts + /// with the appropriate error message in case it doesn't hold + /// @param value1 The first value of the assertion + /// @param value2 The second value of the assertion + /// @param message The error message + function assertEq(value1, value2, message) { + switch eq(value1, value2) + case 0 { assertionError(message) } + default { } + } + + /// @notice Makes sure that the structure of the transaction is set in accordance to its type + /// @dev This function validates only L2 transactions, since the integrity of the L1->L2 + /// transactions is enforced by the L1 smart contracts. + function validateTypedTxStructure(innerTxDataOffset) { + /// Some common checks for all transactions. + let reservedDynamicLength := getReservedDynamicBytesLength(innerTxDataOffset) + if gt(reservedDynamicLength, 0) { + assertionError("non-empty reservedDynamic") + } + let txType := getTxType(innerTxDataOffset) + switch txType + case 0 { + let maxFeePerGas := getMaxFeePerGas(innerTxDataOffset) + let maxPriorityFeePerGas := getMaxPriorityFeePerGas(innerTxDataOffset) + assertEq(maxFeePerGas, maxPriorityFeePerGas, "EIP1559 params wrong") + + + + let from := getFrom(innerTxDataOffset) + let iseoa := isEOA(from) + + assertEq(iseoa, true, "Only EIP-712 can use non-EOA") + + + + + // Here, for type 0 transactions the reserved0 field is used as a marker + // whether the transaction should include chainId in its encoding. + assertEq(lte(getGasPerPubdataByteLimit(innerTxDataOffset), MAX_L2_GAS_PER_PUBDATA()), 1, "Gas per pubdata is wrong") + assertEq(getPaymaster(innerTxDataOffset), 0, "paymaster non zero") + + + + assertEq(gt(getFrom(innerTxDataOffset), MAX_SYSTEM_CONTRACT_ADDR()), 1, "from in kernel space") + + + + assertEq(getReserved1(innerTxDataOffset), 0, "reserved1 non zero") + assertEq(getReserved2(innerTxDataOffset), 0, "reserved2 non zero") + assertEq(getReserved3(innerTxDataOffset), 0, "reserved3 non zero") + assertEq(getFactoryDepsBytesLength(innerTxDataOffset), 0, "factory deps non zero") + assertEq(getPaymasterInputBytesLength(innerTxDataOffset), 0, "paymasterInput non zero") + } + case 1 { + let maxFeePerGas := getMaxFeePerGas(innerTxDataOffset) + let maxPriorityFeePerGas := getMaxPriorityFeePerGas(innerTxDataOffset) + assertEq(maxFeePerGas, maxPriorityFeePerGas, "EIP1559 params wrong") + + + + let from := getFrom(innerTxDataOffset) + let iseoa := isEOA(from) + + assertEq(iseoa, true, "Only EIP-712 can use non-EOA") + + + + + assertEq(lte(getGasPerPubdataByteLimit(innerTxDataOffset), MAX_L2_GAS_PER_PUBDATA()), 1, "Gas per pubdata is wrong") + assertEq(getPaymaster(innerTxDataOffset), 0, "paymaster non zero") + + + + assertEq(gt(getFrom(innerTxDataOffset), MAX_SYSTEM_CONTRACT_ADDR()), 1, "from in kernel space") + + + + assertEq(getReserved0(innerTxDataOffset), 0, "reserved0 non zero") + assertEq(getReserved1(innerTxDataOffset), 0, "reserved1 non zero") + assertEq(getReserved2(innerTxDataOffset), 0, "reserved2 non zero") + assertEq(getReserved3(innerTxDataOffset), 0, "reserved3 non zero") + assertEq(getFactoryDepsBytesLength(innerTxDataOffset), 0, "factory deps non zero") + assertEq(getPaymasterInputBytesLength(innerTxDataOffset), 0, "paymasterInput non zero") + } + case 2 { + assertEq(lte(getGasPerPubdataByteLimit(innerTxDataOffset), MAX_L2_GAS_PER_PUBDATA()), 1, "Gas per pubdata is wrong") + assertEq(getPaymaster(innerTxDataOffset), 0, "paymaster non zero") + + + + let from := getFrom(innerTxDataOffset) + let iseoa := isEOA(from) + + assertEq(iseoa, true, "Only EIP-712 can use non-EOA") + + + + + + + + assertEq(gt(getFrom(innerTxDataOffset), MAX_SYSTEM_CONTRACT_ADDR()), 1, "from in kernel space") + + + + assertEq(getReserved0(innerTxDataOffset), 0, "reserved0 non zero") + assertEq(getReserved1(innerTxDataOffset), 0, "reserved1 non zero") + assertEq(getReserved2(innerTxDataOffset), 0, "reserved2 non zero") + assertEq(getReserved3(innerTxDataOffset), 0, "reserved3 non zero") + assertEq(getFactoryDepsBytesLength(innerTxDataOffset), 0, "factory deps non zero") + assertEq(getPaymasterInputBytesLength(innerTxDataOffset), 0, "paymasterInput non zero") + } + case 113 { + let paymaster := getPaymaster(innerTxDataOffset) + assertEq(or(gt(paymaster, MAX_SYSTEM_CONTRACT_ADDR()), iszero(paymaster)), 1, "paymaster in kernel space") + + if iszero(paymaster) { + // Double checking that the paymasterInput is 0 if the paymaster is 0 + assertEq(getPaymasterInputBytesLength(innerTxDataOffset), 0, "paymasterInput non zero") + } + + + + assertEq(gt(getFrom(innerTxDataOffset), MAX_SYSTEM_CONTRACT_ADDR()), 1, "from in kernel space") + + + assertEq(getReserved0(innerTxDataOffset), 0, "reserved0 non zero") + assertEq(getReserved1(innerTxDataOffset), 0, "reserved1 non zero") + assertEq(getReserved2(innerTxDataOffset), 0, "reserved2 non zero") + assertEq(getReserved3(innerTxDataOffset), 0, "reserved3 non zero") + } + case 254 { + // Upgrade transaction, no need to validate as it is validated on L1. + } + case 255 { + // Double-check that the operator doesn't try to do an upgrade transaction via L1 -> L2 transaction. + assertEq(gt(getFrom(innerTxDataOffset), MAX_SYSTEM_CONTRACT_ADDR()), 1, "from in kernel space") + // L1 transaction, no need to validate as it is validated on L1. + } + default { + assertionError("Unknown tx type") + } + } + + /// + /// TransactionData utilities + /// + /// @dev The next methods are programmatically generated + /// + + function getTxType(innerTxDataOffset) -> ret { + ret := mload(innerTxDataOffset) + } + + function getFrom(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 32)) + } + + function getTo(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 64)) + } + + function getGasLimit(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 96)) + } + + function getGasPerPubdataByteLimit(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 128)) + } + + function getMaxFeePerGas(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 160)) + } + + function getMaxPriorityFeePerGas(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 192)) + } + + function getPaymaster(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 224)) + } + + function getNonce(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 256)) + } + + function getValue(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 288)) + } + + function getReserved0(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 320)) + } + + function getReserved1(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 352)) + } + + function getReserved2(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 384)) + } + + function getReserved3(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 416)) + } + + function getDataPtr(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 448)) + ret := add(innerTxDataOffset, ret) + } + + function getDataBytesLength(innerTxDataOffset) -> ret { + let ptr := getDataPtr(innerTxDataOffset) + ret := lengthRoundedByWords(mload(ptr)) + } + + function getSignaturePtr(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 480)) + ret := add(innerTxDataOffset, ret) + } + + function getSignatureBytesLength(innerTxDataOffset) -> ret { + let ptr := getSignaturePtr(innerTxDataOffset) + ret := lengthRoundedByWords(mload(ptr)) + } + + function getFactoryDepsPtr(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 512)) + ret := add(innerTxDataOffset, ret) + } + + function getFactoryDepsBytesLength(innerTxDataOffset) -> ret { + let ptr := getFactoryDepsPtr(innerTxDataOffset) + ret := safeMul(mload(ptr),32, "fwop") + } + + function getPaymasterInputPtr(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 544)) + ret := add(innerTxDataOffset, ret) + } + + function getPaymasterInputBytesLength(innerTxDataOffset) -> ret { + let ptr := getPaymasterInputPtr(innerTxDataOffset) + ret := lengthRoundedByWords(mload(ptr)) + } + + function getReservedDynamicPtr(innerTxDataOffset) -> ret { + ret := mload(add(innerTxDataOffset, 576)) + ret := add(innerTxDataOffset, ret) + } + + function getReservedDynamicBytesLength(innerTxDataOffset) -> ret { + let ptr := getReservedDynamicPtr(innerTxDataOffset) + ret := lengthRoundedByWords(mload(ptr)) + } + + /// This method checks that the transaction's structure is correct + /// and tightly packed + function validateAbiEncoding(txDataOffset) -> ret { + if iszero(eq(mload(txDataOffset), 32)) { + assertionError("Encoding offset") + } + + let innerTxDataOffset := add(txDataOffset, 32) + + let fromValue := getFrom(innerTxDataOffset) + if iszero(validateAddress(fromValue)) { + assertionError("Encoding from") + } + + let toValue := getTo(innerTxDataOffset) + if iszero(validateAddress(toValue)) { + assertionError("Encoding to") + } + + let gasLimitValue := getGasLimit(innerTxDataOffset) + if iszero(validateUint32(gasLimitValue)) { + assertionError("Encoding gasLimit") + } + + let gasPerPubdataByteLimitValue := getGasPerPubdataByteLimit(innerTxDataOffset) + if iszero(validateUint32(gasPerPubdataByteLimitValue)) { + assertionError("Encoding gasPerPubdataByteLimit") + } + + let maxFeePerGas := getMaxFeePerGas(innerTxDataOffset) + if iszero(validateUint128(maxFeePerGas)) { + assertionError("Encoding maxFeePerGas") + } + + let maxPriorityFeePerGas := getMaxPriorityFeePerGas(innerTxDataOffset) + if iszero(validateUint128(maxPriorityFeePerGas)) { + assertionError("Encoding maxPriorityFeePerGas") + } + + let paymasterValue := getPaymaster(innerTxDataOffset) + if iszero(validateAddress(paymasterValue)) { + assertionError("Encoding paymaster") + } + + let expectedDynamicLenPtr := add(innerTxDataOffset, 608) + + let dataLengthPos := getDataPtr(innerTxDataOffset) + if iszero(eq(dataLengthPos, expectedDynamicLenPtr)) { + assertionError("Encoding data") + } + expectedDynamicLenPtr := validateBytes(dataLengthPos) + + let signatureLengthPos := getSignaturePtr(innerTxDataOffset) + if iszero(eq(signatureLengthPos, expectedDynamicLenPtr)) { + assertionError("Encoding signature") + } + expectedDynamicLenPtr := validateBytes(signatureLengthPos) + + let factoryDepsLengthPos := getFactoryDepsPtr(innerTxDataOffset) + if iszero(eq(factoryDepsLengthPos, expectedDynamicLenPtr)) { + assertionError("Encoding factoryDeps") + } + expectedDynamicLenPtr := validateBytes32Array(factoryDepsLengthPos) + + let paymasterInputLengthPos := getPaymasterInputPtr(innerTxDataOffset) + if iszero(eq(paymasterInputLengthPos, expectedDynamicLenPtr)) { + assertionError("Encoding paymasterInput") + } + expectedDynamicLenPtr := validateBytes(paymasterInputLengthPos) + + let reservedDynamicLengthPos := getReservedDynamicPtr(innerTxDataOffset) + if iszero(eq(reservedDynamicLengthPos, expectedDynamicLenPtr)) { + assertionError("Encoding reservedDynamic") + } + expectedDynamicLenPtr := validateBytes(reservedDynamicLengthPos) + + ret := expectedDynamicLenPtr + } + + function getDataLength(innerTxDataOffset) -> ret { + // To get the length of the txData in bytes, we can simply + // get the number of fields * 32 + the length of the dynamic types + // in bytes. + ret := 768 + + ret := safeAdd(ret, getDataBytesLength(innerTxDataOffset), "asx") + ret := safeAdd(ret, getSignatureBytesLength(innerTxDataOffset), "qwqa") + ret := safeAdd(ret, getFactoryDepsBytesLength(innerTxDataOffset), "sic") + ret := safeAdd(ret, getPaymasterInputBytesLength(innerTxDataOffset), "tpiw") + ret := safeAdd(ret, getReservedDynamicBytesLength(innerTxDataOffset), "shy") + } + + /// + /// End of programmatically generated code + /// + + /// @dev Accepts an address and returns whether or not it is + /// a valid address + function validateAddress(addr) -> ret { + ret := lt(addr, shl(160, 1)) + } + + /// @dev Accepts an uint32 and returns whether or not it is + /// a valid uint32 + function validateUint32(x) -> ret { + ret := lt(x, shl(32,1)) + } + + /// @dev Accepts an uint32 and returns whether or not it is + /// a valid uint64 + function validateUint64(x) -> ret { + ret := lt(x, shl(64,1)) + } + + /// @dev Accepts an uint32 and returns whether or not it is + /// a valid uint64 + function validateUint128(x) -> ret { + ret := lt(x, shl(128,1)) + } + + /// Validates that the `bytes` is formed correctly + /// and returns the pointer right after the end of the bytes + function validateBytes(bytesPtr) -> bytesEnd { + let length := mload(bytesPtr) + let lastWordBytes := mod(length, 32) + + switch lastWordBytes + case 0 { + // If the length is divisible by 32, then + // the bytes occupy whole words, so there is + // nothing to validate + bytesEnd := safeAdd(bytesPtr, safeAdd(length, 32, "pol"), "aop") + } + default { + // If the length is not divisible by 32, then + // the last word is padded with zeroes, i.e. + // the last 32 - `lastWordBytes` bytes must be zeroes + // The easiest way to check this is to use AND operator + + let zeroBytes := sub(32, lastWordBytes) + // It has its first 32 - `lastWordBytes` bytes set to 255 + let mask := sub(shl(mul(zeroBytes,8),1),1) + + let fullLen := lengthRoundedByWords(length) + bytesEnd := safeAdd(bytesPtr, safeAdd(32, fullLen, "dza"), "dzp") + + let lastWord := mload(sub(bytesEnd, 32)) + + // If last word contains some unintended bits + // return 0 + if and(lastWord, mask) { + assertionError("bad bytes encoding") + } + } + } + + /// @dev Accepts the pointer to the bytes32[] array length and + /// returns the pointer right after the array's content + function validateBytes32Array(arrayPtr) -> arrayEnd { + // The bytes32[] array takes full words which may contain any content. + // Thus, there is nothing to validate. + let length := mload(arrayPtr) + arrayEnd := safeAdd(arrayPtr, safeAdd(32, safeMul(length, 32, "lop"), "asa"), "sp") + } + + /// + /// Safe math utilities + /// + + /// @dev Returns the multiplication of two unsigned integers, reverting on overflow. + function safeMul(x, y, errMsg) -> ret { + switch y + case 0 { + ret := 0 + } + default { + ret := mul(x, y) + if iszero(eq(div(ret, y), x)) { + assertionError(errMsg) + } + } + } + + /// @dev Returns the integer division of two unsigned integers. Reverts with custom message on + /// division by zero. The result is rounded towards zero. + function safeDiv(x, y, errMsg) -> ret { + if iszero(y) { + assertionError(errMsg) + } + ret := div(x, y) + } + + /// @dev Returns the addition of two unsigned integers, reverting on overflow. + function safeAdd(x, y, errMsg) -> ret { + ret := add(x, y) + if lt(ret, x) { + assertionError(errMsg) + } + } + + /// @dev Returns the subtraction of two unsigned integers, reverting on underflow. + function safeSub(x, y, errMsg) -> ret { + if gt(y, x) { + assertionError(errMsg) + } + ret := sub(x, y) + } + + /// + /// Debug utilities + /// + + /// @notice A method used to prevent optimization of x by the compiler + /// @dev This method is only used for logging purposes + function nonOptimized(x) -> ret { + // value() is always 0 in bootloader context. + ret := add(mul(callvalue(),x),x) + } + + /// @dev This method accepts the message and some 1-word data associated with it + /// It triggers a VM hook that allows the server to observe the behavior of the system. + function debugLog(msg, data) { + storeVmHookParam(0, nonOptimized(msg)) + storeVmHookParam(1, nonOptimized(data)) + setHook(nonOptimized(VM_HOOK_DEBUG_LOG())) + } + + /// @dev Triggers a hook that displays the returndata on the server side. + function debugReturndata() { + debugLog("returndataptr", returnDataPtr()) + storeVmHookParam(0, returnDataPtr()) + setHook(VM_HOOK_DEBUG_RETURNDATA()) + } + + /// @dev Triggers a hook that notifies the operator about the factual number of gas + /// refunded to the user. This is to be used by the operator to derive the correct + /// `gasUsed` in the API. + function notifyAboutRefund(refund) { + storeVmHookParam(0, nonOptimized(refund)) + setHook(VM_NOTIFY_OPERATOR_ABOUT_FINAL_REFUND()) + debugLog("refund(gas)", refund) + } + + function notifyExecutionResult(success) { + let ptr := returnDataPtr() + storeVmHookParam(0, nonOptimized(success)) + storeVmHookParam(1, nonOptimized(ptr)) + setHook(VM_HOOK_EXECUTION_RESULT()) + + debugLog("execution result: success", success) + debugLog("execution result: ptr", ptr) + } + + /// @dev Asks operator for the refund for the transaction. The function provides + /// the operator with the leftover gas found by the bootloader. + /// This function is called before the refund stage, because at that point + /// only the operator knows how close does a transaction + /// bring us to closing the batch as well as how much the transaction + /// should've spent on the pubdata/computation/etc. + /// After it is run, the operator should put the expected refund + /// into the memory slot (in the out of circuit execution). + /// Since the slot after the transaction is not touched, + /// this slot can be used in the in-circuit VM out of box. + function askOperatorForRefund(gasLeft) { + storeVmHookParam(0, nonOptimized(gasLeft)) + setHook(VM_HOOK_ASK_OPERATOR_FOR_REFUND()) + } + + /// + /// Error codes used for more correct diagnostics from the server side. + /// + + function ETH_CALL_ERR_CODE() -> ret { + ret := 0 + } + + function ACCOUNT_TX_VALIDATION_ERR_CODE() -> ret { + ret := 1 + } + + function FAILED_TO_CHARGE_FEE_ERR_CODE() -> ret { + ret := 2 + } + + function FROM_IS_NOT_AN_ACCOUNT_ERR_CODE() -> ret { + ret := 3 + } + + function FAILED_TO_CHECK_ACCOUNT_ERR_CODE() -> ret { + ret := 4 + } + + function UNACCEPTABLE_GAS_PRICE_ERR_CODE() -> ret { + ret := 5 + } + + function FAILED_TO_SET_NEW_BATCH_ERR_CODE() -> ret { + ret := 6 + } + + function PAY_FOR_TX_FAILED_ERR_CODE() -> ret { + ret := 7 + } + + function PRE_PAYMASTER_PREPARATION_FAILED_ERR_CODE() -> ret { + ret := 8 + } + + function PAYMASTER_VALIDATION_FAILED_ERR_CODE() -> ret { + ret := 9 + } + + function FAILED_TO_SEND_FEES_TO_THE_OPERATOR() -> ret { + ret := 10 + } + + function UNACCEPTABLE_PUBDATA_PRICE_ERR_CODE() -> ret { + ret := 11 + } + + function TX_VALIDATION_FAILED_ERR_CODE() -> ret { + ret := 12 + } + + function MAX_PRIORITY_FEE_PER_GAS_GREATER_THAN_MAX_FEE_PER_GAS() -> ret { + ret := 13 + } + + function BASE_FEE_GREATER_THAN_MAX_FEE_PER_GAS() -> ret { + ret := 14 + } + + function PAYMASTER_RETURNED_INVALID_CONTEXT() -> ret { + ret := 15 + } + + function PAYMASTER_RETURNED_CONTEXT_IS_TOO_LONG() -> ret { + ret := 16 + } + + function ASSERTION_ERROR() -> ret { + ret := 17 + } + + function FAILED_TO_MARK_FACTORY_DEPS() -> ret { + ret := 18 + } + + function TX_VALIDATION_OUT_OF_GAS() -> ret { + ret := 19 + } + + function NOT_ENOUGH_GAS_PROVIDED_ERR_CODE() -> ret { + ret := 20 + } + + function ACCOUNT_RETURNED_INVALID_MAGIC_ERR_CODE() -> ret { + ret := 21 + } + + function PAYMASTER_RETURNED_INVALID_MAGIC_ERR_CODE() -> ret { + ret := 22 + } + + function MINT_ETHER_FAILED_ERR_CODE() -> ret { + ret := 23 + } + + function FAILED_TO_APPEND_TRANSACTION_TO_L2_BLOCK() -> ret { + ret := 24 + } + + function FAILED_TO_SET_L2_BLOCK() -> ret { + ret := 25 + } + + function FAILED_TO_PUBLISH_TIMESTAMP_DATA_TO_L1() -> ret { + ret := 26 + } + + function L1_MESSENGER_PUBLISHING_FAILED_ERR_CODE() -> ret { + ret := 27 + } + + function L1_MESSENGER_LOG_SENDING_FAILED_ERR_CODE() -> ret { + ret := 28 + } + + function FAILED_TO_CALL_SYSTEM_CONTEXT_ERR_CODE() -> ret { + ret := 29 + } + + /// @dev Accepts a 1-word literal and returns its length in bytes + /// @param str A string literal + function getStrLen(str) -> len { + len := 0 + // The string literals are stored left-aligned. Thus, + // In order to get the length of such string, + // we shift it to the left (remove one byte to the left) until + // no more non-empty bytes are left. + for {} str {str := shl(8, str)} { + len := add(len, 1) + } + } + + // Selector of the errors used by the "require" statements in Solidity + // and the one that can be parsed by our server. + function GENERAL_ERROR_SELECTOR() -> ret { + ret := {{REVERT_ERROR_SELECTOR}} + } + + /// @notice Reverts with assertion error with the provided error string literal. + function assertionError(err) { + let ptr := 0 + + // The first byte indicates that the revert reason is an assertion error + mstore8(ptr, ASSERTION_ERROR()) + ptr := add(ptr, 1) + + // Then, we need to put the returndata in a way that is easily parsable by our + // servers + mstore(ptr, GENERAL_ERROR_SELECTOR()) + ptr := add(ptr, 4) + + // Then, goes the "data offset". It is has constant value of 32. + mstore(ptr, 32) + ptr := add(ptr, 32) + + // Then, goes the length of the string: + mstore(ptr, getStrLen(err)) + ptr := add(ptr, 32) + + // Then, we put the actual string + mstore(ptr, err) + ptr := add(ptr, 32) + + revert(0, ptr) + } + + /// @notice Accepts an error code and whether there is a need to copy returndata + /// @param errCode The code of the error + /// @param sendReturnData A flag of whether or not the returndata should be used in the + /// revert reason as well. + function revertWithReason(errCode, sendReturnData) { + let returndataLen := 1 + mstore8(0, errCode) + + if sendReturnData { + // Here we ignore all kinds of limits on the returned data, + // since the `revert` will happen shortly after. + returndataLen := add(returndataLen, returndatasize()) + returndatacopy(1, 0, returndatasize()) + } + revert(0, returndataLen) + } + + /// @notice The id of the VM hook that notifies the operator that the transaction + /// validation rules should start applying (i.e. the user should not be allowed to access + /// other users' storage, etc). + function VM_HOOK_ACCOUNT_VALIDATION_ENTERED() -> ret { + ret := 0 + } + + /// @notice The id of the VM hook that notifies the operator that the transaction + /// paymaster validation has started. + function VM_HOOK_PAYMASTER_VALIDATION_ENTERED() -> ret { + ret := 1 + } + + /// @notice The id of the VM hook that notifies the operator that the transaction's validation + /// restrictions should no longer apply. Note, that this is different from the validation ending, + /// since for instance the bootloader needs to do some actions during validation which are forbidden for users. + /// So this hook is used to notify the operator that the restrictions should be temporarily lifted. + function VM_HOOK_NO_VALIDATION_ENTERED() -> ret { + ret := 2 + } + + /// @notice The id of the VM hook that notifies the operator that the transaction's validation has ended. + function VM_HOOK_VALIDATION_STEP_ENDED() -> ret { + ret := 3 + } + + /// @notice The id of the VM hook that notifies the operator that the transaction's execution has started. + function VM_HOOK_TX_HAS_ENDED() -> ret { + ret := 4 + } + + /// @notice The id of the VM hook that is used to emit debugging logs consisting of pair . + function VM_HOOK_DEBUG_LOG() -> ret { + ret := 5 + } + + /// @notice The id of the VM hook that is used to emit debugging logs with the returndata of the latest transaction. + function VM_HOOK_DEBUG_RETURNDATA() -> ret { + ret := 6 + } + + /// @notice The id of the VM hook that is used to notify the operator about the entry into the + /// `ZKSYNC_CATCH_NEAR_CALL` function. + function VM_HOOK_CATCH_NEAR_CALL() -> ret { + ret := 7 + } + + /// @notice The id of the VM hook that is used to notify the operator about the need to put the refund for + /// the current transaction into the bootloader's memory. + function VM_HOOK_ASK_OPERATOR_FOR_REFUND() -> ret { + ret := 8 + } + + /// @notice The id of the VM hook that is used to notify the operator about the refund given to the user by the bootloader. + function VM_NOTIFY_OPERATOR_ABOUT_FINAL_REFUND() -> ret { + ret := 9 + } + + /// @notice The id of the VM hook that is used to notify the operator about the execution result of the transaction. + function VM_HOOK_EXECUTION_RESULT() -> ret { + ret := 10 + } + + /// @notice The id of the VM hook that is used to notify the operator that it needs to insert the information about the last + /// fictive miniblock. + function VM_HOOK_FINAL_L2_STATE_INFO() -> ret { + ret := 11 + } + + /// @norice The id of the VM hook that use used to notify the operator that it needs to insert the pubdata. + function VM_HOOK_PUBDATA_REQUESTED() -> ret { + ret := 12 + } + + // Need to prevent the compiler from optimizing out similar operations, + // which may have different meaning for the offline debugging + function unoptimized(val) -> ret { + ret := add(val, callvalue()) + } + + /// @notice Triggers a VM hook. + /// The server will recognize it and output corresponding logs. + function setHook(hook) { + mstore(VM_HOOK_PTR(), unoptimized(hook)) + } + + /// @notice Sets a value to a param of the vm hook. + /// @param paramId The id of the VmHook parameter. + /// @param value The value of the parameter. + /// @dev This method should be called before triggering the VM hook itself. + /// @dev It is the responsibility of the caller to never provide + /// paramId smaller than the VM_HOOK_PARAMS() + function storeVmHookParam(paramId, value) { + let offset := add(VM_HOOK_PARAMS_OFFSET(), mul(32, paramId)) + mstore(offset, unoptimized(value)) + } + + /// @dev Log key used by Executor.sol for processing. See Constants.sol::SystemLogKey enum + function chainedPriorityTxnHashLogKey() -> ret { + ret := 5 + } + + /// @dev Log key used by Executor.sol for processing. See Constants.sol::SystemLogKey enum + function numberOfLayer1TxsLogKey() -> ret { + ret := 6 + } + + /// @dev Log key used by Executor.sol for processing. See Constants.sol::SystemLogKey enum + function protocolUpgradeTxHashKey() -> ret { + ret := 7 + } + + //////////////////////////////////////////////////////////////////////////// + // Main Transaction Processing + //////////////////////////////////////////////////////////////////////////// + + /// @notice the address that will be the beneficiary of all the fees + let OPERATOR_ADDRESS := mload(0) + + let GAS_PRICE_PER_PUBDATA := 0 + + // Initializing block params + { + /// @notice The hash of the previous batch + let PREV_BATCH_HASH := mload(32) + /// @notice The timestamp of the batch being processed + let NEW_BATCH_TIMESTAMP := mload(64) + /// @notice The number of the new batch being processed. + /// While this number is deterministic for each batch, we + /// still provide it here to ensure consistency between the state + /// of the VM and the state of the operator. + let NEW_BATCH_NUMBER := mload(96) + + /// @notice The gas price on L1 for ETH. In the future, a trustless value will be enforced. + /// For now, this value is trusted to be fairly provided by the operator. + let L1_GAS_PRICE := mload(128) + + /// @notice The minimal gas price that the operator agrees upon. + /// In the future, it will have an EIP1559-like lower bound. + let FAIR_L2_GAS_PRICE := mload(160) + + /// @notice The expected base fee by the operator. + /// Just like the batch number, while calculated on the bootloader side, + /// the operator still provides it to make sure that its data is in sync. + let EXPECTED_BASE_FEE := mload(192) + + validateOperatorProvidedPrices(L1_GAS_PRICE, FAIR_L2_GAS_PRICE) + + let baseFee := 0 + + + + // This implementation of the bootloader relies on the correct version of the SystemContext + // and it can not be upgraded via a standard upgrade transaction, but needs to ensure + // correctness itself before any transaction is executed. + upgradeSystemContextIfNeeded() + + // Only for the proved batch we enforce that the baseFee proposed + // by the operator is equal to the expected one. For the playground batch, we allow + // the operator to provide any baseFee the operator wants. + baseFee, GAS_PRICE_PER_PUBDATA := getBaseFee(L1_GAS_PRICE, FAIR_L2_GAS_PRICE) + if iszero(eq(baseFee, EXPECTED_BASE_FEE)) { + debugLog("baseFee", baseFee) + debugLog("EXPECTED_BASE_FEE", EXPECTED_BASE_FEE) + assertionError("baseFee inconsistent") + } + + setNewBatch(PREV_BATCH_HASH, NEW_BATCH_TIMESTAMP, NEW_BATCH_NUMBER, EXPECTED_BASE_FEE) + + + + + + baseFee, GAS_PRICE_PER_PUBDATA := getBaseFee(L1_GAS_PRICE, FAIR_L2_GAS_PRICE) + + let SHOULD_SET_NEW_BATCH := mload(224) + + upgradeSystemContextIfNeeded() + + switch SHOULD_SET_NEW_BATCH + case 0 { + unsafeOverrideBatch(NEW_BATCH_TIMESTAMP, NEW_BATCH_NUMBER, EXPECTED_BASE_FEE) + } + default { + setNewBatch(PREV_BATCH_HASH, NEW_BATCH_TIMESTAMP, NEW_BATCH_NUMBER, EXPECTED_BASE_FEE) + } + + + } + + // Now, we iterate over all transactions, processing each of them + // one by one. + // Here, the `resultPtr` is the pointer to the memory slot, where we will write + // `true` or `false` based on whether the tx execution was successful, + + // The position at which the tx offset of the transaction should be placed + let currentExpectedTxOffset := add(TXS_IN_BATCH_LAST_PTR(), mul(MAX_POSTOP_SLOTS(), 32)) + + let txPtr := TX_DESCRIPTION_BEGIN_BYTE() + + // At the COMPRESSED_BYTECODES_BEGIN_BYTE() the pointer to the newest bytecode to be published + // is stored. + mstore(COMPRESSED_BYTECODES_BEGIN_BYTE(), add(COMPRESSED_BYTECODES_BEGIN_BYTE(), 32)) + + // At start storing keccak256("") as `chainedPriorityTxsHash` and 0 as `numberOfLayer1Txs` + mstore(PRIORITY_TXS_L1_DATA_BEGIN_BYTE(), EMPTY_STRING_KECCAK()) + mstore(add(PRIORITY_TXS_L1_DATA_BEGIN_BYTE(), 32), 0) + + // Iterating through transaction descriptions + let transactionIndex := 0 + for { + let resultPtr := RESULT_START_PTR() + } lt(txPtr, TXS_IN_BATCH_LAST_PTR()) { + txPtr := add(txPtr, TX_DESCRIPTION_SIZE()) + resultPtr := add(resultPtr, 32) + transactionIndex := add(transactionIndex, 1) + } { + let execute := mload(txPtr) + + debugLog("txPtr", txPtr) + debugLog("execute", execute) + + if iszero(execute) { + // We expect that all transactions that are executed + // are continuous in the array. + break + } + + let txDataOffset := mload(add(txPtr, 32)) + + // We strongly enforce the positions of transactions + if iszero(eq(currentExpectedTxOffset, txDataOffset)) { + debugLog("currentExpectedTxOffset", currentExpectedTxOffset) + debugLog("txDataOffset", txDataOffset) + + assertionError("Tx data offset is incorrect") + } + + currentExpectedTxOffset := validateAbiEncoding(txDataOffset) + + // Checking whether the last slot of the transaction's description + // does not go out of bounds. + if gt(sub(currentExpectedTxOffset, 32), LAST_FREE_SLOT()) { + debugLog("currentExpectedTxOffset", currentExpectedTxOffset) + debugLog("LAST_FREE_SLOT", LAST_FREE_SLOT()) + + assertionError("currentExpectedTxOffset too high") + } + + validateTypedTxStructure(add(txDataOffset, 32)) + + + { + debugLog("ethCall", 0) + processTx(txDataOffset, resultPtr, transactionIndex, 0, GAS_PRICE_PER_PUBDATA) + } + + + { + let txMeta := mload(txPtr) + let processFlags := getWordByte(txMeta, 31) + debugLog("flags", processFlags) + + + // `processFlags` argument denotes which parts of execution should be done: + // Possible values: + // 0x00: validate & execute (normal mode) + // 0x02: perform ethCall (i.e. use mimicCall to simulate the call) + + let isETHCall := eq(processFlags, 0x02) + debugLog("ethCall", isETHCall) + processTx(txDataOffset, resultPtr, transactionIndex, isETHCall, GAS_PRICE_PER_PUBDATA) + } + + // Signal to the vm that the transaction execution is complete + setHook(VM_HOOK_TX_HAS_ENDED()) + // Increment tx index within the system. + considerNewTx() + } + + // The bootloader doesn't have to pay anything + setPricePerPubdataByte(0) + + // Resetting tx.origin and gasPrice to 0, so we don't pay for + // publishing them on-chain. + setTxOrigin(0) + setGasPrice(0) + + // Transfering all the ETH received in the block to the operator + directETHTransfer( + selfbalance(), + OPERATOR_ADDRESS + ) + + // Hook that notifies that the operator should provide final information for the batch + setHook(VM_HOOK_FINAL_L2_STATE_INFO()) + + // Each batch typically ends with a special block which contains no transactions. + // So we need to have this method to reflect it in the system contracts too. + // + // The reason is that as of now our node requires that each storage write (event, etc) belongs to a particular + // L2 block. In case a batch is sealed by timeout (i.e. the resources of the batch have not been exhaused, but we need + // to seal it to assure timely finality), we need to process sending funds to the operator *after* the last + // non-empty L2 block has been already sealed. We can not override old L2 blocks, so we need to create a new empty "fictive" block for it. + // + // The other reason why we need to set this block is so that in case of empty batch (i.e. the one which has no transactions), + // the virtual block number as well as miniblock number are incremented. + setL2Block(transactionIndex) + + callSystemContext({{RIGHT_PADDED_RESET_TX_NUMBER_IN_BLOCK_SELECTOR}}) + + publishTimestampDataToL1() + + // Sending system logs (to be processed on L1) + sendToL1Native(true, chainedPriorityTxnHashLogKey(), mload(PRIORITY_TXS_L1_DATA_BEGIN_BYTE())) + sendToL1Native(true, numberOfLayer1TxsLogKey(), mload(add(PRIORITY_TXS_L1_DATA_BEGIN_BYTE(), 32))) + + l1MessengerPublishingCall() + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/bootloader/test_infra/Cargo.lock b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/Cargo.lock new file mode 100644 index 00000000..c3d586f0 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/Cargo.lock @@ -0,0 +1,5418 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "addchain" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3b2e69442aa5628ea6951fa33e24efe8313f4321a91bd729fc2f75bdfc858570" +dependencies = [ + "num-bigint 0.3.3", + "num-integer", + "num-traits", +] + +[[package]] +name = "addr2line" +version = "0.21.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a30b2e23b9e17a9f90641c7ab1549cd9b44f296d3ccbf309d2863cfe398a0cb" +dependencies = [ + "gimli", +] + +[[package]] +name = "adler" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" + +[[package]] +name = "aes" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "884391ef1066acaa41e766ba8f596341b96e93ce34f9a43e7d24bf0a0eaf0561" +dependencies = [ + "aes-soft", + "aesni", + "cipher", +] + +[[package]] +name = "aes-ctr" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7729c3cde54d67063be556aeac75a81330d802f0259500ca40cb52967f975763" +dependencies = [ + "aes-soft", + "aesni", + "cipher", + "ctr", +] + +[[package]] +name = "aes-soft" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "be14c7498ea50828a38d0e24a765ed2effe92a705885b57d029cd67d45744072" +dependencies = [ + "cipher", + "opaque-debug", +] + +[[package]] +name = "aesni" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ea2e11f5e94c2f7d386164cc2aa1f97823fed6f259e486940a71c174dd01b0ce" +dependencies = [ + "cipher", + "opaque-debug", +] + +[[package]] +name = "ahash" +version = "0.7.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fcb51a0695d8f838b1ee009b3fbf66bda078cd64590202a864a8f3e8c4315c47" +dependencies = [ + "getrandom 0.2.10", + "once_cell", + "version_check", +] + +[[package]] +name = "ahash" +version = "0.8.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2c99f64d1e06488f620f932677e24bc6e2897582980441ae90a671415bd7ec2f" +dependencies = [ + "cfg-if 1.0.0", + "once_cell", + "version_check", +] + +[[package]] +name = "aho-corasick" +version = "1.0.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0c378d78423fdad8089616f827526ee33c19f2fddbd5de1629152c9593ba4783" +dependencies = [ + "memchr", +] + +[[package]] +name = "android-tzdata" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e999941b234f3131b00bc13c22d06e8c5ff726d1b6318ac7eb276997bbb4fef0" + +[[package]] +name = "android_system_properties" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311" +dependencies = [ + "libc", +] + +[[package]] +name = "ansi_term" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d52a9bb7ec0cf484c551830a7ce27bd20d67eac647e1befb56b0be4ee39a55d2" +dependencies = [ + "winapi", +] + +[[package]] +name = "anyhow" +version = "1.0.75" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a4668cab20f66d8d020e1fbc0ebe47217433c1b6c8f2040faf858554e394ace6" + +[[package]] +name = "arr_macro" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6a105bfda48707cf19220129e78fca01e9639433ffaef4163546ed8fb04120a5" +dependencies = [ + "arr_macro_impl", + "proc-macro-hack", +] + +[[package]] +name = "arr_macro_impl" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0609c78bd572f4edc74310dfb63a01f5609d53fa8b4dd7c4d98aef3b3e8d72d1" +dependencies = [ + "proc-macro-hack", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "arrayref" +version = "0.3.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6b4930d2cb77ce62f89ee5d5289b4ac049559b1c45539271f5ed4fdc7db34545" + +[[package]] +name = "arrayvec" +version = "0.4.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cd9fd44efafa8690358b7408d253adf110036b88f55672a933f01d616ad9b1b9" +dependencies = [ + "nodrop", +] + +[[package]] +name = "arrayvec" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b" + +[[package]] +name = "arrayvec" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "96d30a06541fbafbc7f82ed10c06164cfbd2c401138f6addd8404629c4b16711" + +[[package]] +name = "async-trait" +version = "0.1.73" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bc00ceb34980c03614e35a3a4e218276a0a824e911d07651cd0d858a51e8c0f0" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "atoi" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "616896e05fc0e2649463a93a15183c6a16bf03413a7af88ef1285ddedfa9cda5" +dependencies = [ + "num-traits", +] + +[[package]] +name = "atty" +version = "0.2.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d9b39be18770d11421cdb1b9947a45dd3f37e93092cbf377614828a319d5fee8" +dependencies = [ + "hermit-abi 0.1.19", + "libc", + "winapi", +] + +[[package]] +name = "autocfg" +version = "0.1.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0dde43e75fd43e8a1bf86103336bc699aa8d17ad1be60c76c0bdfd4828e19b78" +dependencies = [ + "autocfg 1.1.0", +] + +[[package]] +name = "autocfg" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" + +[[package]] +name = "backtrace" +version = "0.3.69" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2089b7e3f35b9dd2d0ed921ead4f6d318c27680d4a5bd167b3ee120edb105837" +dependencies = [ + "addr2line", + "cc", + "cfg-if 1.0.0", + "libc", + "miniz_oxide", + "object", + "rustc-demangle", +] + +[[package]] +name = "base16ct" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "349a06037c7bf932dd7e7d1f653678b2038b9ad46a74102f1fc7bd7872678cce" + +[[package]] +name = "base64" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9e1b586273c5702936fe7b7d6896644d8be71e6314cfe09d3167c95f712589e8" + +[[package]] +name = "base64" +version = "0.21.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "414dcefbc63d77c526a76b3afcf6fbb9b5e2791c19c3aa2297733208750c6e53" + +[[package]] +name = "base64ct" +version = "1.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8c3c1a368f70d6cf7302d78f8f7093da241fb8e8807c05cc9e51a125895a6d5b" + +[[package]] +name = "bellman_ce" +version = "0.3.2" +source = "git+https://github.com/matter-labs/bellman?branch=dev#bbac0559fdc440b2331eca1c347a30559a3dd969" +dependencies = [ + "arrayvec 0.7.4", + "bit-vec", + "blake2s_const", + "blake2s_simd", + "byteorder", + "cfg-if 1.0.0", + "crossbeam 0.7.3", + "futures", + "hex", + "lazy_static", + "num_cpus", + "pairing_ce", + "rand 0.4.6", + "serde", + "smallvec", + "tiny-keccak 1.5.0", +] + +[[package]] +name = "bigdecimal" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d1e50562e37200edf7c6c43e54a08e64a5553bfb59d9c297d5572512aa517256" +dependencies = [ + "num-bigint 0.3.3", + "num-integer", + "num-traits", + "serde", +] + +[[package]] +name = "bincode" +version = "1.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b1f45e9417d87227c7a56d22e471c6206462cba514c7590c09aff4cf6d1ddcad" +dependencies = [ + "serde", +] + +[[package]] +name = "bindgen" +version = "0.65.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cfdf7b466f9a4903edc73f95d6d2bcd5baf8ae620638762244d3f60143643cc5" +dependencies = [ + "bitflags 1.3.2", + "cexpr", + "clang-sys", + "lazy_static", + "lazycell", + "peeking_take_while", + "prettyplease", + "proc-macro2 1.0.66", + "quote 1.0.33", + "regex", + "rustc-hash", + "shlex", + "syn 2.0.31", +] + +[[package]] +name = "bit-vec" +version = "0.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "349f9b6a179ed607305526ca489b34ad0a41aed5f7980fa90eb03160b69598fb" +dependencies = [ + "serde", +] + +[[package]] +name = "bitflags" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" + +[[package]] +name = "bitflags" +version = "2.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4682ae6287fcf752ecaabbfcc7b6f9b72aa33933dc23a554d853aea8eea8635" + +[[package]] +name = "bitvec" +version = "0.20.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7774144344a4faa177370406a7ff5f1da24303817368584c6206c8303eb07848" +dependencies = [ + "funty 1.1.0", + "radium 0.6.2", + "tap", + "wyz 0.2.0", +] + +[[package]] +name = "bitvec" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1bc2832c24239b0141d5674bb9174f9d68a8b5b3f2753311927c172ca46f7e9c" +dependencies = [ + "funty 2.0.0", + "radium 0.7.0", + "tap", + "wyz 0.5.1", +] + +[[package]] +name = "blake2" +version = "0.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0a4e37d16930f5459780f5621038b6382b9bb37c19016f39fb6b5808d831f174" +dependencies = [ + "crypto-mac 0.8.0", + "digest 0.9.0", + "opaque-debug", +] + +[[package]] +name = "blake2" +version = "0.10.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "46502ad458c9a52b69d4d4d32775c788b7a1b85e8bc9d482d92250fc0e3f8efe" +dependencies = [ + "digest 0.10.7", +] + +[[package]] +name = "blake2-rfc_bellman_edition" +version = "0.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fdc60350286c7c3db13b98e91dbe5c8b6830a6821bc20af5b0c310ce94d74915" +dependencies = [ + "arrayvec 0.4.12", + "byteorder", + "constant_time_eq", +] + +[[package]] +name = "blake2s_const" +version = "0.6.0" +source = "git+https://github.com/matter-labs/bellman?branch=dev#bbac0559fdc440b2331eca1c347a30559a3dd969" +dependencies = [ + "arrayref", + "arrayvec 0.5.2", + "constant_time_eq", +] + +[[package]] +name = "blake2s_simd" +version = "0.5.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9e461a7034e85b211a4acb57ee2e6730b32912b06c08cc242243c39fc21ae6a2" +dependencies = [ + "arrayref", + "arrayvec 0.5.2", + "constant_time_eq", +] + +[[package]] +name = "block-buffer" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4152116fd6e9dadb291ae18fc1ec3575ed6d84c29642d97890f4b4a3417297e4" +dependencies = [ + "block-padding", + "generic-array", +] + +[[package]] +name = "block-buffer" +version = "0.10.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3078c7629b62d3f0439517fa394996acacc5cbc91c5a20d8c658e77abd503a71" +dependencies = [ + "generic-array", +] + +[[package]] +name = "block-modes" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "57a0e8073e8baa88212fb5823574c02ebccb395136ba9a164ab89379ec6072f0" +dependencies = [ + "block-padding", + "cipher", +] + +[[package]] +name = "block-padding" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8d696c370c750c948ada61c69a0ee2cbbb9c50b1019ddb86d9317157a99c2cae" + +[[package]] +name = "bumpalo" +version = "3.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a3e2c3daef883ecc1b5d58c15adae93470a91d425f3532ba1695849656af3fc1" + +[[package]] +name = "byte-slice-cast" +version = "1.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c3ac9f8b63eca6fd385229b3675f6cc0dc5c8a5c8a54a59d4f52ffd670d87b0c" + +[[package]] +name = "bytecount" +version = "0.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2c676a478f63e9fa2dd5368a42f28bba0d6c560b775f38583c8bbaa7fcd67c9c" + +[[package]] +name = "byteorder" +version = "1.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "14c189c53d098945499cdfa7ecc63567cf3886b3332b312a5b4585d8d3a6a610" + +[[package]] +name = "bytes" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a2bd12c1caf447e69cd4528f47f94d203fd2582878ecb9e9465484c4148a8223" + +[[package]] +name = "bzip2-sys" +version = "0.1.11+1.0.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "736a955f3fa7875102d57c82b8cac37ec45224a07fd32d58f9f7a186b6cd4cdc" +dependencies = [ + "cc", + "libc", + "pkg-config", +] + +[[package]] +name = "camino" +version = "1.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c59e92b5a388f549b863a7bea62612c09f24c8393560709a54558a9abdfb3b9c" +dependencies = [ + "serde", +] + +[[package]] +name = "cargo-platform" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2cfa25e60aea747ec7e1124f238816749faa93759c6ff5b31f1ccdda137f4479" +dependencies = [ + "serde", +] + +[[package]] +name = "cargo_metadata" +version = "0.14.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4acbb09d9ee8e23699b9634375c72795d095bf268439da88562cf9b501f181fa" +dependencies = [ + "camino", + "cargo-platform", + "semver", + "serde", + "serde_json", +] + +[[package]] +name = "cc" +version = "1.0.83" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1174fb0b6ec23863f8b971027804a42614e347eafb0a95bf0b12cdae21fc4d0" +dependencies = [ + "jobserver", + "libc", +] + +[[package]] +name = "cexpr" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6fac387a98bb7c37292057cffc56d62ecb629900026402633ae9160df93a8766" +dependencies = [ + "nom", +] + +[[package]] +name = "cfg-if" +version = "0.1.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822" + +[[package]] +name = "cfg-if" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" + +[[package]] +name = "chrono" +version = "0.4.30" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "defd4e7873dbddba6c7c91e199c7fcb946abc4a6a4ac3195400bcfb01b5de877" +dependencies = [ + "android-tzdata", + "iana-time-zone", + "js-sys", + "num-traits", + "serde", + "wasm-bindgen", + "windows-targets", +] + +[[package]] +name = "cipher" +version = "0.2.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "12f8e7987cbd042a63249497f41aed09f8e65add917ea6566effbc56578d6801" +dependencies = [ + "generic-array", +] + +[[package]] +name = "circuit_testing" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-circuit_testing.git?branch=main#164c0adac85be39ee44bd9456b2b91cdede5af80" +dependencies = [ + "bellman_ce", +] + +[[package]] +name = "clang-sys" +version = "1.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c688fc74432808e3eb684cae8830a86be1d66a2bd58e1f248ed0960a590baf6f" +dependencies = [ + "glob", + "libc", + "libloading", +] + +[[package]] +name = "clap" +version = "2.34.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a0610544180c38b88101fecf2dd634b174a62eef6946f84dfc6a7127512b381c" +dependencies = [ + "ansi_term", + "atty", + "bitflags 1.3.2", + "strsim 0.8.0", + "textwrap", + "unicode-width", + "vec_map", +] + +[[package]] +name = "cloudabi" +version = "0.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ddfc5b9aa5d4507acaf872de71051dfd0e309860e88966e1051e462a077aac4f" +dependencies = [ + "bitflags 1.3.2", +] + +[[package]] +name = "codegen" +version = "0.1.0" +source = "git+https://github.com/matter-labs/solidity_plonk_verifier.git?branch=dev#07954802c13fb087efb5874c2ce521f843d614fd" +dependencies = [ + "ethereum-types 0.14.1", + "franklin-crypto", + "handlebars", + "hex", + "paste", + "rescue_poseidon", + "serde", + "serde_derive", + "serde_json", +] + +[[package]] +name = "codegen" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ff61280aed771c3070e7dcc9e050c66f1eb1e3b96431ba66f9f74641d02fc41d" +dependencies = [ + "indexmap 1.9.3", +] + +[[package]] +name = "colored" +version = "2.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2674ec482fbc38012cf31e6c42ba0177b431a0cb6f15fe40efa5aab1bda516f6" +dependencies = [ + "is-terminal", + "lazy_static", + "windows-sys", +] + +[[package]] +name = "const-oid" +version = "0.9.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "28c122c3980598d243d63d9a704629a2d748d101f278052ff068be5a4423ab6f" + +[[package]] +name = "constant_time_eq" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "245097e9a4535ee1e3e3931fcfcd55a796a44c643e8596ff6566d68f09b87bbc" + +[[package]] +name = "convert_case" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6245d59a3e82a7fc217c5828a6692dbc6dfb63a0c8c90495621f7b9d79704a0e" + +[[package]] +name = "core-foundation" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "194a7a9e6de53fa55116934067c844d9d749312f75c6f6d0980e8c252f8c2146" +dependencies = [ + "core-foundation-sys", + "libc", +] + +[[package]] +name = "core-foundation-sys" +version = "0.8.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e496a50fda8aacccc86d7529e2c1e0892dbd0f898a6b5645b5561b89c3210efa" + +[[package]] +name = "cpufeatures" +version = "0.2.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a17b76ff3a4162b0b27f354a0c87015ddad39d35f9c0c36607a3bdd175dde1f1" +dependencies = [ + "libc", +] + +[[package]] +name = "crc" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49fc9a695bca7f35f5f4c15cddc84415f66a74ea78eef08e90c5024f2b540e23" +dependencies = [ + "crc-catalog", +] + +[[package]] +name = "crc-catalog" +version = "1.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ccaeedb56da03b09f598226e25e80088cb4cd25f316e6e4df7d695f0feeb1403" + +[[package]] +name = "crossbeam" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "69323bff1fb41c635347b8ead484a5ca6c3f11914d784170b158d8449ab07f8e" +dependencies = [ + "cfg-if 0.1.10", + "crossbeam-channel 0.4.4", + "crossbeam-deque 0.7.4", + "crossbeam-epoch 0.8.2", + "crossbeam-queue 0.2.3", + "crossbeam-utils 0.7.2", +] + +[[package]] +name = "crossbeam" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2801af0d36612ae591caa9568261fddce32ce6e08a7275ea334a06a4ad021a2c" +dependencies = [ + "cfg-if 1.0.0", + "crossbeam-channel 0.5.8", + "crossbeam-deque 0.8.3", + "crossbeam-epoch 0.9.15", + "crossbeam-queue 0.3.8", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "crossbeam-channel" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b153fe7cbef478c567df0f972e02e6d736db11affe43dfc9c56a9374d1adfb87" +dependencies = [ + "crossbeam-utils 0.7.2", + "maybe-uninit", +] + +[[package]] +name = "crossbeam-channel" +version = "0.5.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a33c2bf77f2df06183c3aa30d1e96c0695a313d4f9c453cc3762a6db39f99200" +dependencies = [ + "cfg-if 1.0.0", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "crossbeam-deque" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c20ff29ded3204c5106278a81a38f4b482636ed4fa1e6cfbeef193291beb29ed" +dependencies = [ + "crossbeam-epoch 0.8.2", + "crossbeam-utils 0.7.2", + "maybe-uninit", +] + +[[package]] +name = "crossbeam-deque" +version = "0.8.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ce6fd6f855243022dcecf8702fef0c297d4338e226845fe067f6341ad9fa0cef" +dependencies = [ + "cfg-if 1.0.0", + "crossbeam-epoch 0.9.15", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "crossbeam-epoch" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "058ed274caafc1f60c4997b5fc07bf7dc7cca454af7c6e81edffe5f33f70dace" +dependencies = [ + "autocfg 1.1.0", + "cfg-if 0.1.10", + "crossbeam-utils 0.7.2", + "lazy_static", + "maybe-uninit", + "memoffset 0.5.6", + "scopeguard", +] + +[[package]] +name = "crossbeam-epoch" +version = "0.9.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ae211234986c545741a7dc064309f67ee1e5ad243d0e48335adc0484d960bcc7" +dependencies = [ + "autocfg 1.1.0", + "cfg-if 1.0.0", + "crossbeam-utils 0.8.16", + "memoffset 0.9.0", + "scopeguard", +] + +[[package]] +name = "crossbeam-queue" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "774ba60a54c213d409d5353bda12d49cd68d14e45036a285234c8d6f91f92570" +dependencies = [ + "cfg-if 0.1.10", + "crossbeam-utils 0.7.2", + "maybe-uninit", +] + +[[package]] +name = "crossbeam-queue" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d1cfb3ea8a53f37c40dea2c7bedcbd88bdfae54f5e2175d6ecaff1c988353add" +dependencies = [ + "cfg-if 1.0.0", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "crossbeam-utils" +version = "0.7.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c3c7c73a2d1e9fc0886a08b93e98eb643461230d5f1925e4036204d5f2e261a8" +dependencies = [ + "autocfg 1.1.0", + "cfg-if 0.1.10", + "lazy_static", +] + +[[package]] +name = "crossbeam-utils" +version = "0.8.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a22b2d63d4d1dc0b7f1b6b2747dd0088008a9be28b6ddf0b1e7d335e3037294" +dependencies = [ + "cfg-if 1.0.0", +] + +[[package]] +name = "crunchy" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a81dae078cea95a014a339291cec439d2f232ebe854a9d672b796c6afafa9b7" + +[[package]] +name = "crypto-bigint" +version = "0.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ef2b4b23cddf68b89b8f8069890e8c270d54e2d5fe1b143820234805e4cb17ef" +dependencies = [ + "generic-array", + "rand_core 0.6.4", + "subtle", + "zeroize", +] + +[[package]] +name = "crypto-common" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1bfb12502f3fc46cca1bb51ac28df9d618d813cdc3d2f25b9fe775a34af26bb3" +dependencies = [ + "generic-array", + "typenum", +] + +[[package]] +name = "crypto-mac" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b584a330336237c1eecd3e94266efb216c56ed91225d634cb2991c5f3fd1aeab" +dependencies = [ + "generic-array", + "subtle", +] + +[[package]] +name = "crypto-mac" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bff07008ec701e8028e2ceb8f83f0e4274ee62bd2dbdc4fefff2e9a91824081a" +dependencies = [ + "generic-array", + "subtle", +] + +[[package]] +name = "cs_derive" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-sync_vm.git?branch=v1.3.3#e819d15b107a06a746299f98bbd9802e26eeb348" +dependencies = [ + "proc-macro-error", + "proc-macro2 1.0.66", + "quote 1.0.33", + "serde", + "syn 1.0.109", +] + +[[package]] +name = "ctr" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb4a30d54f7443bf3d6191dcd486aca19e67cb3c49fa7a06a319966346707e7f" +dependencies = [ + "cipher", +] + +[[package]] +name = "darling" +version = "0.13.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a01d95850c592940db9b8194bc39f4bc0e89dee5c4265e4b1807c34a9aba453c" +dependencies = [ + "darling_core", + "darling_macro", +] + +[[package]] +name = "darling_core" +version = "0.13.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "859d65a907b6852c9361e3185c862aae7fafd2887876799fa55f5f99dc40d610" +dependencies = [ + "fnv", + "ident_case", + "proc-macro2 1.0.66", + "quote 1.0.33", + "strsim 0.10.0", + "syn 1.0.109", +] + +[[package]] +name = "darling_macro" +version = "0.13.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c972679f83bdf9c42bd905396b6c3588a843a17f0f16dfcfa3e2c5d57441835" +dependencies = [ + "darling_core", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "dashmap" +version = "5.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "978747c1d849a7d2ee5e8adc0159961c48fb7e5db2f06af6723b80123bb53856" +dependencies = [ + "cfg-if 1.0.0", + "hashbrown 0.14.0", + "lock_api", + "once_cell", + "parking_lot_core 0.9.8", +] + +[[package]] +name = "debugid" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bef552e6f588e446098f6ba40d89ac146c8c7b64aade83c051ee00bb5d2bc18d" +dependencies = [ + "serde", + "uuid", +] + +[[package]] +name = "der" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1a467a65c5e759bce6e65eaf91cc29f466cdc57cb65777bd646872a8a1fd4de" +dependencies = [ + "const-oid", + "zeroize", +] + +[[package]] +name = "deranged" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f2696e8a945f658fd14dc3b87242e6b80cd0f36ff04ea560fa39082368847946" + +[[package]] +name = "derivative" +version = "2.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fcc3dd5e9e9c0b295d6e1e4d811fb6f157d5ffd784b8d202fc62eac8035a770b" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "derive_more" +version = "0.99.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4fb810d30a7c1953f91334de7244731fc3f3c10d7fe163338a35b9f640960321" +dependencies = [ + "convert_case", + "proc-macro2 1.0.66", + "quote 1.0.33", + "rustc_version", + "syn 1.0.109", +] + +[[package]] +name = "digest" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3dd60d1080a57a05ab032377049e0591415d2b31afd7028356dbf3cc6dcb066" +dependencies = [ + "generic-array", +] + +[[package]] +name = "digest" +version = "0.10.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9ed9a281f7bc9b7576e61468ba615a66a5c8cfdff42420a70aa82701a3b1e292" +dependencies = [ + "block-buffer 0.10.4", + "crypto-common", + "subtle", +] + +[[package]] +name = "dirs" +version = "4.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ca3aa72a6f96ea37bbc5aa912f6788242832f75369bdfdadcb0e38423f100059" +dependencies = [ + "dirs-sys", +] + +[[package]] +name = "dirs-sys" +version = "0.3.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1b1d1d91c932ef41c0f2663aa8b0ca0342d444d842c06914aa0a7e352d0bada6" +dependencies = [ + "libc", + "redox_users", + "winapi", +] + +[[package]] +name = "dotenv" +version = "0.15.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77c90badedccf4105eca100756a0b1289e191f6fcbdadd3cee1d2f614f97da8f" + +[[package]] +name = "dtoa" +version = "1.0.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dcbb2bf8e87535c23f7a8a321e364ce21462d0ff10cb6407820e8e96dfff6653" + +[[package]] +name = "ecdsa" +version = "0.14.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "413301934810f597c1d19ca71c8710e99a3f1ba28a0d2ebc01551a2daeea3c5c" +dependencies = [ + "der", + "elliptic-curve", + "rfc6979", + "signature", +] + +[[package]] +name = "either" +version = "1.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a26ae43d7bcc3b814de94796a5e736d4029efb0ee900c12e2d54c993ad1a1e07" +dependencies = [ + "serde", +] + +[[package]] +name = "elliptic-curve" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e7bb888ab5300a19b8e5bceef25ac745ad065f3c9f7efc6de1b91958110891d3" +dependencies = [ + "base16ct", + "crypto-bigint", + "der", + "digest 0.10.7", + "ff", + "generic-array", + "group", + "pkcs8", + "rand_core 0.6.4", + "sec1", + "subtle", + "zeroize", +] + +[[package]] +name = "elsa" +version = "1.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "714f766f3556b44e7e4776ad133fcc3445a489517c25c704ace411bb14790194" +dependencies = [ + "stable_deref_trait", +] + +[[package]] +name = "encoding_rs" +version = "0.8.33" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7268b386296a025e474d5140678f75d6de9493ae55a5d709eeb9dd08149945e1" +dependencies = [ + "cfg-if 1.0.0", +] + +[[package]] +name = "env_logger" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a12e6657c4c97ebab115a42dcee77225f7f482cdd841cf7088c657a42e9e00e7" +dependencies = [ + "atty", + "humantime", + "log", + "regex", + "termcolor", +] + +[[package]] +name = "envy" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f47e0157f2cb54f5ae1bd371b30a2ae4311e1c028f575cd4e81de7353215965" +dependencies = [ + "serde", +] + +[[package]] +name = "equivalent" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5" + +[[package]] +name = "errno" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "136526188508e25c6fef639d7927dfb3e0e3084488bf202267829cf7fc23dbdd" +dependencies = [ + "errno-dragonfly", + "libc", + "windows-sys", +] + +[[package]] +name = "errno-dragonfly" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "aa68f1b12764fab894d2755d2518754e71b4fd80ecfb822714a1206c2aab39bf" +dependencies = [ + "cc", + "libc", +] + +[[package]] +name = "error-chain" +version = "0.12.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2d2f06b9cac1506ece98fe3231e3cc9c4410ec3d5b1f24ae1c8946f0742cdefc" +dependencies = [ + "version_check", +] + +[[package]] +name = "ethabi" +version = "18.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7413c5f74cc903ea37386a8965a936cbeb334bd270862fdece542c1b2dcbc898" +dependencies = [ + "ethereum-types 0.14.1", + "hex", + "once_cell", + "regex", + "serde", + "serde_json", + "sha3 0.10.6", + "thiserror", + "uint", +] + +[[package]] +name = "ethbloom" +version = "0.11.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfb684ac8fa8f6c5759f788862bb22ec6fe3cb392f6bfd08e3c64b603661e3f8" +dependencies = [ + "crunchy", + "fixed-hash 0.7.0", + "impl-rlp", + "impl-serde 0.3.2", + "tiny-keccak 2.0.2", +] + +[[package]] +name = "ethbloom" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c22d4b5885b6aa2fe5e8b9329fb8d232bf739e434e6b87347c63bdd00c120f60" +dependencies = [ + "crunchy", + "fixed-hash 0.8.0", + "impl-rlp", + "impl-serde 0.4.0", + "tiny-keccak 2.0.2", +] + +[[package]] +name = "ethereum-types" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "05136f7057fe789f06e6d41d07b34e6f70d8c86e5693b60f97aaa6553553bdaf" +dependencies = [ + "ethbloom 0.11.1", + "fixed-hash 0.7.0", + "impl-rlp", + "impl-serde 0.3.2", + "primitive-types 0.10.1", + "uint", +] + +[[package]] +name = "ethereum-types" +version = "0.14.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "02d215cbf040552efcbe99a38372fe80ab9d00268e20012b79fcd0f073edd8ee" +dependencies = [ + "ethbloom 0.13.0", + "fixed-hash 0.8.0", + "impl-rlp", + "impl-serde 0.4.0", + "primitive-types 0.12.1", + "uint", +] + +[[package]] +name = "event-listener" +version = "2.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0206175f82b8d6bf6652ff7d71a1e27fd2e4efde587fd368662814d6ec1d9ce0" + +[[package]] +name = "fastrand" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6999dc1837253364c2ebb0704ba97994bd874e8f195d665c50b7548f6ea92764" + +[[package]] +name = "ff" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d013fc25338cc558c5c2cfbad646908fb23591e2404481826742b651c9af7160" +dependencies = [ + "rand_core 0.6.4", + "subtle", +] + +[[package]] +name = "ff_ce" +version = "0.14.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b538e4231443a5b9c507caee3356f016d832cf7393d2d90f03ea3180d4e3fbc" +dependencies = [ + "byteorder", + "ff_derive_ce", + "hex", + "rand 0.4.6", + "serde", +] + +[[package]] +name = "ff_derive_ce" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b96fbccd88dbb1fac4ee4a07c2fcc4ca719a74ffbd9d2b9d41d8c8eb073d8b20" +dependencies = [ + "num-bigint 0.4.4", + "num-integer", + "num-traits", + "proc-macro2 1.0.66", + "quote 1.0.33", + "serde", + "syn 1.0.109", +] + +[[package]] +name = "findshlibs" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "40b9e59cd0f7e0806cca4be089683ecb6434e602038df21fe6bf6711b2f07f64" +dependencies = [ + "cc", + "lazy_static", + "libc", + "winapi", +] + +[[package]] +name = "finl_unicode" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8fcfdc7a0362c9f4444381a9e697c79d435fe65b52a37466fc2c1184cee9edc6" + +[[package]] +name = "fixed-hash" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cfcf0ed7fe52a17a03854ec54a9f76d6d84508d1c0e66bc1793301c73fc8493c" +dependencies = [ + "byteorder", + "rand 0.8.5", + "rustc-hex", + "static_assertions", +] + +[[package]] +name = "fixed-hash" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "835c052cb0c08c1acf6ffd71c022172e18723949c8282f2b9f27efbc51e64534" +dependencies = [ + "byteorder", + "rand 0.8.5", + "rustc-hex", + "static_assertions", +] + +[[package]] +name = "fnv" +version = "1.0.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1" + +[[package]] +name = "foreign-types" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f6f339eb8adc052cd2ca78910fda869aefa38d22d5cb648e6485e4d3fc06f3b1" +dependencies = [ + "foreign-types-shared", +] + +[[package]] +name = "foreign-types-shared" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b" + +[[package]] +name = "form_urlencoded" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a62bc1cf6f830c2ec14a513a9fb124d0a213a629668a4186f329db21fe045652" +dependencies = [ + "percent-encoding", +] + +[[package]] +name = "franklin-crypto" +version = "0.0.5" +source = "git+https://github.com/matter-labs/franklin-crypto?branch=dev#5922873d25ecec827cd60420ca8cd84a188bb965" +dependencies = [ + "arr_macro", + "bellman_ce", + "bit-vec", + "blake2 0.9.2", + "blake2-rfc_bellman_edition", + "blake2s_simd", + "byteorder", + "digest 0.9.0", + "hex", + "indexmap 1.9.3", + "itertools", + "lazy_static", + "num-bigint 0.4.4", + "num-derive 0.2.5", + "num-integer", + "num-traits", + "rand 0.4.6", + "serde", + "sha2 0.9.9", + "sha3 0.9.1", + "smallvec", + "splitmut", + "tiny-keccak 1.5.0", +] + +[[package]] +name = "fuchsia-cprng" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a06f77d526c1a601b7c4cdd98f54b5eaabffc14d5f2f0296febdc7f357c6d3ba" + +[[package]] +name = "funty" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fed34cd105917e91daa4da6b3728c47b068749d6a62c59811f06ed2ac71d9da7" + +[[package]] +name = "funty" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e6d5a32815ae3f33302d95fdcb2ce17862f8c65363dcfd29360480ba1001fc9c" + +[[package]] +name = "futures" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23342abe12aba583913b2e62f22225ff9c950774065e4bfb61a19cd9770fec40" +dependencies = [ + "futures-channel", + "futures-core", + "futures-executor", + "futures-io", + "futures-sink", + "futures-task", + "futures-util", +] + +[[package]] +name = "futures-channel" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "955518d47e09b25bbebc7a18df10b81f0c766eaf4c4f1cccef2fca5f2a4fb5f2" +dependencies = [ + "futures-core", + "futures-sink", +] + +[[package]] +name = "futures-core" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4bca583b7e26f571124fe5b7561d49cb2868d79116cfa0eefce955557c6fee8c" + +[[package]] +name = "futures-executor" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ccecee823288125bd88b4d7f565c9e58e41858e47ab72e8ea2d64e93624386e0" +dependencies = [ + "futures-core", + "futures-task", + "futures-util", + "num_cpus", +] + +[[package]] +name = "futures-intrusive" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a604f7a68fbf8103337523b1fadc8ade7361ee3f112f7c680ad179651616aed5" +dependencies = [ + "futures-core", + "lock_api", + "parking_lot 0.11.2", +] + +[[package]] +name = "futures-io" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4fff74096e71ed47f8e023204cfd0aa1289cd54ae5430a9523be060cdb849964" + +[[package]] +name = "futures-macro" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "89ca545a94061b6365f2c7355b4b32bd20df3ff95f02da9329b34ccc3bd6ee72" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "futures-sink" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f43be4fe21a13b9781a69afa4985b0f6ee0e1afab2c6f454a8cf30e2b2237b6e" + +[[package]] +name = "futures-task" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "76d3d132be6c0e6aa1534069c705a74a5997a356c0dc2f86a47765e5617c5b65" + +[[package]] +name = "futures-timer" +version = "3.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e64b03909df88034c26dc1547e8970b91f98bdb65165d6a4e9110d94263dbb2c" + +[[package]] +name = "futures-util" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "26b01e40b772d54cf6c6d721c1d1abd0647a0106a12ecaa1c186273392a69533" +dependencies = [ + "futures-channel", + "futures-core", + "futures-io", + "futures-macro", + "futures-sink", + "futures-task", + "memchr", + "pin-project-lite", + "pin-utils", + "slab", +] + +[[package]] +name = "generic-array" +version = "0.14.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "85649ca51fd72272d7821adaf274ad91c288277713d9c18820d8499a7ff69e9a" +dependencies = [ + "typenum", + "version_check", +] + +[[package]] +name = "getrandom" +version = "0.1.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8fc3cb4d91f53b50155bdcfd23f6a4c39ae1969c2ae85982b135750cccaf5fce" +dependencies = [ + "cfg-if 1.0.0", + "libc", + "wasi 0.9.0+wasi-snapshot-preview1", +] + +[[package]] +name = "getrandom" +version = "0.2.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "be4136b2a15dd319360be1c07d9933517ccf0be8f16bf62a3bee4f0d618df427" +dependencies = [ + "cfg-if 1.0.0", + "libc", + "wasi 0.11.0+wasi-snapshot-preview1", +] + +[[package]] +name = "gimli" +version = "0.28.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6fb8d784f27acf97159b40fc4db5ecd8aa23b9ad5ef69cdd136d3bc80665f0c0" + +[[package]] +name = "glob" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d2fabcfbdc87f4758337ca535fb41a6d701b65693ce38287d856d1674551ec9b" + +[[package]] +name = "group" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5dfbfb3a6cfbd390d5c9564ab283a0349b9b9fcd46a706c1eb10e0db70bfbac7" +dependencies = [ + "ff", + "rand_core 0.6.4", + "subtle", +] + +[[package]] +name = "h2" +version = "0.3.21" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "91fc23aa11be92976ef4729127f1a74adf36d8436f7816b185d18df956790833" +dependencies = [ + "bytes", + "fnv", + "futures-core", + "futures-sink", + "futures-util", + "http", + "indexmap 1.9.3", + "slab", + "tokio", + "tokio-util", + "tracing", +] + +[[package]] +name = "handlebars" +version = "4.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c39b3bc2a8f715298032cf5087e58573809374b08160aa7d750582bdb82d2683" +dependencies = [ + "log", + "pest", + "pest_derive", + "serde", + "serde_json", + "thiserror", +] + +[[package]] +name = "hashbrown" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ab5ef0d4909ef3724cc8cce6ccc8572c5c817592e9285f5464f8e86f8bd3726e" +dependencies = [ + "ahash 0.7.6", +] + +[[package]] +name = "hashbrown" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" + +[[package]] +name = "hashbrown" +version = "0.14.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2c6201b9ff9fd90a5a3bac2e56a830d0caa509576f0e503818ee82c181b3437a" + +[[package]] +name = "hashlink" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7249a3129cbc1ffccd74857f81464a323a152173cdb134e0fd81bc803b29facf" +dependencies = [ + "hashbrown 0.11.2", +] + +[[package]] +name = "headers" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "06683b93020a07e3dbcf5f8c0f6d40080d725bea7936fc01ad345c01b97dc270" +dependencies = [ + "base64 0.21.3", + "bytes", + "headers-core", + "http", + "httpdate", + "mime", + "sha1", +] + +[[package]] +name = "headers-core" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e7f66481bfee273957b1f20485a4ff3362987f85b2c236580d81b4eb7a326429" +dependencies = [ + "http", +] + +[[package]] +name = "heck" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6d621efb26863f0e9924c6ac577e8275e5e6b77455db64ffa6c65c904e9e132c" +dependencies = [ + "unicode-segmentation", +] + +[[package]] +name = "heck" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8" +dependencies = [ + "unicode-segmentation", +] + +[[package]] +name = "hermit-abi" +version = "0.1.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62b467343b94ba476dcb2500d242dadbb39557df889310ac77c5d99100aaac33" +dependencies = [ + "libc", +] + +[[package]] +name = "hermit-abi" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "443144c8cdadd93ebf52ddb4056d257f5b52c04d3c804e657d19eb73fc33668b" + +[[package]] +name = "hex" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f24254aa9a54b5c858eaee2f5bccdb46aaf0e486a595ed5fd8f86ba55232a70" + +[[package]] +name = "hkdf" +version = "0.12.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "791a029f6b9fc27657f6f188ec6e5e43f6911f6f878e0dc5501396e09809d437" +dependencies = [ + "hmac 0.12.1", +] + +[[package]] +name = "hmac" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1441c6b1e930e2817404b5046f1f989899143a12bf92de603b69f4e0aee1e15" +dependencies = [ + "crypto-mac 0.10.1", + "digest 0.9.0", +] + +[[package]] +name = "hmac" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c49c37c09c17a53d937dfbb742eb3a961d65a994e6bcdcf37e7399d0cc8ab5e" +dependencies = [ + "digest 0.10.7", +] + +[[package]] +name = "hostname" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3c731c3e10504cc8ed35cfe2f1db4c9274c3d35fa486e3b31df46f068ef3e867" +dependencies = [ + "libc", + "match_cfg", + "winapi", +] + +[[package]] +name = "http" +version = "0.2.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bd6effc99afb63425aff9b05836f029929e345a6148a14b7ecd5ab67af944482" +dependencies = [ + "bytes", + "fnv", + "itoa", +] + +[[package]] +name = "http-body" +version = "0.4.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d5f38f16d184e36f2408a55281cd658ecbd3ca05cce6d6510a176eca393e26d1" +dependencies = [ + "bytes", + "http", + "pin-project-lite", +] + +[[package]] +name = "httparse" +version = "1.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d897f394bad6a705d5f4104762e116a75639e470d80901eed05a860a95cb1904" + +[[package]] +name = "httpdate" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "df3b46402a9d5adb4c86a0cf463f42e19994e3ee891101b1841f30a545cb49a9" + +[[package]] +name = "humantime" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4" + +[[package]] +name = "hyper" +version = "0.14.27" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ffb1cfd654a8219eaef89881fdb3bb3b1cdc5fa75ded05d6933b2b382e395468" +dependencies = [ + "bytes", + "futures-channel", + "futures-core", + "futures-util", + "h2", + "http", + "http-body", + "httparse", + "httpdate", + "itoa", + "pin-project-lite", + "socket2 0.4.9", + "tokio", + "tower-service", + "tracing", + "want", +] + +[[package]] +name = "hyper-rustls" +version = "0.24.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8d78e1e73ec14cf7375674f74d7dde185c8206fd9dea6fb6295e8a98098aaa97" +dependencies = [ + "futures-util", + "http", + "hyper", + "rustls", + "tokio", + "tokio-rustls", +] + +[[package]] +name = "hyper-tls" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d6183ddfa99b85da61a140bea0efc93fdf56ceaa041b37d553518030827f9905" +dependencies = [ + "bytes", + "hyper", + "native-tls", + "tokio", + "tokio-native-tls", +] + +[[package]] +name = "iana-time-zone" +version = "0.1.57" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2fad5b825842d2b38bd206f3e81d6957625fd7f0a361e345c30e01a0ae2dd613" +dependencies = [ + "android_system_properties", + "core-foundation-sys", + "iana-time-zone-haiku", + "js-sys", + "wasm-bindgen", + "windows", +] + +[[package]] +name = "iana-time-zone-haiku" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f31827a206f56af32e590ba56d5d2d085f558508192593743f16b2306495269f" +dependencies = [ + "cc", +] + +[[package]] +name = "ident_case" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +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 = "impl-codec" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "161ebdfec3c8e3b52bf61c4f3550a1eea4f9579d10dc1b936f3171ebdcd6c443" +dependencies = [ + "parity-scale-codec 2.3.1", +] + +[[package]] +name = "impl-codec" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ba6a270039626615617f3f36d15fc827041df3b78c439da2cadfa47455a77f2f" +dependencies = [ + "parity-scale-codec 3.6.5", +] + +[[package]] +name = "impl-rlp" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f28220f89297a075ddc7245cd538076ee98b01f2a9c23a53a4f1105d5a322808" +dependencies = [ + "rlp", +] + +[[package]] +name = "impl-serde" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4551f042f3438e64dbd6226b20527fc84a6e1fe65688b58746a2f53623f25f5c" +dependencies = [ + "serde", +] + +[[package]] +name = "impl-serde" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ebc88fc67028ae3db0c853baa36269d398d5f45b6982f95549ff5def78c935cd" +dependencies = [ + "serde", +] + +[[package]] +name = "impl-trait-for-tuples" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "11d7a9f6330b71fea57921c9b61c47ee6e84f72d394754eff6163ae67e7395eb" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "indexmap" +version = "1.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bd070e393353796e801d209ad339e89596eb4c8d430d18ede6a1cced8fafbd99" +dependencies = [ + "autocfg 1.1.0", + "hashbrown 0.12.3", +] + +[[package]] +name = "indexmap" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d5477fe2230a79769d8dc68e0eabf5437907c0457a5614a9e8dddb67f65eb65d" +dependencies = [ + "equivalent", + "hashbrown 0.14.0", +] + +[[package]] +name = "instant" +version = "0.1.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a5bbe824c507c5da5956355e86a746d82e0e1464f65d862cc5e71da70e94b2c" +dependencies = [ + "cfg-if 1.0.0", +] + +[[package]] +name = "ipnet" +version = "2.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "28b29a3cd74f0f4598934efe3aeba42bae0eb4680554128851ebbecb02af14e6" + +[[package]] +name = "ipnetwork" +version = "0.17.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "02c3eaab3ac0ede60ffa41add21970a7df7d91772c03383aac6c2c3d53cc716b" + +[[package]] +name = "is-terminal" +version = "0.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb0889898416213fab133e1d33a0e5858a48177452750691bde3666d0fdbaf8b" +dependencies = [ + "hermit-abi 0.3.2", + "rustix", + "windows-sys", +] + +[[package]] +name = "itertools" +version = "0.10.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b0fd2260e829bddf4cb6ea802289de2f86d6a7a690192fbe91b3f46e0f2c8473" +dependencies = [ + "either", +] + +[[package]] +name = "itoa" +version = "1.0.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "af150ab688ff2122fcef229be89cb50dd66af9e01a4ff320cc137eecc9bacc38" + +[[package]] +name = "jobserver" +version = "0.1.26" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "936cfd212a0155903bcbc060e316fb6cc7cbf2e1907329391ebadc1fe0ce77c2" +dependencies = [ + "libc", +] + +[[package]] +name = "js-sys" +version = "0.3.64" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c5f195fe497f702db0f318b07fdd68edb16955aed830df8363d837542f8f935a" +dependencies = [ + "wasm-bindgen", +] + +[[package]] +name = "jsonrpc-core" +version = "18.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "14f7f76aef2d054868398427f6c54943cf3d1caa9a7ec7d0c38d69df97a965eb" +dependencies = [ + "futures", + "futures-executor", + "futures-util", + "log", + "serde", + "serde_derive", + "serde_json", +] + +[[package]] +name = "k256" +version = "0.11.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72c1e0b51e7ec0a97369623508396067a486bd0cbed95a2659a4b863d28cfc8b" +dependencies = [ + "cfg-if 1.0.0", + "ecdsa", + "elliptic-curve", + "sha2 0.10.6", +] + +[[package]] +name = "keccak" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f6d5ed8676d904364de097082f4e7d240b571b67989ced0240f08b7f966f940" +dependencies = [ + "cpufeatures", +] + +[[package]] +name = "lazy_static" +version = "1.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" + +[[package]] +name = "lazycell" +version = "1.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "830d08ce1d1d941e6b30645f1a0eb5643013d835ce3779a5fc208261dbe10f55" + +[[package]] +name = "libc" +version = "0.2.147" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4668fb0ea861c1df094127ac5f1da3409a82116a4ba74fca2e58ef927159bb3" + +[[package]] +name = "libloading" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b67380fd3b2fbe7527a606e18729d21c6f3951633d0500574c4dc22d2d638b9f" +dependencies = [ + "cfg-if 1.0.0", + "winapi", +] + +[[package]] +name = "librocksdb-sys" +version = "0.11.0+8.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3386f101bcb4bd252d8e9d2fb41ec3b0862a15a62b478c355b2982efa469e3e" +dependencies = [ + "bindgen", + "bzip2-sys", + "cc", + "glob", + "libc", + "libz-sys", +] + +[[package]] +name = "libz-sys" +version = "1.1.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d97137b25e321a73eef1418d1d5d2eda4d77e12813f8e6dead84bc52c5870a7b" +dependencies = [ + "cc", + "pkg-config", + "vcpkg", +] + +[[package]] +name = "linkme" +version = "0.3.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9f948366ad5bb46b5514ba7a7a80643726eef08b06632592699676748c8bc33b" +dependencies = [ + "linkme-impl", +] + +[[package]] +name = "linkme-impl" +version = "0.3.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bc28438cad73dcc90ff3466fc329a9252b1b8ba668eb0d5668ba97088cf4eef0" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "linux-raw-sys" +version = "0.4.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "57bcfdad1b858c2db7c38303a6d2ad4dfaf5eb53dfeb0910128b2c26d6158503" + +[[package]] +name = "lock_api" +version = "0.4.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1cc9717a20b1bb222f333e6a92fd32f7d8a18ddc5a3191a11af45dcbf4dcd16" +dependencies = [ + "autocfg 1.1.0", + "scopeguard", +] + +[[package]] +name = "log" +version = "0.4.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b5e6163cb8c49088c2c36f57875e58ccd8c87c7427f7fbd50ea6710b2f3f2e8f" + +[[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" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8263075bb86c5a1b1427b5ae862e8889656f126e9f77c484496e8b47cf5c5558" +dependencies = [ + "regex-automata 0.1.10", +] + +[[package]] +name = "maybe-uninit" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60302e4db3a61da70c0cb7991976248362f30319e88850c487b9b95bbf059e00" + +[[package]] +name = "md-5" +version = "0.10.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6365506850d44bff6e2fbcb5176cf63650e48bd45ef2fe2665ae1570e0f4b9ca" +dependencies = [ + "digest 0.10.7", +] + +[[package]] +name = "memchr" +version = "2.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f232d6ef707e1956a43342693d2a31e72989554d58299d7a88738cc95b0d35c" + +[[package]] +name = "memoffset" +version = "0.5.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "043175f069eda7b85febe4a74abbaeff828d9f8b448515d3151a14a3542811aa" +dependencies = [ + "autocfg 1.1.0", +] + +[[package]] +name = "memoffset" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a634b1c61a95585bd15607c6ab0c4e5b226e695ff2800ba0cdccddf208c406c" +dependencies = [ + "autocfg 1.1.0", +] + +[[package]] +name = "metrics" +version = "0.21.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fde3af1a009ed76a778cb84fdef9e7dbbdf5775ae3e4cc1f434a6a307f6f76c5" +dependencies = [ + "ahash 0.8.3", + "metrics-macros", + "portable-atomic", +] + +[[package]] +name = "metrics-macros" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ddece26afd34c31585c74a4db0630c376df271c285d682d1e55012197830b6df" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "mime" +version = "0.3.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6877bb514081ee2a7ff5ef9de3281f14a4dd4bceac4c09388074a6b5df8a139a" + +[[package]] +name = "mini-moka" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23e0b72e7c9042467008b10279fc732326bd605459ae03bda88825909dd19b56" +dependencies = [ + "crossbeam-channel 0.5.8", + "crossbeam-utils 0.8.16", + "dashmap", + "skeptic", + "smallvec", + "tagptr", + "triomphe", +] + +[[package]] +name = "minimal-lexical" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a" + +[[package]] +name = "miniz_oxide" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e7810e0be55b428ada41041c41f32c9f1a42817901b4ccf45fa3d4b6561e74c7" +dependencies = [ + "adler", +] + +[[package]] +name = "mio" +version = "0.8.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "927a765cd3fc26206e66b296465fa9d3e5ab003e651c1b3c060e7956d96b19d2" +dependencies = [ + "libc", + "wasi 0.11.0+wasi-snapshot-preview1", + "windows-sys", +] + +[[package]] +name = "native-tls" +version = "0.2.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "07226173c32f2926027b63cce4bcd8076c3552846cbe7925f3aaffeac0a3b92e" +dependencies = [ + "lazy_static", + "libc", + "log", + "openssl", + "openssl-probe", + "openssl-sys", + "schannel", + "security-framework", + "security-framework-sys", + "tempfile", +] + +[[package]] +name = "nodrop" +version = "0.1.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72ef4a56884ca558e5ddb05a1d1e7e1bfd9a68d9ed024c21704cc98872dae1bb" + +[[package]] +name = "nom" +version = "7.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d273983c5a657a70a3e8f2a01329822f3b8c8172b73826411a55751e404a0a4a" +dependencies = [ + "memchr", + "minimal-lexical", +] + +[[package]] +name = "nu-ansi-term" +version = "0.46.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77a8165726e8236064dbb45459242600304b42a5ea24ee2948e18e023bf7ba84" +dependencies = [ + "overload", + "winapi", +] + +[[package]] +name = "num" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8b7a8e9be5e039e2ff869df49155f1c06bd01ade2117ec783e56ab0932b67a8f" +dependencies = [ + "num-bigint 0.3.3", + "num-complex 0.3.1", + "num-integer", + "num-iter", + "num-rational 0.3.2", + "num-traits", +] + +[[package]] +name = "num" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b05180d69e3da0e530ba2a1dae5110317e49e3b7f3d41be227dc5f92e49ee7af" +dependencies = [ + "num-bigint 0.4.4", + "num-complex 0.4.4", + "num-integer", + "num-iter", + "num-rational 0.4.1", + "num-traits", +] + +[[package]] +name = "num-bigint" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5f6f7833f2cbf2360a6cfd58cd41a53aa7a90bd4c202f5b1c7dd2ed73c57b2c3" +dependencies = [ + "autocfg 1.1.0", + "num-integer", + "num-traits", + "serde", +] + +[[package]] +name = "num-bigint" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "608e7659b5c3d7cba262d894801b9ec9d00de989e8a82bd4bef91d08da45cdc0" +dependencies = [ + "autocfg 1.1.0", + "num-integer", + "num-traits", + "serde", +] + +[[package]] +name = "num-complex" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "747d632c0c558b87dbabbe6a82f3b4ae03720d0646ac5b7b4dae89394be5f2c5" +dependencies = [ + "num-traits", + "serde", +] + +[[package]] +name = "num-complex" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1ba157ca0885411de85d6ca030ba7e2a83a28636056c7c699b07c8b6f7383214" +dependencies = [ + "num-traits", +] + +[[package]] +name = "num-derive" +version = "0.2.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eafd0b45c5537c3ba526f79d3e75120036502bebacbb3f3220914067ce39dbf2" +dependencies = [ + "proc-macro2 0.4.30", + "quote 0.6.13", + "syn 0.15.44", +] + +[[package]] +name = "num-derive" +version = "0.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "876a53fff98e03a936a674b29568b0e605f06b29372c2489ff4de23f1949743d" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "num-integer" +version = "0.1.45" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "225d3389fb3509a24c93f5c29eb6bde2586b98d9f016636dff58d7c6f7569cd9" +dependencies = [ + "autocfg 1.1.0", + "num-traits", +] + +[[package]] +name = "num-iter" +version = "0.1.43" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7d03e6c028c5dc5cac6e2dec0efda81fc887605bb3d884578bb6d6bf7514e252" +dependencies = [ + "autocfg 1.1.0", + "num-integer", + "num-traits", +] + +[[package]] +name = "num-rational" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "12ac428b1cb17fce6f731001d307d351ec70a6d202fc2e60f7d4c5e42d8f4f07" +dependencies = [ + "autocfg 1.1.0", + "num-bigint 0.3.3", + "num-integer", + "num-traits", + "serde", +] + +[[package]] +name = "num-rational" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0638a1c9d0a3c0914158145bc76cff373a75a627e6ecbfb71cbe6f453a5a19b0" +dependencies = [ + "autocfg 1.1.0", + "num-bigint 0.4.4", + "num-integer", + "num-traits", +] + +[[package]] +name = "num-traits" +version = "0.2.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f30b0abd723be7e2ffca1272140fac1a2f084c77ec3e123c192b66af1ee9e6c2" +dependencies = [ + "autocfg 1.1.0", +] + +[[package]] +name = "num_cpus" +version = "1.16.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43" +dependencies = [ + "hermit-abi 0.3.2", + "libc", +] + +[[package]] +name = "num_enum" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a015b430d3c108a207fd776d2e2196aaf8b1cf8cf93253e3a097ff3085076a1" +dependencies = [ + "num_enum_derive", +] + +[[package]] +name = "num_enum_derive" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "96667db765a921f7b295ffee8b60472b686a51d4f21c2ee4ffdb94c7013b65a6" +dependencies = [ + "proc-macro-crate", + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "object" +version = "0.32.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9cf5f9dd3933bd50a9e1f149ec995f39ae2c496d31fd772c1fd45ebc27e902b0" +dependencies = [ + "memchr", +] + +[[package]] +name = "once_cell" +version = "1.18.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dd8b5dd2ae5ed71462c540258bedcb51965123ad7e7ccf4b9a8cafaa4a63576d" + +[[package]] +name = "opaque-debug" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "624a8340c38c1b80fd549087862da4ba43e08858af025b236e509b6649fc13d5" + +[[package]] +name = "openssl" +version = "0.10.57" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bac25ee399abb46215765b1cb35bc0212377e58a061560d8b29b024fd0430e7c" +dependencies = [ + "bitflags 2.4.0", + "cfg-if 1.0.0", + "foreign-types", + "libc", + "once_cell", + "openssl-macros", + "openssl-sys", +] + +[[package]] +name = "openssl-macros" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a948666b637a0f465e8564c73e89d4dde00d72d4d473cc972f390fc3dcee7d9c" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "openssl-probe" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ff011a302c396a5197692431fc1948019154afc178baf7d8e37367442a4601cf" + +[[package]] +name = "openssl-sys" +version = "0.9.93" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "db4d56a4c0478783083cfafcc42493dd4a981d41669da64b4572a2a089b51b1d" +dependencies = [ + "cc", + "libc", + "pkg-config", + "vcpkg", +] + +[[package]] +name = "os_info" +version = "3.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "006e42d5b888366f1880eda20371fedde764ed2213dc8496f49622fa0c99cd5e" +dependencies = [ + "log", + "serde", + "winapi", +] + +[[package]] +name = "overload" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b15813163c1d831bf4a13c3610c05c0d03b39feb07f7e09fa234dac9b15aaf39" + +[[package]] +name = "pairing_ce" +version = "0.28.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "db007b21259660d025918e653508f03050bf23fb96a88601f9936329faadc597" +dependencies = [ + "byteorder", + "cfg-if 1.0.0", + "ff_ce", + "rand 0.4.6", + "serde", +] + +[[package]] +name = "parity-crypto" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4b92ea9ddac0d6e1db7c49991e7d397d34a9fd814b4c93cda53788e8eef94e35" +dependencies = [ + "aes", + "aes-ctr", + "block-modes", + "digest 0.9.0", + "ethereum-types 0.12.1", + "hmac 0.10.1", + "lazy_static", + "pbkdf2 0.7.5", + "ripemd160", + "rustc-hex", + "scrypt", + "secp256k1 0.20.3", + "sha2 0.9.9", + "subtle", + "tiny-keccak 2.0.2", + "zeroize", +] + +[[package]] +name = "parity-scale-codec" +version = "2.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "373b1a4c1338d9cd3d1fa53b3a11bdab5ab6bd80a20f7f7becd76953ae2be909" +dependencies = [ + "arrayvec 0.7.4", + "bitvec 0.20.4", + "byte-slice-cast", + "impl-trait-for-tuples", + "parity-scale-codec-derive 2.3.1", + "serde", +] + +[[package]] +name = "parity-scale-codec" +version = "3.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0dec8a8073036902368c2cdc0387e85ff9a37054d7e7c98e592145e0c92cd4fb" +dependencies = [ + "arrayvec 0.7.4", + "bitvec 1.0.1", + "byte-slice-cast", + "impl-trait-for-tuples", + "parity-scale-codec-derive 3.6.5", + "serde", +] + +[[package]] +name = "parity-scale-codec-derive" +version = "2.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1557010476e0595c9b568d16dcfb81b93cdeb157612726f5170d31aa707bed27" +dependencies = [ + "proc-macro-crate", + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "parity-scale-codec-derive" +version = "3.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "312270ee71e1cd70289dacf597cab7b207aa107d2f28191c2ae45b2ece18a260" +dependencies = [ + "proc-macro-crate", + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "parking_lot" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7d17b78036a60663b797adeaee46f5c9dfebb86948d1255007a1d6be0271ff99" +dependencies = [ + "instant", + "lock_api", + "parking_lot_core 0.8.6", +] + +[[package]] +name = "parking_lot" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f" +dependencies = [ + "lock_api", + "parking_lot_core 0.9.8", +] + +[[package]] +name = "parking_lot_core" +version = "0.8.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60a2cfe6f0ad2bfc16aefa463b497d5c7a5ecd44a23efa72aa342d90177356dc" +dependencies = [ + "cfg-if 1.0.0", + "instant", + "libc", + "redox_syscall 0.2.16", + "smallvec", + "winapi", +] + +[[package]] +name = "parking_lot_core" +version = "0.9.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "93f00c865fe7cabf650081affecd3871070f26767e7b2070a3ffae14c654b447" +dependencies = [ + "cfg-if 1.0.0", + "libc", + "redox_syscall 0.3.5", + "smallvec", + "windows-targets", +] + +[[package]] +name = "password-hash" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "54986aa4bfc9b98c6a5f40184223658d187159d7b3c6af33f2b2aa25ae1db0fa" +dependencies = [ + "base64ct", + "rand_core 0.6.4", +] + +[[package]] +name = "paste" +version = "1.0.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "de3145af08024dea9fa9914f381a17b8fc6034dfb00f3a84013f7ff43f29ed4c" + +[[package]] +name = "pbkdf2" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b3b8c0d71734018084da0c0354193a5edfb81b20d2d57a92c5b154aefc554a4a" +dependencies = [ + "crypto-mac 0.10.1", +] + +[[package]] +name = "pbkdf2" +version = "0.7.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bf916dd32dd26297907890d99dc2740e33f6bd9073965af4ccff2967962f5508" +dependencies = [ + "base64ct", + "crypto-mac 0.10.1", + "hmac 0.10.1", + "password-hash", + "sha2 0.9.9", +] + +[[package]] +name = "peeking_take_while" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "19b17cddbe7ec3f8bc800887bab5e717348c95ea2ca0b1bf0837fb964dc67099" + +[[package]] +name = "percent-encoding" +version = "2.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9b2a4787296e9989611394c33f193f676704af1686e70b8f8033ab5ba9a35a94" + +[[package]] +name = "pest" +version = "2.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d7a4d085fd991ac8d5b05a147b437791b4260b76326baf0fc60cf7c9c27ecd33" +dependencies = [ + "memchr", + "thiserror", + "ucd-trie", +] + +[[package]] +name = "pest_derive" +version = "2.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a2bee7be22ce7918f641a33f08e3f43388c7656772244e2bbb2477f44cc9021a" +dependencies = [ + "pest", + "pest_generator", +] + +[[package]] +name = "pest_generator" +version = "2.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d1511785c5e98d79a05e8a6bc34b4ac2168a0e3e92161862030ad84daa223141" +dependencies = [ + "pest", + "pest_meta", + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "pest_meta" +version = "2.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b42f0394d3123e33353ca5e1e89092e533d2cc490389f2bd6131c43c634ebc5f" +dependencies = [ + "once_cell", + "pest", + "sha2 0.10.6", +] + +[[package]] +name = "pin-project" +version = "1.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fda4ed1c6c173e3fc7a83629421152e01d7b1f9b7f65fb301e490e8cfc656422" +dependencies = [ + "pin-project-internal", +] + +[[package]] +name = "pin-project-internal" +version = "1.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4359fd9c9171ec6e8c62926d6faaf553a8dc3f64e1507e76da7911b4f6a04405" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "pin-project-lite" +version = "0.2.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8afb450f006bf6385ca15ef45d71d2288452bc3683ce2e2cacc0d18e4be60b58" + +[[package]] +name = "pin-utils" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184" + +[[package]] +name = "pkcs8" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9eca2c590a5f85da82668fa685c09ce2888b9430e83299debf1f34b65fd4a4ba" +dependencies = [ + "der", + "spki", +] + +[[package]] +name = "pkg-config" +version = "0.3.27" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "26072860ba924cbfa98ea39c8c19b4dd6a4a25423dbdf219c1eca91aa0cf6964" + +[[package]] +name = "portable-atomic" +version = "1.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "31114a898e107c51bb1609ffaf55a0e011cf6a4d7f1170d0015a165082c0338b" + +[[package]] +name = "ppv-lite86" +version = "0.2.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b40af805b3121feab8a3c29f04d8ad262fa8e0561883e7653e024ae4479e6de" + +[[package]] +name = "prettyplease" +version = "0.2.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ae005bd773ab59b4725093fd7df83fd7892f7d8eafb48dbd7de6e024e4215f9d" +dependencies = [ + "proc-macro2 1.0.66", + "syn 2.0.31", +] + +[[package]] +name = "primitive-types" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "05e4722c697a58a99d5d06a08c30821d7c082a4632198de1eaa5a6c22ef42373" +dependencies = [ + "fixed-hash 0.7.0", + "impl-codec 0.5.1", + "impl-rlp", + "impl-serde 0.3.2", + "uint", +] + +[[package]] +name = "primitive-types" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9f3486ccba82358b11a77516035647c34ba167dfa53312630de83b12bd4f3d66" +dependencies = [ + "fixed-hash 0.8.0", + "impl-codec 0.6.0", + "impl-rlp", + "impl-serde 0.4.0", + "uint", +] + +[[package]] +name = "proc-macro-crate" +version = "1.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f4c021e1093a56626774e81216a4ce732a735e5bad4868a03f3ed65ca0c3919" +dependencies = [ + "once_cell", + "toml_edit", +] + +[[package]] +name = "proc-macro-error" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "da25490ff9892aab3fcf7c36f08cfb902dd3e71ca0f9f9517bea02a73a5ce38c" +dependencies = [ + "proc-macro-error-attr", + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 1.0.109", + "version_check", +] + +[[package]] +name = "proc-macro-error-attr" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a1be40180e52ecc98ad80b184934baf3d0d29f979574e439af5a55274b35f869" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "version_check", +] + +[[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-macro2" +version = "0.4.30" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cf3d2011ab5c909338f7887f4fc896d35932e29146c12c8d01da6b22a80ba759" +dependencies = [ + "unicode-xid", +] + +[[package]] +name = "proc-macro2" +version = "1.0.66" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "18fb31db3f9bddb2ea821cde30a9f70117e3f119938b5ee630b7403aa6e2ead9" +dependencies = [ + "unicode-ident", +] + +[[package]] +name = "prometheus-client" +version = "0.21.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3c99afa9a01501019ac3a14d71d9f94050346f55ca471ce90c799a15c58f61e2" +dependencies = [ + "dtoa", + "itoa", + "parking_lot 0.12.1", + "prometheus-client-derive-encode", +] + +[[package]] +name = "prometheus-client-derive-encode" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "440f724eba9f6996b75d63681b0a92b06947f1457076d503a4d2e2c8f56442b8" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "pulldown-cmark" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77a1a2f1f0a7ecff9c31abbe177637be0e97a0aef46cf8738ece09327985d998" +dependencies = [ + "bitflags 1.3.2", + "memchr", + "unicase", +] + +[[package]] +name = "quote" +version = "0.6.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6ce23b6b870e8f94f81fb0a363d65d86675884b34a09043c81e5562f11c1f8e1" +dependencies = [ + "proc-macro2 0.4.30", +] + +[[package]] +name = "quote" +version = "1.0.33" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5267fca4496028628a95160fc423a33e8b2e6af8a5302579e322e4b520293cae" +dependencies = [ + "proc-macro2 1.0.66", +] + +[[package]] +name = "radium" +version = "0.6.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "643f8f41a8ebc4c5dc4515c82bb8abd397b527fc20fd681b7c011c2aee5d44fb" + +[[package]] +name = "radium" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dc33ff2d4973d518d823d61aa239014831e521c75da58e3df4840d3f47749d09" + +[[package]] +name = "rand" +version = "0.4.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "552840b97013b1a26992c11eac34bdd778e464601a4c2054b5f0bff7c6761293" +dependencies = [ + "fuchsia-cprng", + "libc", + "rand_core 0.3.1", + "rdrand", + "winapi", +] + +[[package]] +name = "rand" +version = "0.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6d71dacdc3c88c1fde3885a3be3fbab9f35724e6ce99467f7d9c5026132184ca" +dependencies = [ + "autocfg 0.1.8", + "libc", + "rand_chacha 0.1.1", + "rand_core 0.4.2", + "rand_hc 0.1.0", + "rand_isaac", + "rand_jitter", + "rand_os", + "rand_pcg", + "rand_xorshift", + "winapi", +] + +[[package]] +name = "rand" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6a6b1679d49b24bbfe0c803429aa1874472f50d9b363131f0e89fc356b544d03" +dependencies = [ + "rand_chacha 0.2.2", + "rand_core 0.5.1", + "rand_hc 0.2.0", +] + +[[package]] +name = "rand" +version = "0.8.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404" +dependencies = [ + "libc", + "rand_chacha 0.3.1", + "rand_core 0.6.4", +] + +[[package]] +name = "rand_chacha" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "556d3a1ca6600bfcbab7c7c91ccb085ac7fbbcd70e008a98742e7847f4f7bcef" +dependencies = [ + "autocfg 0.1.8", + "rand_core 0.3.1", +] + +[[package]] +name = "rand_chacha" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f4c8ed856279c9737206bf725bf36935d8666ead7aa69b52be55af369d193402" +dependencies = [ + "ppv-lite86", + "rand_core 0.5.1", +] + +[[package]] +name = "rand_chacha" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e6c10a63a0fa32252be49d21e7709d4d4baf8d231c2dbce1eaa8141b9b127d88" +dependencies = [ + "ppv-lite86", + "rand_core 0.6.4", +] + +[[package]] +name = "rand_core" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a6fdeb83b075e8266dcc8762c22776f6877a63111121f5f8c7411e5be7eed4b" +dependencies = [ + "rand_core 0.4.2", +] + +[[package]] +name = "rand_core" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c33a3c44ca05fa6f1807d8e6743f3824e8509beca625669633be0acbdf509dc" + +[[package]] +name = "rand_core" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "90bde5296fc891b0cef12a6d03ddccc162ce7b2aff54160af9338f8d40df6d19" +dependencies = [ + "getrandom 0.1.16", +] + +[[package]] +name = "rand_core" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c" +dependencies = [ + "getrandom 0.2.10", +] + +[[package]] +name = "rand_hc" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b40677c7be09ae76218dc623efbf7b18e34bced3f38883af07bb75630a21bc4" +dependencies = [ + "rand_core 0.3.1", +] + +[[package]] +name = "rand_hc" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ca3129af7b92a17112d59ad498c6f81eaf463253766b90396d39ea7a39d6613c" +dependencies = [ + "rand_core 0.5.1", +] + +[[package]] +name = "rand_isaac" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ded997c9d5f13925be2a6fd7e66bf1872597f759fd9dd93513dd7e92e5a5ee08" +dependencies = [ + "rand_core 0.3.1", +] + +[[package]] +name = "rand_jitter" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1166d5c91dc97b88d1decc3285bb0a99ed84b05cfd0bc2341bdf2d43fc41e39b" +dependencies = [ + "libc", + "rand_core 0.4.2", + "winapi", +] + +[[package]] +name = "rand_os" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b75f676a1e053fc562eafbb47838d67c84801e38fc1ba459e8f180deabd5071" +dependencies = [ + "cloudabi", + "fuchsia-cprng", + "libc", + "rand_core 0.4.2", + "rdrand", + "winapi", +] + +[[package]] +name = "rand_pcg" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "abf9b09b01790cfe0364f52bf32995ea3c39f4d2dd011eac241d2914146d0b44" +dependencies = [ + "autocfg 0.1.8", + "rand_core 0.4.2", +] + +[[package]] +name = "rand_xorshift" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cbf7e9e623549b0e21f6e97cf8ecf247c1a8fd2e8a992ae265314300b2455d5c" +dependencies = [ + "rand_core 0.3.1", +] + +[[package]] +name = "rayon" +version = "1.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1d2df5196e37bcc87abebc0053e20787d73847bb33134a69841207dd0a47f03b" +dependencies = [ + "either", + "rayon-core", +] + +[[package]] +name = "rayon-core" +version = "1.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4b8f95bd6966f5c87776639160a66bd8ab9895d9d4ab01ddba9fc60661aebe8d" +dependencies = [ + "crossbeam-channel 0.5.8", + "crossbeam-deque 0.8.3", + "crossbeam-utils 0.8.16", + "num_cpus", +] + +[[package]] +name = "rdrand" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "678054eb77286b51581ba43620cc911abf02758c91f93f479767aed0f90458b2" +dependencies = [ + "rand_core 0.3.1", +] + +[[package]] +name = "redox_syscall" +version = "0.2.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb5a58c1855b4b6819d59012155603f0b22ad30cad752600aadfcb695265519a" +dependencies = [ + "bitflags 1.3.2", +] + +[[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_users" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b033d837a7cf162d7993aded9304e30a83213c648b6e389db233191f891e5c2b" +dependencies = [ + "getrandom 0.2.10", + "redox_syscall 0.2.16", + "thiserror", +] + +[[package]] +name = "regex" +version = "1.9.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "697061221ea1b4a94a624f67d0ae2bfe4e22b8a17b6a192afb11046542cc8c47" +dependencies = [ + "aho-corasick", + "memchr", + "regex-automata 0.3.8", + "regex-syntax 0.7.5", +] + +[[package]] +name = "regex-automata" +version = "0.1.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c230d73fb8d8c1b9c0b3135c5142a8acee3a0558fb8db5cf1cb65f8d7862132" +dependencies = [ + "regex-syntax 0.6.29", +] + +[[package]] +name = "regex-automata" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c2f401f4955220693b56f8ec66ee9c78abffd8d1c4f23dc41a23839eb88f0795" +dependencies = [ + "aho-corasick", + "memchr", + "regex-syntax 0.7.5", +] + +[[package]] +name = "regex-syntax" +version = "0.6.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f162c6dd7b008981e4d40210aca20b4bd0f9b60ca9271061b07f78537722f2e1" + +[[package]] +name = "regex-syntax" +version = "0.7.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dbb5fb1acd8a1a18b3dd5be62d25485eb770e05afb408a9627d14d451bae12da" + +[[package]] +name = "reqwest" +version = "0.11.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3e9ad3fe7488d7e34558a2033d45a0c90b72d97b4f80705666fea71472e2e6a1" +dependencies = [ + "base64 0.21.3", + "bytes", + "encoding_rs", + "futures-core", + "futures-util", + "h2", + "http", + "http-body", + "hyper", + "hyper-rustls", + "hyper-tls", + "ipnet", + "js-sys", + "log", + "mime", + "native-tls", + "once_cell", + "percent-encoding", + "pin-project-lite", + "rustls", + "rustls-pemfile", + "serde", + "serde_json", + "serde_urlencoded", + "tokio", + "tokio-native-tls", + "tokio-rustls", + "tower-service", + "url", + "wasm-bindgen", + "wasm-bindgen-futures", + "web-sys", + "webpki-roots", + "winreg", +] + +[[package]] +name = "rescue_poseidon" +version = "0.4.1" +source = "git+https://github.com/matter-labs/rescue-poseidon#f611a3353e48cf42153e44d89ed90da9bc5934e8" +dependencies = [ + "addchain", + "arrayvec 0.7.4", + "blake2 0.10.6", + "byteorder", + "franklin-crypto", + "num-bigint 0.3.3", + "num-integer", + "num-iter", + "num-traits", + "rand 0.4.6", + "serde", + "sha3 0.9.1", + "smallvec", +] + +[[package]] +name = "rfc6979" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7743f17af12fa0b03b803ba12cd6a8d9483a587e89c69445e3909655c0b9fabb" +dependencies = [ + "crypto-bigint", + "hmac 0.12.1", + "zeroize", +] + +[[package]] +name = "ring" +version = "0.16.20" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3053cf52e236a3ed746dfc745aa9cacf1b791d846bdaf412f60a8d7d6e17c8fc" +dependencies = [ + "cc", + "libc", + "once_cell", + "spin", + "untrusted", + "web-sys", + "winapi", +] + +[[package]] +name = "ripemd160" +version = "0.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2eca4ecc81b7f313189bf73ce724400a07da2a6dac19588b03c8bd76a2dcc251" +dependencies = [ + "block-buffer 0.9.0", + "digest 0.9.0", + "opaque-debug", +] + +[[package]] +name = "rlp" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bb919243f34364b6bd2fc10ef797edbfa75f33c252e7998527479c6d6b47e1ec" +dependencies = [ + "bytes", + "rustc-hex", +] + +[[package]] +name = "rocksdb" +version = "0.21.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bb6f170a4041d50a0ce04b0d2e14916d6ca863ea2e422689a5b694395d299ffe" +dependencies = [ + "libc", + "librocksdb-sys", +] + +[[package]] +name = "rustc-demangle" +version = "0.1.23" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76" + +[[package]] +name = "rustc-hash" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "08d43f7aa6b08d49f382cde6a7982047c3426db949b1424bc4b7ec9ae12c6ce2" + +[[package]] +name = "rustc-hex" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3e75f6a532d0fd9f7f13144f392b6ad56a32696bfcd9c78f797f16bbb6f072d6" + +[[package]] +name = "rustc_version" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366" +dependencies = [ + "semver", +] + +[[package]] +name = "rustix" +version = "0.38.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c0c3dde1fc030af041adc40e79c0e7fbcf431dd24870053d187d7c66e4b87453" +dependencies = [ + "bitflags 2.4.0", + "errno", + "libc", + "linux-raw-sys", + "windows-sys", +] + +[[package]] +name = "rustls" +version = "0.21.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cd8d6c9f025a446bc4d18ad9632e69aec8f287aa84499ee335599fabd20c3fd8" +dependencies = [ + "log", + "ring", + "rustls-webpki", + "sct", +] + +[[package]] +name = "rustls-pemfile" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2d3987094b1d07b653b7dfdc3f70ce9a1da9c51ac18c1b06b662e4f9a0e9f4b2" +dependencies = [ + "base64 0.21.3", +] + +[[package]] +name = "rustls-webpki" +version = "0.101.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7d93931baf2d282fff8d3a532bbfd7653f734643161b87e3e01e59a04439bf0d" +dependencies = [ + "ring", + "untrusted", +] + +[[package]] +name = "rustversion" +version = "1.0.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7ffc183a10b4478d04cbbbfc96d0873219d962dd5accaff2ffbd4ceb7df837f4" + +[[package]] +name = "ryu" +version = "1.0.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1ad4cc8da4ef723ed60bced201181d83791ad433213d8c24efffda1eec85d741" + +[[package]] +name = "salsa20" +version = "0.7.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "399f290ffc409596022fce5ea5d4138184be4784f2b28c62c59f0d8389059a15" +dependencies = [ + "cipher", +] + +[[package]] +name = "same-file" +version = "1.0.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "93fc1dc3aaa9bfed95e02e6eadabb4baf7e3078b0bd1b4d7b6b0b68378900502" +dependencies = [ + "winapi-util", +] + +[[package]] +name = "schannel" +version = "0.1.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0c3733bf4cf7ea0880754e19cb5a462007c4a8c1914bff372ccc95b464f1df88" +dependencies = [ + "windows-sys", +] + +[[package]] +name = "scopeguard" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49" + +[[package]] +name = "scrypt" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8da492dab03f925d977776a0b7233d7b934d6dc2b94faead48928e2e9bacedb9" +dependencies = [ + "base64 0.13.1", + "hmac 0.10.1", + "pbkdf2 0.6.0", + "rand 0.7.3", + "rand_core 0.5.1", + "salsa20", + "sha2 0.9.9", + "subtle", +] + +[[package]] +name = "sct" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d53dcdb7c9f8158937a7981b48accfd39a43af418591a5d008c7b22b5e1b7ca4" +dependencies = [ + "ring", + "untrusted", +] + +[[package]] +name = "sec1" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3be24c1842290c45df0a7bf069e0c268a747ad05a192f2fd7dcfdbc1cba40928" +dependencies = [ + "base16ct", + "der", + "generic-array", + "pkcs8", + "subtle", + "zeroize", +] + +[[package]] +name = "secp256k1" +version = "0.20.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "97d03ceae636d0fed5bae6a7f4f664354c5f4fcedf6eef053fef17e49f837d0a" +dependencies = [ + "rand 0.6.5", + "secp256k1-sys 0.4.2", +] + +[[package]] +name = "secp256k1" +version = "0.27.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "25996b82292a7a57ed3508f052cfff8640d38d32018784acd714758b43da9c8f" +dependencies = [ + "secp256k1-sys 0.8.1", +] + +[[package]] +name = "secp256k1-sys" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "957da2573cde917463ece3570eab4a0b3f19de6f1646cde62e6fd3868f566036" +dependencies = [ + "cc", +] + +[[package]] +name = "secp256k1-sys" +version = "0.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "70a129b9e9efbfb223753b9163c4ab3b13cff7fd9c7f010fbac25ab4099fa07e" +dependencies = [ + "cc", +] + +[[package]] +name = "security-framework" +version = "2.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "05b64fb303737d99b81884b2c63433e9ae28abebe5eb5045dcdd175dc2ecf4de" +dependencies = [ + "bitflags 1.3.2", + "core-foundation", + "core-foundation-sys", + "libc", + "security-framework-sys", +] + +[[package]] +name = "security-framework-sys" +version = "2.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e932934257d3b408ed8f30db49d85ea163bfe74961f017f405b025af298f0c7a" +dependencies = [ + "core-foundation-sys", + "libc", +] + +[[package]] +name = "semver" +version = "1.0.18" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b0293b4b29daaf487284529cc2f5675b8e57c61f70167ba415a463651fd6a918" +dependencies = [ + "serde", +] + +[[package]] +name = "sentry" +version = "0.31.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2e95efd0cefa32028cdb9766c96de71d96671072f9fb494dc9fb84c0ef93e52b" +dependencies = [ + "httpdate", + "native-tls", + "reqwest", + "sentry-backtrace", + "sentry-contexts", + "sentry-core", + "sentry-debug-images", + "sentry-panic", + "sentry-tracing", + "tokio", + "ureq", +] + +[[package]] +name = "sentry-backtrace" +version = "0.31.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6ac2bac6f310c4c4c4bb094d1541d32ae497f8c5c23405e85492cefdfe0971a9" +dependencies = [ + "backtrace", + "once_cell", + "regex", + "sentry-core", +] + +[[package]] +name = "sentry-contexts" +version = "0.31.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c3e17295cecdbacf66c5bd38d6e1147e09e1e9d824d2d5341f76638eda02a3a" +dependencies = [ + "hostname", + "libc", + "os_info", + "rustc_version", + "sentry-core", + "uname", +] + +[[package]] +name = "sentry-core" +version = "0.31.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8339474f587f36cb110fa1ed1b64229eea6d47b0b886375579297b7e47aeb055" +dependencies = [ + "once_cell", + "rand 0.8.5", + "sentry-types", + "serde", + "serde_json", +] + +[[package]] +name = "sentry-debug-images" +version = "0.31.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1c11e7d2b809b06497a18a2e60f513206462ae2db27081dfb7be9ade1f329cc8" +dependencies = [ + "findshlibs", + "once_cell", + "sentry-core", +] + +[[package]] +name = "sentry-panic" +version = "0.31.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "875b69f506da75bd664029eafb05f8934297d2990192896d17325f066bd665b7" +dependencies = [ + "sentry-backtrace", + "sentry-core", +] + +[[package]] +name = "sentry-tracing" +version = "0.31.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "89feead9bdd116f8035e89567651340fc382db29240b6c55ef412078b08d1aa3" +dependencies = [ + "sentry-backtrace", + "sentry-core", + "tracing-core", + "tracing-subscriber", +] + +[[package]] +name = "sentry-types" +version = "0.31.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "99dc599bd6646884fc403d593cdcb9816dd67c50cff3271c01ff123617908dcd" +dependencies = [ + "debugid", + "getrandom 0.2.10", + "hex", + "serde", + "serde_json", + "thiserror", + "time", + "url", + "uuid", +] + +[[package]] +name = "serde" +version = "1.0.188" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cf9e0fcba69a370eed61bcf2b728575f726b50b55cba78064753d708ddc7549e" +dependencies = [ + "serde_derive", +] + +[[package]] +name = "serde_derive" +version = "1.0.188" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4eca7ac642d82aa35b60049a6eccb4be6be75e599bd2e9adb5f875a737654af2" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "serde_json" +version = "1.0.105" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "693151e1ac27563d6dbcec9dee9fbd5da8539b20fa14ad3752b2e6d363ace360" +dependencies = [ + "itoa", + "ryu", + "serde", +] + +[[package]] +name = "serde_urlencoded" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3491c14715ca2294c4d6a88f15e84739788c1d030eed8c110436aafdaa2f3fd" +dependencies = [ + "form_urlencoded", + "itoa", + "ryu", + "serde", +] + +[[package]] +name = "serde_with" +version = "1.14.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "678b5a069e50bf00ecd22d0cd8ddf7c236f68581b03db652061ed5eb13a312ff" +dependencies = [ + "base64 0.13.1", + "serde", + "serde_with_macros", +] + +[[package]] +name = "serde_with_macros" +version = "1.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e182d6ec6f05393cc0e5ed1bf81ad6db3a8feedf8ee515ecdd369809bcce8082" +dependencies = [ + "darling", + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "sha-1" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f5058ada175748e33390e40e872bd0fe59a19f265d0158daa551c5a88a76009c" +dependencies = [ + "cfg-if 1.0.0", + "cpufeatures", + "digest 0.10.7", +] + +[[package]] +name = "sha1" +version = "0.10.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f04293dc80c3993519f2d7f6f511707ee7094fe0c6d3406feb330cdb3540eba3" +dependencies = [ + "cfg-if 1.0.0", + "cpufeatures", + "digest 0.10.7", +] + +[[package]] +name = "sha2" +version = "0.9.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4d58a1e1bf39749807d89cf2d98ac2dfa0ff1cb3faa38fbb64dd88ac8013d800" +dependencies = [ + "block-buffer 0.9.0", + "cfg-if 1.0.0", + "cpufeatures", + "digest 0.9.0", + "opaque-debug", +] + +[[package]] +name = "sha2" +version = "0.10.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "82e6b795fe2e3b1e845bafcb27aa35405c4d47cdfc92af5fc8d3002f76cebdc0" +dependencies = [ + "cfg-if 1.0.0", + "cpufeatures", + "digest 0.10.7", +] + +[[package]] +name = "sha3" +version = "0.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f81199417d4e5de3f04b1e871023acea7389672c4135918f05aa9cbf2f2fa809" +dependencies = [ + "block-buffer 0.9.0", + "digest 0.9.0", + "keccak", + "opaque-debug", +] + +[[package]] +name = "sha3" +version = "0.10.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bdf0c33fae925bdc080598b84bc15c55e7b9a4a43b3c704da051f977469691c9" +dependencies = [ + "digest 0.10.7", + "keccak", +] + +[[package]] +name = "sharded-slab" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "900fba806f70c630b0a382d0d825e17a0f19fcd059a2ade1ff237bcddf446b31" +dependencies = [ + "lazy_static", +] + +[[package]] +name = "shlex" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a7cee0529a6d40f580e7a5e6c495c8fbfe21b7b52795ed4bb5e62cdf92bc6380" + +[[package]] +name = "signal-hook-registry" +version = "1.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d8229b473baa5980ac72ef434c4415e70c4b5e71b423043adb4ba059f89c99a1" +dependencies = [ + "libc", +] + +[[package]] +name = "signature" +version = "1.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74233d3b3b2f6d4b006dc19dee745e73e2a6bfb6f93607cd3b02bd5b00797d7c" +dependencies = [ + "digest 0.10.7", + "rand_core 0.6.4", +] + +[[package]] +name = "skeptic" +version = "0.13.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "16d23b015676c90a0f01c197bfdc786c20342c73a0afdda9025adb0bc42940a8" +dependencies = [ + "bytecount", + "cargo_metadata", + "error-chain", + "glob", + "pulldown-cmark", + "tempfile", + "walkdir", +] + +[[package]] +name = "slab" +version = "0.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f92a496fb766b417c996b9c5e57daf2f7ad3b0bebe1ccfca4856390e3d3bb67" +dependencies = [ + "autocfg 1.1.0", +] + +[[package]] +name = "smallvec" +version = "1.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62bb4feee49fdd9f707ef802e22365a35de4b7b299de4763d44bfea899442ff9" + +[[package]] +name = "socket2" +version = "0.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "64a4a911eed85daf18834cfaa86a79b7d266ff93ff5ba14005426219480ed662" +dependencies = [ + "libc", + "winapi", +] + +[[package]] +name = "socket2" +version = "0.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2538b18701741680e0322a2302176d3253a35388e2e62f172f64f4f16605f877" +dependencies = [ + "libc", + "windows-sys", +] + +[[package]] +name = "spin" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6e63cff320ae2c57904679ba7cb63280a3dc4613885beafb148ee7bf9aa9042d" + +[[package]] +name = "spki" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "67cf02bbac7a337dc36e4f5a693db6c21e7863f45070f7064577eb4367a3212b" +dependencies = [ + "base64ct", + "der", +] + +[[package]] +name = "splitmut" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c85070f382340e8b23a75808e83573ddf65f9ad9143df9573ca37c1ed2ee956a" + +[[package]] +name = "sqlformat" +version = "0.1.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4b7922be017ee70900be125523f38bdd644f4f06a1b16e8fa5a8ee8c34bffd4" +dependencies = [ + "itertools", + "nom", + "unicode_categories", +] + +[[package]] +name = "sqlx" +version = "0.5.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "551873805652ba0d912fec5bbb0f8b4cdd96baf8e2ebf5970e5671092966019b" +dependencies = [ + "sqlx-core", + "sqlx-macros", +] + +[[package]] +name = "sqlx-core" +version = "0.5.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e48c61941ccf5ddcada342cd59e3e5173b007c509e1e8e990dafc830294d9dc5" +dependencies = [ + "ahash 0.7.6", + "atoi", + "base64 0.13.1", + "bigdecimal", + "bitflags 1.3.2", + "byteorder", + "bytes", + "chrono", + "crc", + "crossbeam-queue 0.3.8", + "dirs", + "either", + "event-listener", + "futures-channel", + "futures-core", + "futures-intrusive", + "futures-util", + "hashlink", + "hex", + "hkdf", + "hmac 0.12.1", + "indexmap 1.9.3", + "ipnetwork", + "itoa", + "libc", + "log", + "md-5", + "memchr", + "num-bigint 0.3.3", + "once_cell", + "paste", + "percent-encoding", + "rand 0.8.5", + "serde", + "serde_json", + "sha-1", + "sha2 0.10.6", + "smallvec", + "sqlformat", + "sqlx-rt", + "stringprep", + "thiserror", + "tokio-stream", + "url", + "whoami", +] + +[[package]] +name = "sqlx-macros" +version = "0.5.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bc0fba2b0cae21fc00fe6046f8baa4c7fcb49e379f0f592b04696607f69ed2e1" +dependencies = [ + "dotenv", + "either", + "heck 0.4.1", + "hex", + "once_cell", + "proc-macro2 1.0.66", + "quote 1.0.33", + "serde", + "serde_json", + "sha2 0.10.6", + "sqlx-core", + "sqlx-rt", + "syn 1.0.109", + "url", +] + +[[package]] +name = "sqlx-rt" +version = "0.5.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4db708cd3e459078f85f39f96a00960bd841f66ee2a669e90bf36907f5a79aae" +dependencies = [ + "native-tls", + "once_cell", + "tokio", + "tokio-native-tls", +] + +[[package]] +name = "stable_deref_trait" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3" + +[[package]] +name = "static_assertions" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a2eb9349b6444b326872e140eb1cf5e7c522154d69e7a0ffb0fb81c06b37543f" + +[[package]] +name = "stringprep" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bb41d74e231a107a1b4ee36bd1214b11285b77768d2e3824aedafa988fd36ee6" +dependencies = [ + "finl_unicode", + "unicode-bidi", + "unicode-normalization", +] + +[[package]] +name = "strsim" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8ea5119cdb4c55b55d432abb513a0429384878c15dde60cc77b1c99de1a95a6a" + +[[package]] +name = "strsim" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623" + +[[package]] +name = "structopt" +version = "0.3.26" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0c6b5c64445ba8094a6ab0c3cd2ad323e07171012d9c98b0b15651daf1787a10" +dependencies = [ + "clap", + "lazy_static", + "structopt-derive", +] + +[[package]] +name = "structopt-derive" +version = "0.4.18" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dcb5ae327f9cc13b68763b5749770cb9e048a99bd9dfdfa58d0cf05d5f64afe0" +dependencies = [ + "heck 0.3.3", + "proc-macro-error", + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "strum" +version = "0.24.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "063e6045c0e62079840579a7e47a355ae92f60eb74daaf156fb1e84ba164e63f" +dependencies = [ + "strum_macros", +] + +[[package]] +name = "strum_macros" +version = "0.24.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1e385be0d24f186b4ce2f9982191e7101bb737312ad61c1f2f984f34bcf85d59" +dependencies = [ + "heck 0.4.1", + "proc-macro2 1.0.66", + "quote 1.0.33", + "rustversion", + "syn 1.0.109", +] + +[[package]] +name = "subtle" +version = "2.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6bdef32e8150c2a081110b42772ffe7d7c9032b606bc226c8260fd97e0976601" + +[[package]] +name = "syn" +version = "0.15.44" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9ca4b3b69a77cbe1ffc9e198781b7acb0c7365a883670e8f1c1bc66fba79a5c5" +dependencies = [ + "proc-macro2 0.4.30", + "quote 0.6.13", + "unicode-xid", +] + +[[package]] +name = "syn" +version = "1.0.109" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "unicode-ident", +] + +[[package]] +name = "syn" +version = "2.0.31" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "718fa2415bcb8d8bd775917a1bf12a7931b6dfa890753378538118181e0cb398" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "unicode-ident", +] + +[[package]] +name = "sync_vm" +version = "1.3.3" +source = "git+https://github.com/matter-labs/era-sync_vm.git?branch=v1.3.3#e819d15b107a06a746299f98bbd9802e26eeb348" +dependencies = [ + "arrayvec 0.7.4", + "cs_derive", + "derivative", + "franklin-crypto", + "hex", + "itertools", + "num-bigint 0.4.4", + "num-derive 0.3.3", + "num-integer", + "num-traits", + "once_cell", + "rand 0.4.6", + "rescue_poseidon", + "serde", + "sha2 0.10.6", + "sha3 0.10.6", + "smallvec", + "zk_evm", + "zkevm_opcode_defs", +] + +[[package]] +name = "tagptr" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b2093cf4c8eb1e67749a6762251bc9cd836b6fc171623bd0a9d324d37af2417" + +[[package]] +name = "tap" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "55937e1799185b12863d447f42597ed69d9928686b8d88a1df17376a097d8369" + +[[package]] +name = "tempfile" +version = "3.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb94d2f3cc536af71caac6b6fcebf65860b347e7ce0cc9ebe8f70d3e521054ef" +dependencies = [ + "cfg-if 1.0.0", + "fastrand", + "redox_syscall 0.3.5", + "rustix", + "windows-sys", +] + +[[package]] +name = "termcolor" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "be55cf8942feac5c765c2c993422806843c9a9a45d4d5c407ad6dd2ea95eb9b6" +dependencies = [ + "winapi-util", +] + +[[package]] +name = "test-log" +version = "0.2.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d9601d162c1d77e62c1ea0bc8116cd1caf143ce3af947536c3c9052a1677fe0c" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 1.0.109", +] + +[[package]] +name = "test_infra" +version = "0.1.0" +dependencies = [ + "colored", + "hex", + "once_cell", + "serde", + "serde_json", + "tracing", + "tracing-subscriber", + "vlog", + "vm", + "zksync_contracts", + "zksync_state", + "zksync_types", + "zksync_utils", +] + +[[package]] +name = "textwrap" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d326610f408c7a4eb6f51c37c330e496b08506c9457c9d34287ecc38809fb060" +dependencies = [ + "unicode-width", +] + +[[package]] +name = "thiserror" +version = "1.0.48" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9d6d7a740b8a666a7e828dd00da9c0dc290dff53154ea77ac109281de90589b7" +dependencies = [ + "thiserror-impl", +] + +[[package]] +name = "thiserror-impl" +version = "1.0.48" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49922ecae66cc8a249b77e68d1d0623c1b2c514f0060c27cdc68bd62a1219d35" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "thread_local" +version = "1.1.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3fdd6f064ccff2d6567adcb3873ca630700f00b5ad3f060c25b5dcfd9a4ce152" +dependencies = [ + "cfg-if 1.0.0", + "once_cell", +] + +[[package]] +name = "time" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "17f6bb557fd245c28e6411aa56b6403c689ad95061f50e4be16c274e70a17e48" +dependencies = [ + "deranged", + "itoa", + "serde", + "time-core", + "time-macros", +] + +[[package]] +name = "time-core" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7300fbefb4dadc1af235a9cef3737cea692a9d97e1b9cbcd4ebdae6f8868e6fb" + +[[package]] +name = "time-macros" +version = "0.2.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a942f44339478ef67935ab2bbaec2fb0322496cf3cbe84b261e06ac3814c572" +dependencies = [ + "time-core", +] + +[[package]] +name = "tiny-keccak" +version = "1.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1d8a021c69bb74a44ccedb824a046447e2c84a01df9e5c20779750acb38e11b2" +dependencies = [ + "crunchy", +] + +[[package]] +name = "tiny-keccak" +version = "2.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2c9d3793400a45f954c52e73d068316d76b6f4e36977e3fcebb13a2721e80237" +dependencies = [ + "crunchy", +] + +[[package]] +name = "tinyvec" +version = "1.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "87cc5ceb3875bb20c2890005a4e226a4651264a5c75edb2421b52861a0a0cb50" +dependencies = [ + "tinyvec_macros", +] + +[[package]] +name = "tinyvec_macros" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" + +[[package]] +name = "tokio" +version = "1.32.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "17ed6077ed6cd6c74735e21f37eb16dc3935f96878b1fe961074089cc80893f9" +dependencies = [ + "backtrace", + "bytes", + "libc", + "mio", + "num_cpus", + "parking_lot 0.12.1", + "pin-project-lite", + "signal-hook-registry", + "socket2 0.5.3", + "tokio-macros", + "windows-sys", +] + +[[package]] +name = "tokio-macros" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "630bdcf245f78637c13ec01ffae6187cca34625e8c63150d424b59e55af2675e" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "tokio-native-tls" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bbae76ab933c85776efabc971569dd6119c580d8f5d448769dec1764bf796ef2" +dependencies = [ + "native-tls", + "tokio", +] + +[[package]] +name = "tokio-rustls" +version = "0.24.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c28327cf380ac148141087fbfb9de9d7bd4e84ab5d2c28fbc911d753de8a7081" +dependencies = [ + "rustls", + "tokio", +] + +[[package]] +name = "tokio-stream" +version = "0.1.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "397c988d37662c7dda6d2208364a706264bf3d6138b11d436cbac0ad38832842" +dependencies = [ + "futures-core", + "pin-project-lite", + "tokio", +] + +[[package]] +name = "tokio-util" +version = "0.7.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "806fe8c2c87eccc8b3267cbae29ed3ab2d0bd37fca70ab622e46aaa9375ddb7d" +dependencies = [ + "bytes", + "futures-core", + "futures-sink", + "pin-project-lite", + "tokio", + "tracing", +] + +[[package]] +name = "toml_datetime" +version = "0.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7cda73e2f1397b1262d6dfdcef8aafae14d1de7748d66822d3bfeeb6d03e5e4b" + +[[package]] +name = "toml_edit" +version = "0.19.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1b5bb770da30e5cbfde35a2d7b9b8a2c4b8ef89548a7a6aeab5c9a576e3e7421" +dependencies = [ + "indexmap 2.0.0", + "toml_datetime", + "winnow", +] + +[[package]] +name = "tower-service" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b6bc1c9ce2b5135ac7f93c72918fc37feb872bdc6a5533a8b85eb4b86bfdae52" + +[[package]] +name = "tracing" +version = "0.1.37" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8ce8c33a8d48bd45d624a6e523445fd21ec13d3653cd51f681abf67418f54eb8" +dependencies = [ + "cfg-if 1.0.0", + "log", + "pin-project-lite", + "tracing-attributes", + "tracing-core", +] + +[[package]] +name = "tracing-attributes" +version = "0.1.26" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5f4f31f56159e98206da9efd823404b79b6ef3143b4a7ab76e67b1751b25a4ab" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "tracing-core" +version = "0.1.31" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0955b8137a1df6f1a2e9a37d8a6656291ff0297c1a97c24e0d8425fe2312f79a" +dependencies = [ + "once_cell", + "valuable", +] + +[[package]] +name = "tracing-log" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "78ddad33d2d10b1ed7eb9d1f518a5674713876e97e5bb9b7345a7984fbb4f922" +dependencies = [ + "lazy_static", + "log", + "tracing-core", +] + +[[package]] +name = "tracing-serde" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bc6b213177105856957181934e4920de57730fc69bf42c37ee5bb664d406d9e1" +dependencies = [ + "serde", + "tracing-core", +] + +[[package]] +name = "tracing-subscriber" +version = "0.3.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "30a651bc37f915e81f087d86e62a18eec5f79550c7faff886f7090b4ea757c77" +dependencies = [ + "matchers", + "nu-ansi-term", + "once_cell", + "regex", + "serde", + "serde_json", + "sharded-slab", + "smallvec", + "thread_local", + "time", + "tracing", + "tracing-core", + "tracing-log", + "tracing-serde", +] + +[[package]] +name = "triomphe" +version = "0.1.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0eee8098afad3fb0c54a9007aab6804558410503ad676d4633f9c2559a00ac0f" + +[[package]] +name = "try-lock" +version = "0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3528ecfd12c466c6f163363caf2d02a71161dd5e1cc6ae7b34207ea2d42d81ed" + +[[package]] +name = "typenum" +version = "1.16.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "497961ef93d974e23eb6f433eb5fe1b7930b659f06d12dec6fc44a8f554c0bba" + +[[package]] +name = "ucd-trie" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ed646292ffc8188ef8ea4d1e0e0150fb15a5c2e12ad9b8fc191ae7a8a7f3c4b9" + +[[package]] +name = "uint" +version = "0.9.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "76f64bba2c53b04fcab63c01a7d7427eadc821e3bc48c34dc9ba29c501164b52" +dependencies = [ + "byteorder", + "crunchy", + "hex", + "static_assertions", +] + +[[package]] +name = "uname" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b72f89f0ca32e4db1c04e2a72f5345d59796d4866a1ee0609084569f73683dc8" +dependencies = [ + "libc", +] + +[[package]] +name = "unicase" +version = "2.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f7d2d4dafb69621809a81864c9c1b864479e1235c0dd4e199924b9742439ed89" +dependencies = [ + "version_check", +] + +[[package]] +name = "unicode-bidi" +version = "0.3.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "92888ba5573ff080736b3648696b70cafad7d250551175acbaa4e0385b3e1460" + +[[package]] +name = "unicode-ident" +version = "1.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "301abaae475aa91687eb82514b328ab47a211a533026cb25fc3e519b86adfc3c" + +[[package]] +name = "unicode-normalization" +version = "0.1.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c5713f0fc4b5db668a2ac63cdb7bb4469d8c9fed047b1d0292cc7b0ce2ba921" +dependencies = [ + "tinyvec", +] + +[[package]] +name = "unicode-segmentation" +version = "1.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1dd624098567895118886609431a7c3b8f516e41d30e0643f03d94592a147e36" + +[[package]] +name = "unicode-width" +version = "0.1.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c0edd1e5b14653f783770bce4a4dabb4a5108a5370a5f5d8cfe8710c361f6c8b" + +[[package]] +name = "unicode-xid" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fc72304796d0818e357ead4e000d19c9c174ab23dc11093ac919054d20a6a7fc" + +[[package]] +name = "unicode_categories" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "39ec24b3121d976906ece63c9daad25b85969647682eee313cb5779fdd69e14e" + +[[package]] +name = "untrusted" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a156c684c91ea7d62626509bce3cb4e1d9ed5c4d978f7b4352658f96a4c26b4a" + +[[package]] +name = "ureq" +version = "2.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b11c96ac7ee530603dcdf68ed1557050f374ce55a5a07193ebf8cbc9f8927e9" +dependencies = [ + "base64 0.21.3", + "log", + "native-tls", + "once_cell", + "url", +] + +[[package]] +name = "url" +version = "2.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "143b538f18257fac9cad154828a57c6bf5157e1aa604d4816b5995bf6de87ae5" +dependencies = [ + "form_urlencoded", + "idna", + "percent-encoding", + "serde", +] + +[[package]] +name = "uuid" +version = "1.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "79daa5ed5740825c40b389c5e50312b9c86df53fccd33f281df655642b43869d" +dependencies = [ + "getrandom 0.2.10", + "serde", +] + +[[package]] +name = "valuable" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "830b7e5d4d90034032940e4ace0d9a9a057e7a45cd94e6c007832e39edb82f6d" + +[[package]] +name = "vcpkg" +version = "0.2.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426" + +[[package]] +name = "vec_map" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1bddf1187be692e79c5ffeab891132dfb0f236ed36a43c7ed39f1165ee20191" + +[[package]] +name = "version_check" +version = "0.9.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" + +[[package]] +name = "vise" +version = "0.1.0" +source = "git+https://github.com/matter-labs/vise.git?rev=9d097ab747b037b6e62504df1db5b975425b6bdd#9d097ab747b037b6e62504df1db5b975425b6bdd" +dependencies = [ + "elsa", + "linkme", + "once_cell", + "prometheus-client", + "vise-macros", +] + +[[package]] +name = "vise-macros" +version = "0.1.0" +source = "git+https://github.com/matter-labs/vise.git?rev=9d097ab747b037b6e62504df1db5b975425b6bdd#9d097ab747b037b6e62504df1db5b975425b6bdd" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", +] + +[[package]] +name = "vlog" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "chrono", + "sentry", + "serde_json", + "tracing", + "tracing-subscriber", +] + +[[package]] +name = "vm" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "anyhow", + "hex", + "itertools", + "once_cell", + "thiserror", + "tracing", + "vise", + "zk_evm", + "zksync_config", + "zksync_contracts", + "zksync_state", + "zksync_types", + "zksync_utils", +] + +[[package]] +name = "walkdir" +version = "2.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d71d857dc86794ca4c280d616f7da00d2dbfd8cd788846559a6813e6aa4b54ee" +dependencies = [ + "same-file", + "winapi-util", +] + +[[package]] +name = "want" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bfa7760aed19e106de2c7c0b581b509f2f25d3dacaf737cb82ac61bc6d760b0e" +dependencies = [ + "try-lock", +] + +[[package]] +name = "wasi" +version = "0.9.0+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cccddf32554fecc6acb585f82a32a72e28b48f8c4c1883ddfeeeaa96f7d8e519" + +[[package]] +name = "wasi" +version = "0.11.0+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" + +[[package]] +name = "wasm-bindgen" +version = "0.2.87" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7706a72ab36d8cb1f80ffbf0e071533974a60d0a308d01a5d0375bf60499a342" +dependencies = [ + "cfg-if 1.0.0", + "wasm-bindgen-macro", +] + +[[package]] +name = "wasm-bindgen-backend" +version = "0.2.87" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5ef2b6d3c510e9625e5fe6f509ab07d66a760f0885d858736483c32ed7809abd" +dependencies = [ + "bumpalo", + "log", + "once_cell", + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", + "wasm-bindgen-shared", +] + +[[package]] +name = "wasm-bindgen-futures" +version = "0.4.37" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c02dbc21516f9f1f04f187958890d7e6026df8d16540b7ad9492bc34a67cea03" +dependencies = [ + "cfg-if 1.0.0", + "js-sys", + "wasm-bindgen", + "web-sys", +] + +[[package]] +name = "wasm-bindgen-macro" +version = "0.2.87" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dee495e55982a3bd48105a7b947fd2a9b4a8ae3010041b9e0faab3f9cd028f1d" +dependencies = [ + "quote 1.0.33", + "wasm-bindgen-macro-support", +] + +[[package]] +name = "wasm-bindgen-macro-support" +version = "0.2.87" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "54681b18a46765f095758388f2d0cf16eb8d4169b639ab575a8f5693af210c7b" +dependencies = [ + "proc-macro2 1.0.66", + "quote 1.0.33", + "syn 2.0.31", + "wasm-bindgen-backend", + "wasm-bindgen-shared", +] + +[[package]] +name = "wasm-bindgen-shared" +version = "0.2.87" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ca6ad05a4870b2bf5fe995117d3728437bd27d7cd5f06f13c17443ef369775a1" + +[[package]] +name = "web-sys" +version = "0.3.64" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9b85cbef8c220a6abc02aefd892dfc0fc23afb1c6a426316ec33253a3877249b" +dependencies = [ + "js-sys", + "wasm-bindgen", +] + +[[package]] +name = "web3" +version = "0.19.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5388522c899d1e1c96a4c307e3797e0f697ba7c77dd8e0e625ecba9dd0342937" +dependencies = [ + "arrayvec 0.7.4", + "base64 0.21.3", + "bytes", + "derive_more", + "ethabi", + "ethereum-types 0.14.1", + "futures", + "futures-timer", + "headers", + "hex", + "idna", + "jsonrpc-core", + "log", + "once_cell", + "parking_lot 0.12.1", + "pin-project", + "reqwest", + "rlp", + "secp256k1 0.27.0", + "serde", + "serde_json", + "tiny-keccak 2.0.2", + "url", +] + +[[package]] +name = "webpki-roots" +version = "0.25.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "14247bb57be4f377dfb94c72830b8ce8fc6beac03cf4bf7b9732eadd414123fc" + +[[package]] +name = "whoami" +version = "1.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "22fc3756b8a9133049b26c7f61ab35416c130e8c09b660f5b3958b446f52cc50" +dependencies = [ + "wasm-bindgen", + "web-sys", +] + +[[package]] +name = "winapi" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" +dependencies = [ + "winapi-i686-pc-windows-gnu", + "winapi-x86_64-pc-windows-gnu", +] + +[[package]] +name = "winapi-i686-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" + +[[package]] +name = "winapi-util" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "70ec6ce85bb158151cae5e5c87f95a8e97d2c0c4b001223f33a334e3ce5de178" +dependencies = [ + "winapi", +] + +[[package]] +name = "winapi-x86_64-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" + +[[package]] +name = "windows" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e686886bc078bc1b0b600cac0147aadb815089b6e4da64016cbd754b6342700f" +dependencies = [ + "windows-targets", +] + +[[package]] +name = "windows-sys" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9" +dependencies = [ + "windows-targets", +] + +[[package]] +name = "windows-targets" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9a2fa6e2155d7247be68c096456083145c183cbbbc2764150dda45a87197940c" +dependencies = [ + "windows_aarch64_gnullvm", + "windows_aarch64_msvc", + "windows_i686_gnu", + "windows_i686_msvc", + "windows_x86_64_gnu", + "windows_x86_64_gnullvm", + "windows_x86_64_msvc", +] + +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8" + +[[package]] +name = "windows_aarch64_msvc" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dc35310971f3b2dbbf3f0690a219f40e2d9afcf64f9ab7cc1be722937c26b4bc" + +[[package]] +name = "windows_i686_gnu" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a75915e7def60c94dcef72200b9a8e58e5091744960da64ec734a6c6e9b3743e" + +[[package]] +name = "windows_i686_msvc" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f55c233f70c4b27f66c523580f78f1004e8b5a8b659e05a4eb49d4166cca406" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "53d40abd2583d23e4718fddf1ebec84dbff8381c07cae67ff7768bbf19c6718e" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b7b52767868a23d5bab768e390dc5f5c55825b6d30b86c844ff2dc7414044cc" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.48.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538" + +[[package]] +name = "winnow" +version = "0.5.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7c2e3184b9c4e92ad5167ca73039d0c42476302ab603e2fec4487511f38ccefc" +dependencies = [ + "memchr", +] + +[[package]] +name = "winreg" +version = "0.50.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "524e57b2c537c0f9b1e69f1965311ec12182b4122e45035b1508cd24d2adadb1" +dependencies = [ + "cfg-if 1.0.0", + "windows-sys", +] + +[[package]] +name = "wyz" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "85e60b0d1b5f99db2556934e21937020776a5d31520bf169e851ac44e6420214" + +[[package]] +name = "wyz" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "05f360fc0b24296329c78fda852a1e9ae82de9cf7b27dae4b7f62f118f77b9ed" +dependencies = [ + "tap", +] + +[[package]] +name = "zeroize" +version = "1.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2a0956f1ba7c7909bfb66c2e9e4124ab6f6482560f6628b5aaeba39207c9aad9" + +[[package]] +name = "zk_evm" +version = "1.3.3" +source = "git+https://github.com/matter-labs/era-zk_evm.git?branch=v1.3.3#fe8215a7047d24430ad470cf15a19bedb4d6ba0b" +dependencies = [ + "anyhow", + "lazy_static", + "num 0.4.1", + "serde", + "serde_json", + "static_assertions", + "zk_evm_abstractions", + "zkevm_opcode_defs", +] + +[[package]] +name = "zk_evm_abstractions" +version = "0.1.0" +source = "git+https://github.com/matter-labs/era-zk_evm_abstractions.git#7502a661d7d38906d849dcd3e7a15e5848af6581" +dependencies = [ + "anyhow", + "serde", + "static_assertions", + "zkevm_opcode_defs", +] + +[[package]] +name = "zkevm-assembly" +version = "1.3.2" +source = "git+https://github.com/matter-labs/era-zkEVM-assembly.git?branch=v1.3.2#3c61d450cbe6548068be8f313ed02f1bd229a865" +dependencies = [ + "env_logger", + "hex", + "lazy_static", + "log", + "nom", + "num-bigint 0.4.4", + "num-traits", + "sha3 0.10.6", + "smallvec", + "structopt", + "thiserror", + "zkevm_opcode_defs", +] + +[[package]] +name = "zkevm_opcode_defs" +version = "1.3.2" +source = "git+https://github.com/matter-labs/era-zkevm_opcode_defs.git?branch=v1.3.2#c7ab62f4c60b27dfc690c3ab3efb5fff1ded1a25" +dependencies = [ + "bitflags 2.4.0", + "blake2 0.10.6", + "ethereum-types 0.14.1", + "k256", + "lazy_static", + "sha2 0.10.6", + "sha3 0.10.6", +] + +[[package]] +name = "zkevm_test_harness" +version = "1.3.3" +source = "git+https://github.com/matter-labs/era-zkevm_test_harness.git?branch=v1.3.3#5fe3b73dba7c98e724358428ae10723c4758dfb5" +dependencies = [ + "bincode", + "circuit_testing", + "codegen 0.2.0", + "crossbeam 0.8.2", + "derivative", + "env_logger", + "hex", + "num-bigint 0.4.4", + "num-integer", + "num-traits", + "rayon", + "serde", + "serde_json", + "smallvec", + "structopt", + "sync_vm", + "test-log", + "tracing", + "zk_evm", + "zkevm-assembly", +] + +[[package]] +name = "zksync_basic_types" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "serde", + "serde_json", + "web3", +] + +[[package]] +name = "zksync_config" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "anyhow", + "bigdecimal", + "envy", + "hex", + "num 0.3.1", + "once_cell", + "serde", + "serde_json", + "url", + "zksync_basic_types", + "zksync_contracts", + "zksync_utils", +] + +[[package]] +name = "zksync_contracts" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "envy", + "ethabi", + "hex", + "once_cell", + "serde", + "serde_json", + "zksync_utils", +] + +[[package]] +name = "zksync_crypto" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "base64 0.13.1", + "blake2 0.10.6", + "hex", + "once_cell", + "serde", + "sha2 0.9.9", + "thiserror", + "zksync_basic_types", +] + +[[package]] +name = "zksync_dal" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "anyhow", + "bigdecimal", + "bincode", + "hex", + "itertools", + "num 0.3.1", + "once_cell", + "serde", + "serde_json", + "sqlx", + "strum", + "thiserror", + "tokio", + "tracing", + "vise", + "zksync_config", + "zksync_contracts", + "zksync_health_check", + "zksync_types", + "zksync_utils", +] + +[[package]] +name = "zksync_health_check" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "async-trait", + "futures", + "serde", + "serde_json", + "tokio", + "tracing", +] + +[[package]] +name = "zksync_mini_merkle_tree" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "once_cell", + "zksync_basic_types", + "zksync_crypto", +] + +[[package]] +name = "zksync_state" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "anyhow", + "metrics", + "mini-moka", + "tokio", + "tracing", + "vise", + "zksync_dal", + "zksync_storage", + "zksync_types", + "zksync_utils", +] + +[[package]] +name = "zksync_storage" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "num_cpus", + "once_cell", + "rocksdb", + "tracing", + "vise", +] + +[[package]] +name = "zksync_types" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "blake2 0.10.6", + "chrono", + "codegen 0.1.0", + "ethereum-types 0.12.1", + "num 0.3.1", + "num_enum", + "once_cell", + "parity-crypto", + "rlp", + "serde", + "serde_json", + "serde_with", + "strum", + "thiserror", + "zk_evm", + "zkevm_test_harness", + "zksync_basic_types", + "zksync_config", + "zksync_contracts", + "zksync_mini_merkle_tree", + "zksync_utils", +] + +[[package]] +name = "zksync_utils" +version = "0.1.0" +source = "git+https://github.com/matter-labs/zksync-era.git?branch=boojum-integration#d2ca29bf20b4ec2d9ec9e327b4ba6b281d9793de" +dependencies = [ + "anyhow", + "bigdecimal", + "futures", + "hex", + "itertools", + "metrics", + "num 0.3.1", + "reqwest", + "serde", + "thiserror", + "tokio", + "tracing", + "vlog", + "zk_evm", + "zksync_basic_types", +] diff --git a/.test-node-subtree/etc/system-contracts/bootloader/test_infra/Cargo.toml b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/Cargo.toml new file mode 100644 index 00000000..e78bcf65 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/Cargo.toml @@ -0,0 +1,23 @@ +[package] +name = "test_infra" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] + +vm = { git = "https://github.com/matter-labs/zksync-era.git", branch = "boojum-integration" } +zksync_types = { git = "https://github.com/matter-labs/zksync-era.git", branch = "boojum-integration" } +zksync_contracts = { git = "https://github.com/matter-labs/zksync-era.git", branch = "boojum-integration" } +zksync_utils = { git = "https://github.com/matter-labs/zksync-era.git", branch = "boojum-integration" } +zksync_state = { git = "https://github.com/matter-labs/zksync-era.git", branch = "boojum-integration" } +vlog = { git = "https://github.com/matter-labs/zksync-era.git", branch = "boojum-integration" } + +colored = "2.0" +hex = "0.4" +once_cell = "1.7" +tracing = { version = "0.1.26", features = ["log"] } +tracing-subscriber = { version = "0.3", features = ["fmt", "env-filter", "time", "json"] } +serde_json = "1.0.67" +serde = { version = "1.0", features = ["derive"] } diff --git a/.test-node-subtree/etc/system-contracts/bootloader/test_infra/README.md b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/README.md new file mode 100644 index 00000000..f66ea39e --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/README.md @@ -0,0 +1,15 @@ +# Testing infrastructure for bootloader + +This crate allows you to run the unittests against the bootloader code. + +You should put your tests in `../tests/bootloader/bootloader_test.yul`, then compile the yul with: + +```shell +yarn build +``` + +And afterwards run the testing infrastructure: + +```shell +cargo run +``` diff --git a/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/hook.rs b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/hook.rs new file mode 100644 index 00000000..1cb23ddf --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/hook.rs @@ -0,0 +1,129 @@ +use vm::{ + constants::{BOOTLOADER_HEAP_PAGE, VM_HOOK_PARAMS_START_POSITION}, + HistoryMode, SimpleMemory, +}; + +use zksync_types::{ + zkevm_test_harness::zk_evm::{ + aux_structures::MemoryPage, + tracing::{BeforeExecutionData, VmLocalStateData}, + zkevm_opcode_defs::{FatPointer, Opcode, UMAOpcode}, + }, + U256, +}; +use zksync_utils::u256_to_h256; + +#[derive(Clone, Debug)] +pub(crate) enum TestVmHook { + NoHook, + TestLog(String, String), + AssertEqFailed(String, String, String), + RequestedAssert(String), + // Testing framework reporting the number of tests. + TestCount(u32), + // 104 - test start. + TestStart(String), +} + +// Number of 32-bytes slots that are reserved for test hooks (passing information between bootloader test code and the VM). +const TEST_HOOKS: u32 = 5; +const TEST_HOOK_ENUM_POSITON: u32 = VM_HOOK_PARAMS_START_POSITION - 1; +const TEST_HOOK_START: u32 = TEST_HOOK_ENUM_POSITON - TEST_HOOKS; + +pub fn get_vm_hook_params(memory: &SimpleMemory) -> Vec { + memory.dump_page_content_as_u256_words( + BOOTLOADER_HEAP_PAGE, + TEST_HOOK_START..TEST_HOOK_ENUM_POSITON, + ) +} + +fn strip_trailing_zeros(input: &[u8]) -> &[u8] { + // Find the position of the last non-zero byte. + let end = input + .iter() + .rposition(|&byte| byte != 0) + .map(|pos| pos + 1) + .unwrap_or(0); + + // Return the byte slice up to the position found. + &input[..end] +} + +fn test_hook_as_string(hook_param: U256) -> String { + let msg = u256_to_h256(hook_param).as_bytes().to_vec(); + + String::from_utf8(strip_trailing_zeros(&msg).to_vec()).expect("Invalid debug message") +} + +fn test_hook_as_int_or_hex(hook_param: U256) -> String { + // For long data, it is better to use hex-encoding for greater readibility + if hook_param > U256::from(u64::max_value()) { + let mut bytes = [0u8; 32]; + hook_param.to_big_endian(&mut bytes); + format!("0x{}", hex::encode(bytes)) + } else { + hook_param.to_string() + } +} + +const fn heap_page_from_base(base: MemoryPage) -> MemoryPage { + MemoryPage(base.0 + 2) +} + +impl TestVmHook { + pub(crate) fn from_opcode_memory( + state: &VmLocalStateData<'_>, + data: &BeforeExecutionData, + memory: &SimpleMemory, + ) -> Self { + let opcode_variant = data.opcode.variant; + let heap_page = + heap_page_from_base(state.vm_local_state.callstack.current.base_memory_page).0; + + let src0_value = data.src0_value.value; + + let fat_ptr = FatPointer::from_u256(src0_value); + + let value = data.src1_value.value; + + // Only UMA opcodes in the bootloader serve for vm hooks + if !matches!(opcode_variant.opcode, Opcode::UMA(UMAOpcode::HeapWrite)) + || heap_page != BOOTLOADER_HEAP_PAGE + || fat_ptr.offset != TEST_HOOK_ENUM_POSITON * 32 + { + return Self::NoHook; + } + let vm_hook_params: Vec = get_vm_hook_params(memory); + + match value.as_u32() { + 100 => Self::TestLog( + test_hook_as_string(vm_hook_params[0]), + test_hook_as_int_or_hex(vm_hook_params[1]), + ), + 101 => Self::AssertEqFailed( + test_hook_as_int_or_hex(vm_hook_params[0]), + test_hook_as_int_or_hex(vm_hook_params[1]), + test_hook_as_string(vm_hook_params[2]), + ), + 102 => Self::RequestedAssert(test_hook_as_string(vm_hook_params[0])), + 103 => Self::TestCount(vm_hook_params[0].as_u32()), + 104 => Self::TestStart(test_hook_as_string(vm_hook_params[0])), + + _ => Self::NoHook, + } + } +} + +#[cfg(test)] +mod tests { + use zksync_types::U256; + + use crate::hook::test_hook_as_string; + + #[test] + fn test_to_string() { + let data: U256 = + U256::from("0x77696c6c4661696c000000000000000000000000000000000000000000000000"); + assert_eq!("willFail", test_hook_as_string(data)); + } +} diff --git a/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/main.rs b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/main.rs new file mode 100644 index 00000000..c91a8198 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/main.rs @@ -0,0 +1,179 @@ +use crate::{test_count_tracer::TestCountTracer, tracer::BootloaderTestTracer}; +use colored::Colorize; +use once_cell::sync::OnceCell; +use std::process; +use std::{env, sync::Arc}; +use tracing_subscriber::fmt; +use tracing_subscriber::prelude::__tracing_subscriber_SubscriberExt; +use tracing_subscriber::util::SubscriberInitExt; +use vm::{ + HistoryDisabled, L1BatchEnv, L2BlockEnv, SystemEnv, TxExecutionMode, Vm, VmExecutionMode, + VmTracer, +}; +use zksync_contracts::{ + read_zbin_bytecode, BaseSystemContracts, ContractLanguage, SystemContractCode, + SystemContractsRepo, +}; +use zksync_state::{ + InMemoryStorage, StoragePtr, StorageView, IN_MEMORY_STORAGE_DEFAULT_NETWORK_ID, +}; +use zksync_types::system_contracts::get_system_smart_contracts_from_dir; +use zksync_types::{block::legacy_miniblock_hash, Address, L1BatchNumber, MiniblockNumber, U256}; +use zksync_types::{L2ChainId, Transaction}; +use zksync_utils::bytecode::hash_bytecode; +use zksync_utils::{bytes_to_be_words, u256_to_h256}; + +mod hook; +mod test_count_tracer; +mod tracer; + +// Executes bootloader unittests. +fn execute_internal_bootloader_test() { + let test_location = env::current_dir() + .unwrap() + .join("../build/artifacts/bootloader_test.yul/bootloader_test.yul.zbin"); + println!("Current dir is {:?}", test_location); + let bytecode = read_zbin_bytecode(test_location.as_path()); + let hash = hash_bytecode(&bytecode); + let bootloader = SystemContractCode { + code: bytes_to_be_words(bytecode), + hash, + }; + + let repo = SystemContractsRepo { + root: env::current_dir().unwrap().join("../../"), + }; + + let bytecode = repo.read_sys_contract_bytecode("", "DefaultAccount", ContractLanguage::Sol); + let hash = hash_bytecode(&bytecode); + let default_aa = SystemContractCode { + code: bytes_to_be_words(bytecode), + hash, + }; + + let base_system_contract = BaseSystemContracts { + bootloader, + default_aa, + }; + + let system_env = SystemEnv { + zk_porter_available: false, + version: zksync_types::ProtocolVersionId::latest(), + base_system_smart_contracts: base_system_contract, + gas_limit: u32::MAX, + execution_mode: TxExecutionMode::VerifyExecute, + default_validation_computational_gas_limit: u32::MAX, + chain_id: zksync_types::L2ChainId::from(299), + }; + + let mut l1_batch_env = L1BatchEnv { + previous_batch_hash: None, + number: L1BatchNumber::from(1), + timestamp: 14, + l1_gas_price: 250_000_000, + fair_l2_gas_price: 250_000_000, + fee_account: Address::default(), + + enforced_base_fee: None, + first_l2_block: L2BlockEnv { + number: 1, + timestamp: 15, + prev_block_hash: legacy_miniblock_hash(MiniblockNumber(0)), + max_virtual_blocks_to_create: 1, + }, + }; + + // First - get the number of tests. + let test_count = { + let storage: StoragePtr> = + StorageView::new(InMemoryStorage::with_custom_system_contracts_and_chain_id( + L2ChainId::from(IN_MEMORY_STORAGE_DEFAULT_NETWORK_ID), + hash_bytecode, + get_system_smart_contracts_from_dir(env::current_dir().unwrap().join("../../")), + )) + .into_rc_ptr(); + + let mut vm = Vm::new( + l1_batch_env.clone(), + system_env.clone(), + storage.clone(), + HistoryDisabled, + ); + + let test_count = Arc::new(OnceCell::default()); + let custom_tracers = vec![Box::new(TestCountTracer::new(test_count.clone())) + as Box, HistoryDisabled>>]; + + // We're using a TestCountTracer (and passing 0 as fee account) - this should cause the bootloader + // test framework to report number of tests via VM hook. + vm.inspect(custom_tracers, VmExecutionMode::Bootloader); + + test_count.get().unwrap().clone() + }; + println!(" ==== Running {} tests ====", test_count); + + let mut tests_failed: u32 = 0; + + // Now we iterate over the tests. + for test_id in 1..=test_count { + println!("\n === Running test {}", test_id); + + let storage: StoragePtr> = + StorageView::new(InMemoryStorage::with_custom_system_contracts_and_chain_id( + L2ChainId::from(IN_MEMORY_STORAGE_DEFAULT_NETWORK_ID), + hash_bytecode, + get_system_smart_contracts_from_dir(env::current_dir().unwrap().join("../../")), + )) + .into_rc_ptr(); + + // We are passing id of the test in location (0) where we normally put the operator. + // This is then picked up by the testing framework. + l1_batch_env.fee_account = zksync_types::H160::from(u256_to_h256(U256::from(test_id))); + let mut vm = Vm::new( + l1_batch_env.clone(), + system_env.clone(), + storage.clone(), + HistoryDisabled, + ); + let test_result = Arc::new(OnceCell::default()); + + let custom_tracers = vec![Box::new(BootloaderTestTracer::new(test_result.clone())) + as Box, HistoryDisabled>>]; + + // Let's insert transactions into slots. They are not executed, but the tests can run functions against them. + let json_str = include_str!("test_transactions/0.json"); + let tx: Transaction = serde_json::from_str(json_str).unwrap(); + vm.push_transaction(tx); + + vm.inspect(custom_tracers, VmExecutionMode::Bootloader); + + let test_result = test_result.get().unwrap(); + match &test_result.result { + Ok(_) => println!("{} {}", "[PASS]".green(), test_result.test_name), + Err(error_info) => { + tests_failed += 1; + println!( + "{} {} {}", + "[FAIL]".red(), + test_result.test_name, + error_info + ) + } + } + } + if tests_failed > 0 { + println!("{}", format!("{} tests failed.", tests_failed).red()); + process::exit(1); + } else { + println!("{}", "ALL tests passed.".green()) + } +} + +fn main() { + tracing_subscriber::registry() + .with(fmt::Layer::default()) + .with(tracing_subscriber::EnvFilter::from_default_env()) + .init(); + + execute_internal_bootloader_test(); +} diff --git a/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/test_count_tracer.rs b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/test_count_tracer.rs new file mode 100644 index 00000000..7e5adc5a --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/test_count_tracer.rs @@ -0,0 +1,50 @@ +use std::sync::Arc; + +use once_cell::sync::OnceCell; +use vm::{ + DynTracer, ExecutionEndTracer, ExecutionProcessing, HistoryMode, SimpleMemory, + VmExecutionResultAndLogs, VmTracer, +}; +use zksync_state::{StoragePtr, WriteStorage}; +use zksync_types::zkevm_test_harness::zk_evm::tracing::{BeforeExecutionData, VmLocalStateData}; + +use crate::hook::TestVmHook; + +/// Tracer that returns number of tests in the bootloader test file. +pub struct TestCountTracer { + /// Returns number of tests in the yul file. + pub test_count: Arc>, +} + +impl TestCountTracer { + /// Creates the tracer that should also report the amount of tests in a file. + pub fn new(test_count_result: Arc>) -> Self { + TestCountTracer { + test_count: test_count_result, + } + } +} + +impl DynTracer for TestCountTracer { + fn before_execution( + &mut self, + state: VmLocalStateData<'_>, + data: BeforeExecutionData, + memory: &SimpleMemory, + _storage: StoragePtr, + ) { + if let TestVmHook::TestCount(test_count) = + TestVmHook::from_opcode_memory(&state, &data, memory) + { + self.test_count.set(test_count).unwrap(); + } + } +} + +impl ExecutionEndTracer for TestCountTracer {} + +impl ExecutionProcessing for TestCountTracer {} + +impl VmTracer for TestCountTracer { + fn save_results(&mut self, _result: &mut VmExecutionResultAndLogs) {} +} diff --git a/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/test_transactions/0.json b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/test_transactions/0.json new file mode 100644 index 00000000..0edb7a92 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/test_transactions/0.json @@ -0,0 +1,46 @@ +{ + "common_data": { + "L2": { + "nonce": 1, + "fee": { + "gas_limit": "0xfd617", + "max_fee_per_gas": "0xee6b280", + "max_priority_fee_per_gas": "0x0", + "gas_per_pubdata_limit": "0xc350" + }, + "initiatorAddress": "0x36615cf349d7f6344891b1e7ca7c72883f5dc049", + "signature": [ + 132, 90, 248, 214, 198, 24, 213, 194, 29, 253, 36, 112, 77, 245, 167, 245, 245, 120, 200, 225, 31, 40, 16, 76, + 182, 155, 102, 8, 166, 115, 59, 80, 92, 183, 251, 203, 109, 202, 149, 230, 132, 173, 160, 72, 234, 181, 177, 31, + 224, 177, 28, 52, 251, 76, 107, 79, 160, 132, 47, 135, 199, 146, 71, 193, 28 + ], + "transactionType": "EIP712Transaction", + "input": { + "hash": "0xf415e63408ab712fa72f7931ba8e1f21f9d5e86a2a76fb6857fe7efb84ac8ed4", + "data": [ + 113, 248, 236, 1, 128, 132, 14, 230, 178, 128, 131, 15, 214, 23, 148, 17, 28, 62, 137, 206, 128, 230, 46, 232, + 131, 24, 194, 128, 73, 32, 212, 201, 111, 146, 187, 128, 184, 100, 164, 19, 104, 98, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 75, 105, 108, 108, 101, 114, 32, 99, 111, 109, + 98, 111, 32, 49, 52, 52, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 130, 1, 4, 128, 128, 130, 1, 4, 148, + 54, 97, 92, 243, 73, 215, 246, 52, 72, 145, 177, 231, 202, 124, 114, 136, 63, 93, 192, 73, 130, 195, 80, 192, + 184, 65, 132, 90, 248, 214, 198, 24, 213, 194, 29, 253, 36, 112, 77, 245, 167, 245, 245, 120, 200, 225, 31, + 40, 16, 76, 182, 155, 102, 8, 166, 115, 59, 80, 92, 183, 251, 203, 109, 202, 149, 230, 132, 173, 160, 72, 234, + 181, 177, 31, 224, 177, 28, 52, 251, 76, 107, 79, 160, 132, 47, 135, 199, 146, 71, 193, 28, 192 + ] + }, + "paymasterParams": { + "paymaster": "0x0000000000000000000000000000000000000000", + "paymasterInput": [] + } + } + }, + "execute": { + "contractAddress": "0x111c3e89ce80e62ee88318c2804920d4c96f92bb", + "calldata": "0xa4136862000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000104b696c6c657220636f6d626f2031343400000000000000000000000000000000", + "value": "0x0", + "factoryDeps": [] + }, + "received_timestamp_ms": 1695015132601, + "raw_bytes": "0x71f8ec0180840ee6b280830fd61794111c3e89ce80e62ee88318c2804920d4c96f92bb80b864a4136862000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000104b696c6c657220636f6d626f203134340000000000000000000000000000000082010480808201049436615cf349d7f6344891b1e7ca7c72883f5dc04982c350c0b841845af8d6c618d5c21dfd24704df5a7f5f578c8e11f28104cb69b6608a6733b505cb7fbcb6dca95e684ada048eab5b11fe0b11c34fb4c6b4fa0842f87c79247c11cc0" +} diff --git a/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/test_transactions/README.md b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/test_transactions/README.md new file mode 100644 index 00000000..ee6c1178 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/test_transactions/README.md @@ -0,0 +1,8 @@ +# Test Transactions + +This directory contains JSON serialized 'Transaction' objects that are inserted into bootloader memory during +unittesting. + +Please add files with consecutive numbers (0.json, 1.json) - and insert into bootloader in the same order. + +Then, they can be accessed in the unittest, by calling `testing_txDataOffset(x)`. diff --git a/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/tracer.rs b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/tracer.rs new file mode 100644 index 00000000..942389f2 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/test_infra/src/tracer.rs @@ -0,0 +1,138 @@ +use std::sync::Arc; + +use colored::Colorize; + +use once_cell::sync::OnceCell; +use vm::{ + DynTracer, ExecutionEndTracer, ExecutionProcessing, Halt, HistoryMode, SimpleMemory, + TracerExecutionStatus, TracerExecutionStopReason, VmExecutionResultAndLogs, VmTracer, +}; +use zksync_state::{StoragePtr, WriteStorage}; +use zksync_types::zkevm_test_harness::zk_evm::tracing::{BeforeExecutionData, VmLocalStateData}; + +use crate::hook::TestVmHook; + +#[derive(Debug)] +pub struct TestResult { + pub test_name: String, + pub result: Result<(), String>, +} + +/// Bootloader test tracer that is executing while the bootloader tests are running. +/// It can check the assers, return information about the running tests (and amount of tests) etc. +pub struct BootloaderTestTracer { + /// Set if the currently running test has failed. + test_result: Arc>, + /// Set, if the currently running test should fail with a given assert. + requested_assert: Option, + + test_name: Option, +} + +impl BootloaderTestTracer { + pub fn new(test_result: Arc>) -> Self { + BootloaderTestTracer { + test_result, + requested_assert: None, + test_name: None, + } + } +} + +impl DynTracer for BootloaderTestTracer { + fn before_execution( + &mut self, + state: VmLocalStateData<'_>, + data: BeforeExecutionData, + memory: &SimpleMemory, + _storage: StoragePtr, + ) { + let hook = TestVmHook::from_opcode_memory(&state, &data, memory); + + if let TestVmHook::TestLog(msg, data_str) = &hook { + println!("{} {} {}", "Test log".bold(), msg, data_str); + } + if let TestVmHook::AssertEqFailed(a, b, msg) = &hook { + let result = format!("Assert failed: {} is not equal to {}: {}", a, b, msg); + + self.test_result + .set(TestResult { + test_name: self.test_name.clone().unwrap_or("".to_owned()), + result: Err(result.clone()), + }) + .unwrap(); + } + if let TestVmHook::RequestedAssert(requested_assert) = &hook { + self.requested_assert = Some(requested_assert.clone()) + } + + if let TestVmHook::TestStart(test_name) = &hook { + self.test_name = Some(test_name.clone()); + } + } +} + +impl ExecutionEndTracer for BootloaderTestTracer { + fn should_stop_execution(&self) -> TracerExecutionStatus { + if let Some(TestResult { + test_name: _, + result: Err(_), + }) = self.test_result.get() + { + return TracerExecutionStatus::Stop(TracerExecutionStopReason::Finish); + } + return TracerExecutionStatus::Continue; + } +} + +impl ExecutionProcessing for BootloaderTestTracer {} + +impl VmTracer for BootloaderTestTracer { + fn save_results(&mut self, result: &mut VmExecutionResultAndLogs) { + let r = if let Some(requested_assert) = &self.requested_assert { + match &result.result { + vm::ExecutionResult::Success { .. } => Err(format!( + "Should have failed with {}, but run succesfully.", + requested_assert + )), + vm::ExecutionResult::Revert { output } => Err(format!( + "Should have failed with {}, but run reverted with {}.", + requested_assert, + output.to_user_friendly_string() + )), + vm::ExecutionResult::Halt { reason } => { + if let Halt::UnexpectedVMBehavior(reason) = reason { + let reason = reason.strip_prefix("Assertion error: ").unwrap(); + if reason == requested_assert { + Ok(()) + } else { + Err(format!( + "Should have failed with `{}`, but failed with different assert `{}`", + requested_assert, reason + )) + } + } else { + Err(format!( + "Should have failed with `{}`, but halted with`{}`", + requested_assert, reason + )) + } + } + } + } else { + match &result.result { + vm::ExecutionResult::Success { .. } => Ok(()), + vm::ExecutionResult::Revert { output } => Err(output.to_user_friendly_string()), + vm::ExecutionResult::Halt { reason } => Err(reason.to_string()), + } + }; + if self.test_result.get().is_none() { + self.test_result + .set(TestResult { + test_name: self.test_name.clone().unwrap_or("".to_owned()), + result: r, + }) + .unwrap(); + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/bootloader/tests/README.md b/.test-node-subtree/etc/system-contracts/bootloader/tests/README.md new file mode 100644 index 00000000..31acb0ec --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/tests/README.md @@ -0,0 +1,23 @@ +# Testing + +## Full tests + +`dummy.yul` and `transfer_tests.yul` are full Yul files, which are replacing the bootloader, and are used in +`zksync-era` crate. + +## Unittests + +Please put bootloader unittests in `bootloader/bootloader_test.yul` file, and any testing utility functions in +`utils/test_utils.yul`. + +To execute tests, you should first run yarn to prepare the source code: + +```shell +yarn preprocess && yarn compile-yul +``` + +And then run the test framework: + +```shell +cd test_infa && cargo run +``` diff --git a/.test-node-subtree/etc/system-contracts/bootloader/tests/bootloader/bootloader_test.yul b/.test-node-subtree/etc/system-contracts/bootloader/tests/bootloader/bootloader_test.yul new file mode 100644 index 00000000..cd41c45d --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/tests/bootloader/bootloader_test.yul @@ -0,0 +1,52 @@ +function TEST_safeSub() { + testing_assertEq(safeSub(10, 7, "err"), 3, "Failed to subtract 7") + testing_assertEq(safeSub(10, 8, "err"), 2, "Failed to subtract 8") +} + +function TEST_safeDiv() { + testing_assertEq(safeDiv(4, 2, "err"), 2, "Simple division") + testing_assertEq(safeDiv(5, 2, "err"), 2, "Rouding") + testing_assertEq(safeDiv(5, 3, "err"), 1, "Rouding down") + testing_assertEq(safeDiv(4, 3, "err"), 1, "Rouding down") + testing_assertEq(safeDiv(0, 3, "err"), 0, "Rouding down") +} +function TEST_safeDivAssert() { + testing_testWillFailWith("divByZero") + safeDiv(4, 0, "divByZero") +} + +function TEST_asserts() { + testing_testWillFailWith("willFail") + safeSub(10, 12, "willFail") +} + +function TEST_safeMul() { + testing_assertEq(safeMul(4, 2, "err"), 8, "Simple") + testing_assertEq(safeMul(0, 2, "err"), 0, "With zero") + testing_assertEq(safeMul(0, 0, "err"), 0, "With zero") + testing_assertEq(safeMul(2, 0, "err"), 0, "With zero") +} + +function TEST_safeMulAssert() { + testing_testWillFailWith("overflow") + let left := shl(129, 1) + testing_log("left", left) + safeMul(left, left, "overflow") +} + +// function TEST_should ignore + +function TEST_strLen() { + testing_assertEq(getStrLen("abcd"), 4, "short string") + testing_assertEq(getStrLen("00"), 2, "0 filled string") + testing_assertEq(getStrLen(""), 0, "empty string") + testing_assertEq(getStrLen("12345678901234567890123456789012"), 32, "max length") + testing_assertEq(getStrLen("1234567890123456789012345678901234"), 0, "over max length") +} + +function TEST_simple_transaction() { + // We'll test the transaction from 0.json + let txDataOffset := testing_txDataOffset(0) + let innerTxDataOffset := add(txDataOffset, 0x20) + testing_assertEq(getGasPerPubdataByteLimit(innerTxDataOffset), 0xc350, "Invalid pubdata limit") +} diff --git a/.test-node-subtree/etc/system-contracts/bootloader/tests/dummy.yul b/.test-node-subtree/etc/system-contracts/bootloader/tests/dummy.yul new file mode 100644 index 00000000..49970154 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/tests/dummy.yul @@ -0,0 +1,15 @@ +// A really basic test that only sets one memory cell to 1. +object "Bootloader" { + code { + } + object "Bootloader_deployed" { + code { + let DUMMY_TEST_CELL := 0x00 + let DUMMY_TEST_VALUE := 0x123123123 + mstore(DUMMY_TEST_CELL, DUMMY_TEST_VALUE) + // Need to return. Otherwise, the compiler will optimize out + // the mstore + return(0,32) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/bootloader/tests/transfer_test.yul b/.test-node-subtree/etc/system-contracts/bootloader/tests/transfer_test.yul new file mode 100644 index 00000000..460ff0a8 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/tests/transfer_test.yul @@ -0,0 +1,46 @@ +// A really basic test that only sets one memory cell to 1. +object "Bootloader" { + code { + } + object "Bootloader_deployed" { + code { + // This test is used to calculate the number of gas required to + // do a simple internal transfer + + function ETH_L2_TOKEN_ADDR() -> ret { + ret := 0x000000000000000000000000000000000000800a + } + function BOOTLOADER_FORMAL_ADDR() -> ret { + ret := 0x0000000000000000000000000000000000008001 + } + + // Getting the balance of the account in order to make sure + // that the decommit of the account has already happened and so + // the call of the actual transfer is cheaper. + let myBalance := selfbalance() + // Storing the value to avoid compiler optimization + mstore(100, myBalance) + + let gasBeforeCall := gas() + let transferSuccess := call( + gas(), + ETH_L2_TOKEN_ADDR(), + 0, + 0, + 100, + 0, + 0 + ) + let gasSpent := sub(gasBeforeCall, gas()) + + if iszero(transferSuccess) { + // The transfer should succeed + revert(0,0) + } + + + mstore(0, gasSpent) + return(0, 256) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/bootloader/tests/utils/test_utils.yul b/.test-node-subtree/etc/system-contracts/bootloader/tests/utils/test_utils.yul new file mode 100644 index 00000000..561a4679 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/bootloader/tests/utils/test_utils.yul @@ -0,0 +1,55 @@ + + +// We're locating the test hooks 'before' the last free slot. +function TEST_HOOK_PTR() -> ret { + ret := LAST_FREE_SLOT() +} + +function TEST_HOOK_PARAMS_OFFSET() -> ret { + ret := sub(TEST_HOOK_PTR(), mul(5, 32)) +} + +function setTestHook(hook) { + mstore(TEST_HOOK_PTR(), unoptimized(hook)) +} + +function storeTestHookParam(paramId, value) { + let offset := add(TEST_HOOK_PARAMS_OFFSET(), mul(32, paramId)) + mstore(offset, unoptimized(value)) +} + + +function testing_log(msg, data) { + storeTestHookParam(0, nonOptimized(msg)) + storeTestHookParam(1, nonOptimized(data)) + setTestHook(nonOptimized(100)) +} + +function testing_start(test_name) { + storeTestHookParam(0, nonOptimized(test_name)) + setTestHook(nonOptimized(104)) +} + +function testing_assertEq(a, b, message) { + if iszero(eq(a, b)) { + storeTestHookParam(0, nonOptimized(a)) + storeTestHookParam(1, nonOptimized(b)) + storeTestHookParam(2, nonOptimized(message)) + setTestHook(nonOptimized(101)) + } +} + +function testing_testWillFailWith(message) { + storeTestHookParam(0, unoptimized(message)) + setTestHook(nonOptimized(102)) +} +function testing_totalTests(tests) { + storeTestHookParam(0, unoptimized(tests)) + setTestHook(nonOptimized(103)) +} + +// Returns txDataOffset for the index transaction. +function testing_txDataOffset(index) -> txDataOffset { + let txPtr := add(TX_DESCRIPTION_BEGIN_BYTE(), mul(index, TX_DESCRIPTION_SIZE())) + txDataOffset := mload(add(txPtr, 0x20)) +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/AccountCodeStorage.sol b/.test-node-subtree/etc/system-contracts/contracts/AccountCodeStorage.sol new file mode 100644 index 00000000..d5027f2f --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/AccountCodeStorage.sol @@ -0,0 +1,139 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "./interfaces/IAccountCodeStorage.sol"; +import "./libraries/Utils.sol"; +import {DEPLOYER_SYSTEM_CONTRACT, NONCE_HOLDER_SYSTEM_CONTRACT, CURRENT_MAX_PRECOMPILE_ADDRESS} from "./Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice The storage of this contract serves as a mapping for the code hashes of the 32-byte account addresses. + * @dev Code hash is not strictly a hash, it's a structure where the first byte denotes the version of the hash, + * the second byte denotes whether the contract is constructed, and the next two bytes denote the length in 32-byte words. + * And then the next 28 bytes are the truncated hash. + * @dev In this version of zkSync, the first byte of the hash MUST be 1. + * @dev The length of each bytecode MUST be odd. It's internal code format requirements, due to padding of SHA256 function. + * @dev It is also assumed that all the bytecode hashes are *known*, i.e. the full bytecodes + * were published on L1 as calldata. This contract trusts the ContractDeployer and the KnownCodesStorage + * system contracts to enforce the invariants mentioned above. + */ +contract AccountCodeStorage is IAccountCodeStorage { + bytes32 constant EMPTY_STRING_KECCAK = 0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470; + + modifier onlyDeployer() { + require(msg.sender == address(DEPLOYER_SYSTEM_CONTRACT), "Callable only by the deployer system contract"); + _; + } + + /// @notice Stores the bytecodeHash of constructing contract. + /// @param _address The address of the account to set the codehash to. + /// @param _hash The new bytecode hash of the constructing account. + /// @dev This method trusts the ContractDeployer to make sure that the bytecode is known and well-formed, + /// but checks whether the bytecode hash corresponds to the constructing smart contract. + function storeAccountConstructingCodeHash(address _address, bytes32 _hash) external override onlyDeployer { + // Check that code hash corresponds to the deploying smart contract + require(Utils.isContractConstructing(_hash), "Code hash is not for a contract on constructor"); + _storeCodeHash(_address, _hash); + } + + /// @notice Stores the bytecodeHash of constructed contract. + /// @param _address The address of the account to set the codehash to. + /// @param _hash The new bytecode hash of the constructed account. + /// @dev This method trusts the ContractDeployer to make sure that the bytecode is known and well-formed, + /// but checks whether the bytecode hash corresponds to the constructed smart contract. + function storeAccountConstructedCodeHash(address _address, bytes32 _hash) external override onlyDeployer { + // Check that code hash corresponds to the deploying smart contract + require(Utils.isContractConstructed(_hash), "Code hash is not for a constructed contract"); + _storeCodeHash(_address, _hash); + } + + /// @notice Marks the account bytecodeHash as constructed. + /// @param _address The address of the account to mark as constructed + function markAccountCodeHashAsConstructed(address _address) external override onlyDeployer { + bytes32 codeHash = getRawCodeHash(_address); + + require(Utils.isContractConstructing(codeHash), "Code hash is not for a contract on constructor"); + + // Get the bytecode hash with "isConstructor" flag equal to false + bytes32 constructedBytecodeHash = Utils.constructedBytecodeHash(codeHash); + + _storeCodeHash(_address, constructedBytecodeHash); + } + + /// @dev Store the codehash of the account without any checks. + /// @param _address The address of the account to set the codehash to. + /// @param _hash The new account bytecode hash. + function _storeCodeHash(address _address, bytes32 _hash) internal { + uint256 addressAsKey = uint256(uint160(_address)); + assembly { + sstore(addressAsKey, _hash) + } + } + + /// @notice Get the codehash stored for an address. + /// @param _address The address of the account of which the codehash to return + /// @return codeHash The codehash stored for this account. + function getRawCodeHash(address _address) public view override returns (bytes32 codeHash) { + uint256 addressAsKey = uint256(uint160(_address)); + + assembly { + codeHash := sload(addressAsKey) + } + } + + /// @notice Simulate the behavior of the `extcodehash` EVM opcode. + /// @param _input The 256-bit account address. + /// @return codeHash - hash of the bytecode according to the EIP-1052 specification. + function getCodeHash(uint256 _input) external view override returns (bytes32) { + // We consider the account bytecode hash of the last 20 bytes of the input, because + // according to the spec "If EXTCODEHASH of A is X, then EXTCODEHASH of A + 2**160 is X". + address account = address(uint160(_input)); + if (uint160(account) <= CURRENT_MAX_PRECOMPILE_ADDRESS) { + return EMPTY_STRING_KECCAK; + } + + bytes32 codeHash = getRawCodeHash(account); + + // The code hash is equal to the `keccak256("")` if the account is an EOA with at least one transaction. + // Otherwise, the account is either deployed smart contract or an empty account, + // for both cases the code hash is equal to the raw code hash. + if (codeHash == 0x00 && NONCE_HOLDER_SYSTEM_CONTRACT.getRawNonce(account) > 0) { + codeHash = EMPTY_STRING_KECCAK; + } + // The contract is still on the constructor, which means it is not deployed yet, + // so set `keccak256("")` as a code hash. The EVM has the same behavior. + else if (Utils.isContractConstructing(codeHash)) { + codeHash = EMPTY_STRING_KECCAK; + } + + return codeHash; + } + + /// @notice Simulate the behavior of the `extcodesize` EVM opcode. + /// @param _input The 256-bit account address. + /// @return codeSize - the size of the deployed smart contract in bytes. + function getCodeSize(uint256 _input) external view override returns (uint256 codeSize) { + // We consider the account bytecode size of the last 20 bytes of the input, because + // according to the spec "If EXTCODESIZE of A is X, then EXTCODESIZE of A + 2**160 is X". + address account = address(uint160(_input)); + bytes32 codeHash = getRawCodeHash(account); + + // If the contract is a default account or is on constructor the code size is zero, + // otherwise extract the proper value for it from the bytecode hash. + // NOTE: zero address and precompiles are a special case, they are contracts, but we + // want to preserve EVM invariants (see EIP-1052 specification). That's why we automatically + // return `0` length in the following cases: + // - `codehash(0) == 0` + // - `account` is a precompile. + // - `account` is currently being constructed + if ( + uint160(account) > CURRENT_MAX_PRECOMPILE_ADDRESS && + codeHash != 0x00 && + !Utils.isContractConstructing(codeHash) + ) { + codeSize = Utils.bytecodeLenInBytes(codeHash); + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/BootloaderUtilities.sol b/.test-node-subtree/etc/system-contracts/contracts/BootloaderUtilities.sol new file mode 100644 index 00000000..49467bdc --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/BootloaderUtilities.sol @@ -0,0 +1,320 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "./interfaces/IBootloaderUtilities.sol"; +import "./libraries/TransactionHelper.sol"; +import "./libraries/RLPEncoder.sol"; +import "./libraries/EfficientCall.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice A contract that provides some utility methods for the bootloader + * that is very hard to write in Yul. + */ +contract BootloaderUtilities is IBootloaderUtilities { + using TransactionHelper for *; + + /// @notice Calculates the canonical transaction hash and the recommended transaction hash. + /// @param _transaction The transaction. + /// @return txHash and signedTxHash of the transaction, i.e. the transaction hash to be used in the explorer and commits to all + /// the fields of the transaction and the recommended hash to be signed for this transaction. + /// @dev txHash must be unique for all transactions. + function getTransactionHashes( + Transaction calldata _transaction + ) external view override returns (bytes32 txHash, bytes32 signedTxHash) { + signedTxHash = _transaction.encodeHash(); + if (_transaction.txType == EIP_712_TX_TYPE) { + txHash = keccak256(bytes.concat(signedTxHash, EfficientCall.keccak(_transaction.signature))); + } else if (_transaction.txType == LEGACY_TX_TYPE) { + txHash = encodeLegacyTransactionHash(_transaction); + } else if (_transaction.txType == EIP_1559_TX_TYPE) { + txHash = encodeEIP1559TransactionHash(_transaction); + } else if (_transaction.txType == EIP_2930_TX_TYPE) { + txHash = encodeEIP2930TransactionHash(_transaction); + } else { + revert("Unsupported tx type"); + } + } + + /// @notice Calculates the hash for a legacy transaction. + /// @param _transaction The legacy transaction. + /// @return txHash The hash of the transaction. + function encodeLegacyTransactionHash(Transaction calldata _transaction) internal view returns (bytes32 txHash) { + // Hash of legacy transactions are encoded as one of the: + // - RLP(nonce, gasPrice, gasLimit, to, value, data, chainId, 0, 0) + // - RLP(nonce, gasPrice, gasLimit, to, value, data) + // + // In this RLP encoding, only the first one above list appears, so we encode each element + // inside list and then concatenate the length of all elements with them. + + bytes memory encodedNonce = RLPEncoder.encodeUint256(_transaction.nonce); + // Encode `gasPrice` and `gasLimit` together to prevent "stack too deep error". + bytes memory encodedGasParam; + { + bytes memory encodedGasPrice = RLPEncoder.encodeUint256(_transaction.maxFeePerGas); + bytes memory encodedGasLimit = RLPEncoder.encodeUint256(_transaction.gasLimit); + encodedGasParam = bytes.concat(encodedGasPrice, encodedGasLimit); + } + + bytes memory encodedTo = RLPEncoder.encodeAddress(address(uint160(_transaction.to))); + bytes memory encodedValue = RLPEncoder.encodeUint256(_transaction.value); + // Encode only the length of the transaction data, and not the data itself, + // so as not to copy to memory a potentially huge transaction data twice. + bytes memory encodedDataLength; + { + // Safe cast, because the length of the transaction data can't be so large. + uint64 txDataLen = uint64(_transaction.data.length); + if (txDataLen != 1) { + // If the length is not equal to one, then only using the length can it be encoded definitely. + encodedDataLength = RLPEncoder.encodeNonSingleBytesLen(txDataLen); + } else if (_transaction.data[0] >= 0x80) { + // If input is a byte in [0x80, 0xff] range, RLP encoding will concatenates 0x81 with the byte. + encodedDataLength = hex"81"; + } + // Otherwise the length is not encoded at all. + } + + bytes memory rEncoded; + { + uint256 rInt = uint256(bytes32(_transaction.signature[0:32])); + rEncoded = RLPEncoder.encodeUint256(rInt); + } + bytes memory sEncoded; + { + uint256 sInt = uint256(bytes32(_transaction.signature[32:64])); + sEncoded = RLPEncoder.encodeUint256(sInt); + } + bytes memory vEncoded; + { + uint256 vInt = uint256(uint8(_transaction.signature[64])); + require(vInt == 27 || vInt == 28, "Invalid v value"); + + // If the `chainId` is specified in the transaction, then the `v` value is encoded as + // `35 + y + 2 * chainId == vInt + 8 + 2 * chainId`, where y - parity bit (see EIP-155). + if (_transaction.reserved[0] != 0) { + vInt += 8 + block.chainid * 2; + } + + vEncoded = RLPEncoder.encodeUint256(vInt); + } + + bytes memory encodedListLength; + unchecked { + uint256 listLength = encodedNonce.length + + encodedGasParam.length + + encodedTo.length + + encodedValue.length + + encodedDataLength.length + + _transaction.data.length + + rEncoded.length + + sEncoded.length + + vEncoded.length; + + // Safe cast, because the length of the list can't be so large. + encodedListLength = RLPEncoder.encodeListLen(uint64(listLength)); + } + + return + keccak256( + bytes.concat( + encodedListLength, + encodedNonce, + encodedGasParam, + encodedTo, + encodedValue, + encodedDataLength, + _transaction.data, + vEncoded, + rEncoded, + sEncoded + ) + ); + } + + /// @notice Calculates the hash for an EIP2930 transaction. + /// @param _transaction The EIP2930 transaction. + /// @return txHash The hash of the transaction. + function encodeEIP2930TransactionHash(Transaction calldata _transaction) internal view returns (bytes32) { + // Encode all fixed-length params to avoid "stack too deep error" + bytes memory encodedFixedLengthParams; + { + bytes memory encodedChainId = RLPEncoder.encodeUint256(block.chainid); + bytes memory encodedNonce = RLPEncoder.encodeUint256(_transaction.nonce); + bytes memory encodedGasPrice = RLPEncoder.encodeUint256(_transaction.maxFeePerGas); + bytes memory encodedGasLimit = RLPEncoder.encodeUint256(_transaction.gasLimit); + bytes memory encodedTo = RLPEncoder.encodeAddress(address(uint160(_transaction.to))); + bytes memory encodedValue = RLPEncoder.encodeUint256(_transaction.value); + encodedFixedLengthParams = bytes.concat( + encodedChainId, + encodedNonce, + encodedGasPrice, + encodedGasLimit, + encodedTo, + encodedValue + ); + } + + // Encode only the length of the transaction data, and not the data itself, + // so as not to copy to memory a potentially huge transaction data twice. + bytes memory encodedDataLength; + { + // Safe cast, because the length of the transaction data can't be so large. + uint64 txDataLen = uint64(_transaction.data.length); + if (txDataLen != 1) { + // If the length is not equal to one, then only using the length can it be encoded definitely. + encodedDataLength = RLPEncoder.encodeNonSingleBytesLen(txDataLen); + } else if (_transaction.data[0] >= 0x80) { + // If input is a byte in [0x80, 0xff] range, RLP encoding will concatenates 0x81 with the byte. + encodedDataLength = hex"81"; + } + // Otherwise the length is not encoded at all. + } + + // On zkSync, access lists are always zero length (at least for now). + bytes memory encodedAccessListLength = RLPEncoder.encodeListLen(0); + + bytes memory rEncoded; + { + uint256 rInt = uint256(bytes32(_transaction.signature[0:32])); + rEncoded = RLPEncoder.encodeUint256(rInt); + } + bytes memory sEncoded; + { + uint256 sInt = uint256(bytes32(_transaction.signature[32:64])); + sEncoded = RLPEncoder.encodeUint256(sInt); + } + bytes memory vEncoded; + { + uint256 vInt = uint256(uint8(_transaction.signature[64])); + require(vInt == 27 || vInt == 28, "Invalid v value"); + + vEncoded = RLPEncoder.encodeUint256(vInt - 27); + } + + bytes memory encodedListLength; + unchecked { + uint256 listLength = encodedFixedLengthParams.length + + encodedDataLength.length + + _transaction.data.length + + encodedAccessListLength.length + + rEncoded.length + + sEncoded.length + + vEncoded.length; + + // Safe cast, because the length of the list can't be so large. + encodedListLength = RLPEncoder.encodeListLen(uint64(listLength)); + } + + return + keccak256( + bytes.concat( + "\x01", + encodedListLength, + encodedFixedLengthParams, + encodedDataLength, + _transaction.data, + encodedAccessListLength, + vEncoded, + rEncoded, + sEncoded + ) + ); + } + + /// @notice Calculates the hash for an EIP1559 transaction. + /// @param _transaction The legacy transaction. + /// @return txHash The hash of the transaction. + function encodeEIP1559TransactionHash(Transaction calldata _transaction) internal view returns (bytes32) { + // The formula for hash of EIP1559 transaction in the original proposal: + // https://github.com/ethereum/EIPs/blob/master/EIPS/eip-1559.md + + // Encode all fixed-length params to avoid "stack too deep error" + bytes memory encodedFixedLengthParams; + { + bytes memory encodedChainId = RLPEncoder.encodeUint256(block.chainid); + bytes memory encodedNonce = RLPEncoder.encodeUint256(_transaction.nonce); + bytes memory encodedMaxPriorityFeePerGas = RLPEncoder.encodeUint256(_transaction.maxPriorityFeePerGas); + bytes memory encodedMaxFeePerGas = RLPEncoder.encodeUint256(_transaction.maxFeePerGas); + bytes memory encodedGasLimit = RLPEncoder.encodeUint256(_transaction.gasLimit); + bytes memory encodedTo = RLPEncoder.encodeAddress(address(uint160(_transaction.to))); + bytes memory encodedValue = RLPEncoder.encodeUint256(_transaction.value); + encodedFixedLengthParams = bytes.concat( + encodedChainId, + encodedNonce, + encodedMaxPriorityFeePerGas, + encodedMaxFeePerGas, + encodedGasLimit, + encodedTo, + encodedValue + ); + } + + // Encode only the length of the transaction data, and not the data itself, + // so as not to copy to memory a potentially huge transaction data twice. + bytes memory encodedDataLength; + { + // Safe cast, because the length of the transaction data can't be so large. + uint64 txDataLen = uint64(_transaction.data.length); + if (txDataLen != 1) { + // If the length is not equal to one, then only using the length can it be encoded definitely. + encodedDataLength = RLPEncoder.encodeNonSingleBytesLen(txDataLen); + } else if (_transaction.data[0] >= 0x80) { + // If input is a byte in [0x80, 0xff] range, RLP encoding will concatenates 0x81 with the byte. + encodedDataLength = hex"81"; + } + // Otherwise the length is not encoded at all. + } + + // On zkSync, access lists are always zero length (at least for now). + bytes memory encodedAccessListLength = RLPEncoder.encodeListLen(0); + + bytes memory rEncoded; + { + uint256 rInt = uint256(bytes32(_transaction.signature[0:32])); + rEncoded = RLPEncoder.encodeUint256(rInt); + } + bytes memory sEncoded; + { + uint256 sInt = uint256(bytes32(_transaction.signature[32:64])); + sEncoded = RLPEncoder.encodeUint256(sInt); + } + bytes memory vEncoded; + { + uint256 vInt = uint256(uint8(_transaction.signature[64])); + require(vInt == 27 || vInt == 28, "Invalid v value"); + + vEncoded = RLPEncoder.encodeUint256(vInt - 27); + } + + bytes memory encodedListLength; + unchecked { + uint256 listLength = encodedFixedLengthParams.length + + encodedDataLength.length + + _transaction.data.length + + encodedAccessListLength.length + + rEncoded.length + + sEncoded.length + + vEncoded.length; + + // Safe cast, because the length of the list can't be so large. + encodedListLength = RLPEncoder.encodeListLen(uint64(listLength)); + } + + return + keccak256( + bytes.concat( + "\x02", + encodedListLength, + encodedFixedLengthParams, + encodedDataLength, + _transaction.data, + encodedAccessListLength, + vEncoded, + rEncoded, + sEncoded + ) + ); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/ComplexUpgrader.sol b/.test-node-subtree/etc/system-contracts/contracts/ComplexUpgrader.sol new file mode 100644 index 00000000..2f4d886c --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/ComplexUpgrader.sol @@ -0,0 +1,32 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {IComplexUpgrader} from "./interfaces/IComplexUpgrader.sol"; +import {FORCE_DEPLOYER} from "./Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice Upgrader which should be used to perform complex multistep upgrades on L2. In case some custom logic for an upgrade is needed + * this logic should be deployed into the user space and then this contract will delegatecall to the deployed contract. + */ +contract ComplexUpgrader is IComplexUpgrader { + /// @notice Executes an upgrade process by delegating calls to another contract. + /// @dev This function allows only the `FORCE_DEPLOYER` to initiate the upgrade. + /// If the delegate call fails, the function will revert the transaction, returning the error message + /// provided by the delegated contract. + /// @param _delegateTo the address of the contract to which the calls will be delegated + /// @param _calldata the calldata to be delegate called in the `_delegateTo` contract + function upgrade(address _delegateTo, bytes calldata _calldata) external payable { + require(msg.sender == FORCE_DEPLOYER, "Can only be called by FORCE_DEPLOYER"); + + require(_delegateTo.code.length > 0, "Delegatee is an EOA"); + (bool success, bytes memory returnData) = _delegateTo.delegatecall(_calldata); + assembly { + if iszero(success) { + revert(add(returnData, 0x20), mload(returnData)) + } + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/Compressor.sol b/.test-node-subtree/etc/system-contracts/contracts/Compressor.sol new file mode 100644 index 00000000..24aac725 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/Compressor.sol @@ -0,0 +1,250 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {ICompressor, OPERATION_BITMASK, LENGTH_BITS_OFFSET, MAX_ENUMERATION_INDEX_SIZE} from "./interfaces/ICompressor.sol"; +import {ISystemContract} from "./interfaces/ISystemContract.sol"; +import {Utils} from "./libraries/Utils.sol"; +import {UnsafeBytesCalldata} from "./libraries/UnsafeBytesCalldata.sol"; +import {EfficientCall} from "./libraries/EfficientCall.sol"; +import {L1_MESSENGER_CONTRACT, INITIAL_WRITE_STARTING_POSITION, COMPRESSED_INITIAL_WRITE_SIZE, STATE_DIFF_ENTRY_SIZE, STATE_DIFF_ENUM_INDEX_OFFSET, STATE_DIFF_FINAL_VALUE_OFFSET, STATE_DIFF_DERIVED_KEY_OFFSET, DERIVED_KEY_LENGTH, VALUE_LENGTH, ENUM_INDEX_LENGTH, KNOWN_CODE_STORAGE_CONTRACT} from "./Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice Contract with code pertaining to compression for zkEVM; at the moment this is used for bytecode compression + * and state diff compression validation. + * @dev Every deployed bytecode/published state diffs in zkEVM should be publicly restorable from the L1 data availability. + * For this reason, the user may request the sequencer to publish the original bytecode and mark it as known. + * Or the user may compress the bytecode and publish it instead (fewer data onchain!). At the end of every L1 Batch + * we publish pubdata, part of which contains the state diffs that occurred within the batch. + */ +contract Compressor is ICompressor, ISystemContract { + using UnsafeBytesCalldata for bytes; + + /// @notice Verify the compressed bytecode and publish it on the L1. + /// @param _bytecode The original bytecode to be verified against. + /// @param _rawCompressedData The compressed bytecode in a format of: + /// - 2 bytes: the length of the dictionary + /// - N bytes: the dictionary + /// - M bytes: the encoded data + /// @dev The dictionary is a sequence of 8-byte chunks, each of them has the associated index. + /// @dev The encoded data is a sequence of 2-byte chunks, each of them is an index of the dictionary. + /// @dev The compression algorithm works as follows: + /// 1. The original bytecode is split into 8-byte chunks. + /// Since the bytecode size is always a multiple of 32, this is always possible. + /// 2. For each 8-byte chunk in the original bytecode: + /// * If the chunk is not already in the dictionary, it is added to the dictionary array. + /// * If the dictionary becomes overcrowded (2^16 + 1 elements), the compression process will fail. + /// * The 2-byte index of the chunk in the dictionary is added to the encoded data. + /// @dev Currently, the method may be called only from the bootloader because the server is not ready to publish bytecodes + /// in internal transactions. However, in the future, we will allow everyone to publish compressed bytecodes. + function publishCompressedBytecode( + bytes calldata _bytecode, + bytes calldata _rawCompressedData + ) external payable onlyCallFromBootloader returns (bytes32 bytecodeHash) { + unchecked { + (bytes calldata dictionary, bytes calldata encodedData) = _decodeRawBytecode(_rawCompressedData); + + require(dictionary.length % 8 == 0, "Dictionary length should be a multiple of 8"); + require(dictionary.length <= 2 ** 16 * 8, "Dictionary is too big"); + require( + encodedData.length * 4 == _bytecode.length, + "Encoded data length should be 4 times shorter than the original bytecode" + ); + + for (uint256 encodedDataPointer = 0; encodedDataPointer < encodedData.length; encodedDataPointer += 2) { + uint256 indexOfEncodedChunk = uint256(encodedData.readUint16(encodedDataPointer)) * 8; + require(indexOfEncodedChunk < dictionary.length, "Encoded chunk index is out of bounds"); + + uint64 encodedChunk = dictionary.readUint64(indexOfEncodedChunk); + uint64 realChunk = _bytecode.readUint64(encodedDataPointer * 4); + + require(encodedChunk == realChunk, "Encoded chunk does not match the original bytecode"); + } + } + + bytecodeHash = Utils.hashL2Bytecode(_bytecode); + L1_MESSENGER_CONTRACT.sendToL1(_rawCompressedData); + KNOWN_CODE_STORAGE_CONTRACT.markBytecodeAsPublished(bytecodeHash); + } + + /// @notice Verifies that the compression of state diffs has been done correctly for the {_stateDiffs} param. + /// @param _numberOfStateDiffs The number of state diffs being checked. + /// @param _enumerationIndexSize Number of bytes used to represent an enumeration index for repeated writes. + /// @param _stateDiffs Encoded full state diff structs. See the first dev comment below for encoding. + /// @param _compressedStateDiffs The compressed state diffs + /// @dev We don't verify that the size of {_stateDiffs} is equivalent to {_numberOfStateDiffs} * STATE_DIFF_ENTRY_SIZE since that check is + /// done within the L1Messenger calling contract. + /// @return stateDiffHash Hash of the encoded (uncompressed) state diffs to be committed to via system log. + /// @dev This check assumes that the ordering of state diffs are sorted by (address, key) for the encoded state diffs and + /// then the compressed are sorted the same but with all the initial writes coming before the repeated writes. + /// @dev state diff: [20bytes address][32bytes key][32bytes derived key][8bytes enum index][32bytes initial value][32bytes final value] + /// @dev The compression format: + /// - 2 bytes: number of initial writes + /// - N bytes initial writes + /// - 32 bytes derived key + /// - 1 byte metadata: + /// - first 5 bits: length in bytes of compressed value + /// - last 3 bits: operation + /// - 0 -> Nothing (32 bytes) + /// - 1 -> Add + /// - 2 -> Subtract + /// - 3 -> Transform (< 32 bytes) + /// - Len Bytes: Compressed Value + /// - M bytes repeated writes + /// - {_enumerationIndexSize} bytes for enumeration index + /// - 1 byte metadata: + /// - first 5 bits: length in bytes of compressed value + /// - last 3 bits: operation + /// - 0 -> Nothing (32 bytes) + /// - 1 -> Add + /// - 2 -> Subtract + /// - 3 -> Transform (< 32 bytes) + /// - Len Bytes: Compressed Value + function verifyCompressedStateDiffs( + uint256 _numberOfStateDiffs, + uint256 _enumerationIndexSize, + bytes calldata _stateDiffs, + bytes calldata _compressedStateDiffs + ) external payable onlyCallFrom(address(L1_MESSENGER_CONTRACT)) returns (bytes32 stateDiffHash) { + // We do not enforce the operator to use the optimal, i.e. the minimally possible _enumerationIndexSize. + // We do enforce however, that the _enumerationIndexSize is not larger than 8 bytes long, which is the + // maximal ever possible size for enumeration index. + require(_enumerationIndexSize <= MAX_ENUMERATION_INDEX_SIZE, "enumeration index size is too large"); + + uint256 numberOfInitialWrites = uint256(_compressedStateDiffs.readUint16(0)); + + uint256 stateDiffPtr = 2; + uint256 numInitialWritesProcessed = 0; + + // Process initial writes + for (uint256 i = 0; i < _numberOfStateDiffs * STATE_DIFF_ENTRY_SIZE; i += STATE_DIFF_ENTRY_SIZE) { + bytes calldata stateDiff = _stateDiffs[i:i + STATE_DIFF_ENTRY_SIZE]; + uint64 enumIndex = stateDiff.readUint64(84); + if (enumIndex != 0) { + // It is a repeated write, so we skip it. + continue; + } + + numInitialWritesProcessed++; + + bytes32 derivedKey = stateDiff.readBytes32(52); + uint256 initValue = stateDiff.readUint256(92); + uint256 finalValue = stateDiff.readUint256(124); + require(derivedKey == _compressedStateDiffs.readBytes32(stateDiffPtr), "iw: initial key mismatch"); + stateDiffPtr += 32; + + uint8 metadata = uint8(bytes1(_compressedStateDiffs[stateDiffPtr])); + stateDiffPtr++; + uint8 operation = metadata & OPERATION_BITMASK; + uint8 len = operation == 0 ? 32 : metadata >> LENGTH_BITS_OFFSET; + _verifyValueCompression( + initValue, + finalValue, + operation, + _compressedStateDiffs[stateDiffPtr:stateDiffPtr + len] + ); + stateDiffPtr += len; + } + + require(numInitialWritesProcessed == numberOfInitialWrites, "Incorrect number of initial storage diffs"); + + // Process repeated writes + for (uint256 i = 0; i < _numberOfStateDiffs * STATE_DIFF_ENTRY_SIZE; i += STATE_DIFF_ENTRY_SIZE) { + bytes calldata stateDiff = _stateDiffs[i:i + STATE_DIFF_ENTRY_SIZE]; + uint64 enumIndex = stateDiff.readUint64(84); + if (enumIndex == 0) { + continue; + } + + uint256 initValue = stateDiff.readUint256(92); + uint256 finalValue = stateDiff.readUint256(124); + uint256 compressedEnumIndex = _sliceToUint256( + _compressedStateDiffs[stateDiffPtr:stateDiffPtr + _enumerationIndexSize] + ); + require(enumIndex == compressedEnumIndex, "rw: enum key mismatch"); + stateDiffPtr += _enumerationIndexSize; + + uint8 metadata = uint8(bytes1(_compressedStateDiffs[stateDiffPtr])); + stateDiffPtr += 1; + uint8 operation = metadata & OPERATION_BITMASK; + uint8 len = operation == 0 ? 32 : metadata >> LENGTH_BITS_OFFSET; + _verifyValueCompression( + initValue, + finalValue, + operation, + _compressedStateDiffs[stateDiffPtr:stateDiffPtr + len] + ); + stateDiffPtr += len; + } + + require(stateDiffPtr == _compressedStateDiffs.length, "Extra data in _compressedStateDiffs"); + + stateDiffHash = EfficientCall.keccak(_stateDiffs); + } + + /// @notice Decode the raw compressed data into the dictionary and the encoded data. + /// @param _rawCompressedData The compressed bytecode in a format of: + /// - 2 bytes: the bytes length of the dictionary + /// - N bytes: the dictionary + /// - M bytes: the encoded data + function _decodeRawBytecode( + bytes calldata _rawCompressedData + ) internal pure returns (bytes calldata dictionary, bytes calldata encodedData) { + unchecked { + // The dictionary length can't be more than 2^16, so it fits into 2 bytes. + uint256 dictionaryLen = uint256(_rawCompressedData.readUint16(0)); + dictionary = _rawCompressedData[2:2 + dictionaryLen * 8]; + encodedData = _rawCompressedData[2 + dictionaryLen * 8:]; + } + } + + /// @notice Verify value compression was done correct given initial value, final value, operation, and compressed value + /// @param _initialValue Previous value of key/enumeration index. + /// @param _finalValue Updated value of key/enumeration index. + /// @param _operation The operation that was performed on value. + /// @param _compressedValue The slice of calldata with compressed value either representing the final + /// value or difference between initial and final value. It should be of arbitrary length less than or equal to 32 bytes. + /// @dev It is the responsibility of the caller of this function to ensure that the `_compressedValue` has length no longer than 32 bytes. + /// @dev Operation id mapping: + /// 0 -> Nothing (32 bytes) + /// 1 -> Add + /// 2 -> Subtract + /// 3 -> Transform (< 32 bytes) + function _verifyValueCompression( + uint256 _initialValue, + uint256 _finalValue, + uint256 _operation, + bytes calldata _compressedValue + ) internal pure { + uint256 convertedValue = _sliceToUint256(_compressedValue); + + unchecked { + if (_operation == 0 || _operation == 3) { + require(convertedValue == _finalValue, "transform or no compression: compressed and final mismatch"); + } else if (_operation == 1) { + require( + _initialValue + convertedValue == _finalValue, + "add: initial plus converted not equal to final" + ); + } else if (_operation == 2) { + require( + _initialValue - convertedValue == _finalValue, + "sub: initial minus converted not equal to final" + ); + } else { + revert("unsupported operation"); + } + } + } + + /// @notice Converts a calldata slice into uint256. It is the responsibility of the caller to ensure that + /// the _calldataSlice has length no longer than 32 bytes + /// @param _calldataSlice The calldata slice to convert to uint256 + /// @return number The uint256 representation of the calldata slice + function _sliceToUint256(bytes calldata _calldataSlice) internal pure returns (uint256 number) { + number = uint256(bytes32(_calldataSlice)); + number >>= (256 - (_calldataSlice.length * 8)); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/Constants.sol b/.test-node-subtree/etc/system-contracts/contracts/Constants.sol new file mode 100644 index 00000000..f0896710 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/Constants.sol @@ -0,0 +1,124 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {IAccountCodeStorage} from "./interfaces/IAccountCodeStorage.sol"; +import {INonceHolder} from "./interfaces/INonceHolder.sol"; +import {IContractDeployer} from "./interfaces/IContractDeployer.sol"; +import {IKnownCodesStorage} from "./interfaces/IKnownCodesStorage.sol"; +import {IImmutableSimulator} from "./interfaces/IImmutableSimulator.sol"; +import {IEthToken} from "./interfaces/IEthToken.sol"; +import {IL1Messenger} from "./interfaces/IL1Messenger.sol"; +import {ISystemContext} from "./interfaces/ISystemContext.sol"; +import {ICompressor} from "./interfaces/ICompressor.sol"; +import {IComplexUpgrader} from "./interfaces/IComplexUpgrader.sol"; +import {IBootloaderUtilities} from "./interfaces/IBootloaderUtilities.sol"; + +/// @dev All the system contracts introduced by zkSync have their addresses +/// started from 2^15 in order to avoid collision with Ethereum precompiles. +uint160 constant SYSTEM_CONTRACTS_OFFSET = 0x8000; // 2^15 + +/// @dev All the system contracts must be located in the kernel space, +/// i.e. their addresses must be below 2^16. +uint160 constant MAX_SYSTEM_CONTRACT_ADDRESS = 0xffff; // 2^16 - 1 + +address constant ECRECOVER_SYSTEM_CONTRACT = address(0x01); +address constant SHA256_SYSTEM_CONTRACT = address(0x02); +address constant ECADD_SYSTEM_CONTRACT = address(0x06); +address constant ECMUL_SYSTEM_CONTRACT = address(0x07); + +/// @dev The maximal possible address of an L1-like precompie. These precompiles maintain the following properties: +/// - Their extcodehash is EMPTY_STRING_KECCAK +/// - Their extcodesize is 0 despite having a bytecode formally deployed there. +uint256 constant CURRENT_MAX_PRECOMPILE_ADDRESS = 0xff; + +address payable constant BOOTLOADER_FORMAL_ADDRESS = payable(address(SYSTEM_CONTRACTS_OFFSET + 0x01)); +IAccountCodeStorage constant ACCOUNT_CODE_STORAGE_SYSTEM_CONTRACT = IAccountCodeStorage( + address(SYSTEM_CONTRACTS_OFFSET + 0x02) +); +INonceHolder constant NONCE_HOLDER_SYSTEM_CONTRACT = INonceHolder(address(SYSTEM_CONTRACTS_OFFSET + 0x03)); +IKnownCodesStorage constant KNOWN_CODE_STORAGE_CONTRACT = IKnownCodesStorage(address(SYSTEM_CONTRACTS_OFFSET + 0x04)); +IImmutableSimulator constant IMMUTABLE_SIMULATOR_SYSTEM_CONTRACT = IImmutableSimulator( + address(SYSTEM_CONTRACTS_OFFSET + 0x05) +); +IContractDeployer constant DEPLOYER_SYSTEM_CONTRACT = IContractDeployer(address(SYSTEM_CONTRACTS_OFFSET + 0x06)); + +// A contract that is allowed to deploy any codehash +// on any address. To be used only during an upgrade. +address constant FORCE_DEPLOYER = address(SYSTEM_CONTRACTS_OFFSET + 0x07); +IL1Messenger constant L1_MESSENGER_CONTRACT = IL1Messenger(address(SYSTEM_CONTRACTS_OFFSET + 0x08)); +address constant MSG_VALUE_SYSTEM_CONTRACT = address(SYSTEM_CONTRACTS_OFFSET + 0x09); + +IEthToken constant ETH_TOKEN_SYSTEM_CONTRACT = IEthToken(address(SYSTEM_CONTRACTS_OFFSET + 0x0a)); + +address constant KECCAK256_SYSTEM_CONTRACT = address(SYSTEM_CONTRACTS_OFFSET + 0x10); + +ISystemContext constant SYSTEM_CONTEXT_CONTRACT = ISystemContext(payable(address(SYSTEM_CONTRACTS_OFFSET + 0x0b))); + +IBootloaderUtilities constant BOOTLOADER_UTILITIES = IBootloaderUtilities(address(SYSTEM_CONTRACTS_OFFSET + 0x0c)); + +address constant EVENT_WRITER_CONTRACT = address(SYSTEM_CONTRACTS_OFFSET + 0x0d); + +ICompressor constant COMPRESSOR_CONTRACT = ICompressor(address(SYSTEM_CONTRACTS_OFFSET + 0x0e)); + +IComplexUpgrader constant COMPLEX_UPGRADER_CONTRACT = IComplexUpgrader(address(SYSTEM_CONTRACTS_OFFSET + 0x0f)); + +/// @dev If the bitwise AND of the extraAbi[2] param when calling the MSG_VALUE_SIMULATOR +/// is non-zero, the call will be assumed to be a system one. +uint256 constant MSG_VALUE_SIMULATOR_IS_SYSTEM_BIT = 1; + +/// @dev The maximal msg.value that context can have +uint256 constant MAX_MSG_VALUE = 2 ** 128 - 1; + +/// @dev Prefix used during derivation of account addresses using CREATE2 +/// @dev keccak256("zksyncCreate2") +bytes32 constant CREATE2_PREFIX = 0x2020dba91b30cc0006188af794c2fb30dd8520db7e2c088b7fc7c103c00ca494; +/// @dev Prefix used during derivation of account addresses using CREATE +/// @dev keccak256("zksyncCreate") +bytes32 constant CREATE_PREFIX = 0x63bae3a9951d38e8a3fbb7b70909afc1200610fc5bc55ade242f815974674f23; + +/// @dev Each state diff consists of 156 bytes of actual data and 116 bytes of unused padding, needed for circuit efficiency. +uint256 constant STATE_DIFF_ENTRY_SIZE = 272; + +/// @dev While the "real" amount of pubdata that can be sent rarely exceeds the 110k - 120k, it is better to +/// allow the operator to provide any reasonably large value in order to avoid unneeded constraints on the operator. +uint256 constant MAX_ALLOWED_PUBDATA_PER_BATCH = 520000; + +enum SystemLogKey { + L2_TO_L1_LOGS_TREE_ROOT_KEY, + TOTAL_L2_TO_L1_PUBDATA_KEY, + STATE_DIFF_HASH_KEY, + PACKED_BATCH_AND_L2_BLOCK_TIMESTAMP_KEY, + PREV_BATCH_HASH_KEY, + CHAINED_PRIORITY_TXN_HASH_KEY, + NUMBER_OF_LAYER_1_TXS_KEY, + EXPECTED_SYSTEM_CONTRACT_UPGRADE_TX_HASH_KEY +} + +/// @dev The number of leaves in the L2->L1 log Merkle tree. +/// While formally a tree of any length is acceptable, the node supports only a constant length of 2048 leaves. +uint256 constant L2_TO_L1_LOGS_MERKLE_TREE_LEAVES = 2048; + +/// @dev The length of the derived key in bytes inside compressed state diffs. +uint256 constant DERIVED_KEY_LENGTH = 32; +/// @dev The length of the enum index in bytes inside compressed state diffs. +uint256 constant ENUM_INDEX_LENGTH = 8; +/// @dev The length of value in bytes inside compressed state diffs. +uint256 constant VALUE_LENGTH = 32; + +/// @dev The length of the compressed initial storage write in bytes. +uint256 constant COMPRESSED_INITIAL_WRITE_SIZE = DERIVED_KEY_LENGTH + VALUE_LENGTH; +/// @dev The length of the compressed repeated storage write in bytes. +uint256 constant COMPRESSED_REPEATED_WRITE_SIZE = ENUM_INDEX_LENGTH + VALUE_LENGTH; + +/// @dev The position from which the initial writes start in the compressed state diffs. +uint256 constant INITIAL_WRITE_STARTING_POSITION = 4; + +/// @dev Each storage diffs consists of the following elements: +/// [20bytes address][32bytes key][32bytes derived key][8bytes enum index][32bytes initial value][32bytes final value] +/// @dev The offset of the deriived key in a storage diff. +uint256 constant STATE_DIFF_DERIVED_KEY_OFFSET = 52; +/// @dev The offset of the enum index in a storage diff. +uint256 constant STATE_DIFF_ENUM_INDEX_OFFSET = 84; +/// @dev The offset of the final value in a storage diff. +uint256 constant STATE_DIFF_FINAL_VALUE_OFFSET = 124; diff --git a/.test-node-subtree/etc/system-contracts/contracts/ContractDeployer.sol b/.test-node-subtree/etc/system-contracts/contracts/ContractDeployer.sol new file mode 100644 index 00000000..50af9742 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/ContractDeployer.sol @@ -0,0 +1,378 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {ImmutableData} from "./interfaces/IImmutableSimulator.sol"; +import {IContractDeployer} from "./interfaces/IContractDeployer.sol"; +import {CREATE2_PREFIX, CREATE_PREFIX, NONCE_HOLDER_SYSTEM_CONTRACT, ACCOUNT_CODE_STORAGE_SYSTEM_CONTRACT, FORCE_DEPLOYER, MAX_SYSTEM_CONTRACT_ADDRESS, KNOWN_CODE_STORAGE_CONTRACT, ETH_TOKEN_SYSTEM_CONTRACT, IMMUTABLE_SIMULATOR_SYSTEM_CONTRACT, COMPLEX_UPGRADER_CONTRACT, KECCAK256_SYSTEM_CONTRACT} from "./Constants.sol"; + +import {Utils} from "./libraries/Utils.sol"; +import {EfficientCall} from "./libraries/EfficientCall.sol"; +import {SystemContractHelper} from "./libraries/SystemContractHelper.sol"; +import {ISystemContract} from "./interfaces/ISystemContract.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice System smart contract that is responsible for deploying other smart contracts on zkSync. + * @dev The contract is responsible for generating the address of the deployed smart contract, + * incrementing the deployment nonce and making sure that the constructor is never called twice in a contract. + * Note, contracts with bytecode that have already been published to L1 once + * do not need to be published anymore. + */ +contract ContractDeployer is IContractDeployer, ISystemContract { + /// @notice Information about an account contract. + /// @dev For EOA and simple contracts (i.e. not accounts) this value is 0. + mapping(address => AccountInfo) internal accountInfo; + + modifier onlySelf() { + require(msg.sender == address(this), "Callable only by self"); + _; + } + + /// @notice Returns information about a certain account. + function getAccountInfo(address _address) external view returns (AccountInfo memory info) { + return accountInfo[_address]; + } + + /// @notice Returns the account abstraction version if `_address` is a deployed contract. + /// Returns the latest supported account abstraction version if `_address` is an EOA. + function extendedAccountVersion(address _address) public view returns (AccountAbstractionVersion) { + AccountInfo memory info = accountInfo[_address]; + if (info.supportedAAVersion != AccountAbstractionVersion.None) { + return info.supportedAAVersion; + } + + // It is an EOA, it is still an account. + if ( + _address > address(MAX_SYSTEM_CONTRACT_ADDRESS) && + ACCOUNT_CODE_STORAGE_SYSTEM_CONTRACT.getRawCodeHash(_address) == 0 + ) { + return AccountAbstractionVersion.Version1; + } + + return AccountAbstractionVersion.None; + } + + /// @notice Stores the new account information + function _storeAccountInfo(address _address, AccountInfo memory _newInfo) internal { + accountInfo[_address] = _newInfo; + } + + /// @notice Update the used version of the account. + /// @param _version The new version of the AA protocol to use. + /// @dev Note that it allows changes from account to non-account and vice versa. + function updateAccountVersion(AccountAbstractionVersion _version) external onlySystemCall { + accountInfo[msg.sender].supportedAAVersion = _version; + + emit AccountVersionUpdated(msg.sender, _version); + } + + /// @notice Updates the nonce ordering of the account. Currently, + /// it only allows changes from sequential to arbitrary ordering. + /// @param _nonceOrdering The new nonce ordering to use. + function updateNonceOrdering(AccountNonceOrdering _nonceOrdering) external onlySystemCall { + AccountInfo memory currentInfo = accountInfo[msg.sender]; + + require( + _nonceOrdering == AccountNonceOrdering.Arbitrary && + currentInfo.nonceOrdering == AccountNonceOrdering.Sequential, + "It is only possible to change from sequential to arbitrary ordering" + ); + + currentInfo.nonceOrdering = _nonceOrdering; + _storeAccountInfo(msg.sender, currentInfo); + + emit AccountNonceOrderingUpdated(msg.sender, _nonceOrdering); + } + + /// @notice Calculates the address of a deployed contract via create2 + /// @param _sender The account that deploys the contract. + /// @param _bytecodeHash The correctly formatted hash of the bytecode. + /// @param _salt The create2 salt. + /// @param _input The constructor data. + /// @return newAddress The derived address of the account. + function getNewAddressCreate2( + address _sender, + bytes32 _bytecodeHash, + bytes32 _salt, + bytes calldata _input + ) public view override returns (address newAddress) { + // No collision is possible with the Ethereum's CREATE2, since + // the prefix begins with 0x20.... + bytes32 constructorInputHash = EfficientCall.keccak(_input); + + bytes32 hash = keccak256( + bytes.concat(CREATE2_PREFIX, bytes32(uint256(uint160(_sender))), _salt, _bytecodeHash, constructorInputHash) + ); + + newAddress = address(uint160(uint256(hash))); + } + + /// @notice Calculates the address of a deployed contract via create + /// @param _sender The account that deploys the contract. + /// @param _senderNonce The deploy nonce of the sender's account. + function getNewAddressCreate( + address _sender, + uint256 _senderNonce + ) public pure override returns (address newAddress) { + // No collision is possible with the Ethereum's CREATE, since + // the prefix begins with 0x63.... + bytes32 hash = keccak256( + bytes.concat(CREATE_PREFIX, bytes32(uint256(uint160(_sender))), bytes32(_senderNonce)) + ); + + newAddress = address(uint160(uint256(hash))); + } + + /// @notice Deploys a contract with similar address derivation rules to the EVM's `CREATE2` opcode. + /// @param _salt The CREATE2 salt + /// @param _bytecodeHash The correctly formatted hash of the bytecode. + /// @param _input The constructor calldata + /// @dev In case of a revert, the zero address should be returned. + function create2( + bytes32 _salt, + bytes32 _bytecodeHash, + bytes calldata _input + ) external payable override returns (address) { + return create2Account(_salt, _bytecodeHash, _input, AccountAbstractionVersion.None); + } + + /// @notice Deploys a contract with similar address derivation rules to the EVM's `CREATE` opcode. + /// @param _bytecodeHash The correctly formatted hash of the bytecode. + /// @param _input The constructor calldata + /// @dev This method also accepts nonce as one of its parameters. + /// It is not used anywhere and it needed simply for the consistency for the compiler + /// @dev In case of a revert, the zero address should be returned. + /// Note: this method may be callable only in system mode, + /// that is checked in the `createAccount` by `onlySystemCall` modifier. + function create( + bytes32 _salt, + bytes32 _bytecodeHash, + bytes calldata _input + ) external payable override returns (address) { + return createAccount(_salt, _bytecodeHash, _input, AccountAbstractionVersion.None); + } + + /// @notice Deploys a contract account with similar address derivation rules to the EVM's `CREATE2` opcode. + /// @param _salt The CREATE2 salt + /// @param _bytecodeHash The correctly formatted hash of the bytecode. + /// @param _input The constructor calldata. + /// @param _aaVersion The account abstraction version to use. + /// @dev In case of a revert, the zero address should be returned. + /// Note: this method may be callable only in system mode, + /// that is checked in the `createAccount` by `onlySystemCall` modifier. + function create2Account( + bytes32 _salt, + bytes32 _bytecodeHash, + bytes calldata _input, + AccountAbstractionVersion _aaVersion + ) public payable override onlySystemCall returns (address) { + NONCE_HOLDER_SYSTEM_CONTRACT.incrementDeploymentNonce(msg.sender); + address newAddress = getNewAddressCreate2(msg.sender, _bytecodeHash, _salt, _input); + + _nonSystemDeployOnAddress(_bytecodeHash, newAddress, _aaVersion, _input); + + return newAddress; + } + + /// @notice Deploys a contract account with similar address derivation rules to the EVM's `CREATE` opcode. + /// @param _bytecodeHash The correctly formatted hash of the bytecode. + /// @param _input The constructor calldata. + /// @param _aaVersion The account abstraction version to use. + /// @dev This method also accepts salt as one of its parameters. + /// It is not used anywhere and it needed simply for the consistency for the compiler + /// @dev In case of a revert, the zero address should be returned. + function createAccount( + bytes32, // salt + bytes32 _bytecodeHash, + bytes calldata _input, + AccountAbstractionVersion _aaVersion + ) public payable override onlySystemCall returns (address) { + uint256 senderNonce = NONCE_HOLDER_SYSTEM_CONTRACT.incrementDeploymentNonce(msg.sender); + address newAddress = getNewAddressCreate(msg.sender, senderNonce); + + _nonSystemDeployOnAddress(_bytecodeHash, newAddress, _aaVersion, _input); + + return newAddress; + } + + /// @notice A struct that describes a forced deployment on an address + struct ForceDeployment { + // The bytecode hash to put on an address + bytes32 bytecodeHash; + // The address on which to deploy the bytecodehash to + address newAddress; + // Whether to run the constructor on the force deployment + bool callConstructor; + // The value with which to initialize a contract + uint256 value; + // The constructor calldata + bytes input; + } + + /// @notice The method that can be used to forcefully deploy a contract. + /// @param _deployment Information about the forced deployment. + /// @param _sender The `msg.sender` inside the constructor call. + function forceDeployOnAddress(ForceDeployment calldata _deployment, address _sender) external payable onlySelf { + _ensureBytecodeIsKnown(_deployment.bytecodeHash); + + // Since the `forceDeployOnAddress` function is called only during upgrades, the Governance is trusted to correctly select + // the addresses to deploy the new bytecodes to and to assess whether overriding the AccountInfo for the "force-deployed" + // contract is acceptable. + AccountInfo memory newAccountInfo; + newAccountInfo.supportedAAVersion = AccountAbstractionVersion.None; + // Accounts have sequential nonces by default. + newAccountInfo.nonceOrdering = AccountNonceOrdering.Sequential; + _storeAccountInfo(_deployment.newAddress, newAccountInfo); + + _constructContract( + _sender, + _deployment.newAddress, + _deployment.bytecodeHash, + _deployment.input, + false, + _deployment.callConstructor + ); + } + + /// @notice The method that is temporarily needed to upgrade the Keccak256 precompile. It is to be removed in the + /// future. Unlike a normal forced deployment, it does not update account information as it requires updating a + /// mapping, and so requires Keccak256 precompile to work already. + /// @dev This method expects the sender (FORCE_DEPLOYER) to provide the correct bytecode hash for the Keccak256 + /// precompile. + function forceDeployKeccak256(bytes32 _keccak256BytecodeHash) external payable onlyCallFrom(FORCE_DEPLOYER) { + _ensureBytecodeIsKnown(_keccak256BytecodeHash); + _constructContract( + msg.sender, + address(KECCAK256_SYSTEM_CONTRACT), + _keccak256BytecodeHash, + msg.data[0:0], + false, + false + ); + } + + /// @notice This method is to be used only during an upgrade to set bytecodes on specific addresses. + /// @dev We do not require `onlySystemCall` here, since the method is accessible only + /// by `FORCE_DEPLOYER`. + function forceDeployOnAddresses(ForceDeployment[] calldata _deployments) external payable { + require( + msg.sender == FORCE_DEPLOYER || msg.sender == address(COMPLEX_UPGRADER_CONTRACT), + "Can only be called by FORCE_DEPLOYER or COMPLEX_UPGRADER_CONTRACT" + ); + + uint256 deploymentsLength = _deployments.length; + // We need to ensure that the `value` provided by the call is enough to provide `value` + // for all of the deployments + uint256 sumOfValues = 0; + for (uint256 i = 0; i < deploymentsLength; ++i) { + sumOfValues += _deployments[i].value; + } + require(msg.value == sumOfValues, "`value` provided is not equal to the combined `value`s of deployments"); + + for (uint256 i = 0; i < deploymentsLength; ++i) { + this.forceDeployOnAddress{value: _deployments[i].value}(_deployments[i], msg.sender); + } + } + + function _nonSystemDeployOnAddress( + bytes32 _bytecodeHash, + address _newAddress, + AccountAbstractionVersion _aaVersion, + bytes calldata _input + ) internal { + require(_bytecodeHash != bytes32(0x0), "BytecodeHash cannot be zero"); + require(uint160(_newAddress) > MAX_SYSTEM_CONTRACT_ADDRESS, "Can not deploy contracts in kernel space"); + + // We do not allow deploying twice on the same address. + require( + ACCOUNT_CODE_STORAGE_SYSTEM_CONTRACT.getCodeHash(uint256(uint160(_newAddress))) == 0x0, + "Code hash is non-zero" + ); + // Do not allow deploying contracts to default accounts that have already executed transactions. + require(NONCE_HOLDER_SYSTEM_CONTRACT.getRawNonce(_newAddress) == 0x00, "Account is occupied"); + + _performDeployOnAddress(_bytecodeHash, _newAddress, _aaVersion, _input); + } + + /// @notice Deploy a certain bytecode on the address. + /// @param _bytecodeHash The correctly formatted hash of the bytecode. + /// @param _newAddress The address of the contract to be deployed. + /// @param _aaVersion The version of the account abstraction protocol to use. + /// @param _input The constructor calldata. + function _performDeployOnAddress( + bytes32 _bytecodeHash, + address _newAddress, + AccountAbstractionVersion _aaVersion, + bytes calldata _input + ) internal { + _ensureBytecodeIsKnown(_bytecodeHash); + + AccountInfo memory newAccountInfo; + newAccountInfo.supportedAAVersion = _aaVersion; + // Accounts have sequential nonces by default. + newAccountInfo.nonceOrdering = AccountNonceOrdering.Sequential; + _storeAccountInfo(_newAddress, newAccountInfo); + + _constructContract(msg.sender, _newAddress, _bytecodeHash, _input, false, true); + } + + /// @notice Check that bytecode hash is marked as known on the `KnownCodeStorage` system contracts + function _ensureBytecodeIsKnown(bytes32 _bytecodeHash) internal view { + uint256 knownCodeMarker = KNOWN_CODE_STORAGE_CONTRACT.getMarker(_bytecodeHash); + require(knownCodeMarker > 0, "The code hash is not known"); + } + + /// @notice Ensures that the _newAddress and assigns a new contract hash to it + /// @param _newAddress The address of the deployed contract + /// @param _bytecodeHash The correctly formatted hash of the bytecode. + function _storeConstructingByteCodeHashOnAddress(address _newAddress, bytes32 _bytecodeHash) internal { + // Set the "isConstructor" flag to the bytecode hash + bytes32 constructingBytecodeHash = Utils.constructingBytecodeHash(_bytecodeHash); + ACCOUNT_CODE_STORAGE_SYSTEM_CONTRACT.storeAccountConstructingCodeHash(_newAddress, constructingBytecodeHash); + } + + /// @notice Transfers the `msg.value` ETH to the deployed account & invokes its constructor. + /// This function must revert in case the deployment fails. + /// @param _sender The msg.sender to be used in the constructor + /// @param _newAddress The address of the deployed contract + /// @param _input The constructor calldata + /// @param _isSystem Whether the call should be a system call (could be possibly required in the future). + function _constructContract( + address _sender, + address _newAddress, + bytes32 _bytecodeHash, + bytes calldata _input, + bool _isSystem, + bool _callConstructor + ) internal { + uint256 value = msg.value; + if (_callConstructor) { + // 1. Transfer the balance to the new address on the constructor call. + if (value > 0) { + ETH_TOKEN_SYSTEM_CONTRACT.transferFromTo(address(this), _newAddress, value); + } + // 2. Set the constructed code hash on the account + _storeConstructingByteCodeHashOnAddress(_newAddress, _bytecodeHash); + + // 3. Call the constructor on behalf of the account + if (value > 0) { + // Safe to cast value, because `msg.value` <= `uint128.max` due to `MessageValueSimulator` invariant + SystemContractHelper.setValueForNextFarCall(uint128(value)); + } + bytes memory returnData = EfficientCall.mimicCall(gasleft(), _newAddress, _input, _sender, true, _isSystem); + // 4. Mark bytecode hash as constructed + ACCOUNT_CODE_STORAGE_SYSTEM_CONTRACT.markAccountCodeHashAsConstructed(_newAddress); + // 5. Set the contract immutables + ImmutableData[] memory immutables = abi.decode(returnData, (ImmutableData[])); + IMMUTABLE_SIMULATOR_SYSTEM_CONTRACT.setImmutables(_newAddress, immutables); + } else { + require(value == 0, "The value must be zero if we do not call the constructor"); + // If we do not call the constructor, we need to set the constructed code hash. + ACCOUNT_CODE_STORAGE_SYSTEM_CONTRACT.storeAccountConstructedCodeHash(_newAddress, _bytecodeHash); + } + + emit ContractDeployed(_sender, _bytecodeHash, _newAddress); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/DefaultAccount.sol b/.test-node-subtree/etc/system-contracts/contracts/DefaultAccount.sol new file mode 100644 index 00000000..b5cb46c9 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/DefaultAccount.sol @@ -0,0 +1,237 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "./interfaces/IAccount.sol"; +import "./libraries/TransactionHelper.sol"; +import "./libraries/SystemContractHelper.sol"; +import "./libraries/EfficientCall.sol"; +import {BOOTLOADER_FORMAL_ADDRESS, NONCE_HOLDER_SYSTEM_CONTRACT, DEPLOYER_SYSTEM_CONTRACT, INonceHolder} from "./Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice The default implementation of account. + * @dev The bytecode of the contract is set by default for all addresses for which no other bytecodes are deployed. + * @notice If the caller is not a bootloader always returns empty data on call, just like EOA does. + * @notice If it is delegate called always returns empty data, just like EOA does. + */ +contract DefaultAccount is IAccount { + using TransactionHelper for *; + + /** + * @dev Simulate the behavior of the EOA if the caller is not the bootloader. + * Essentially, for all non-bootloader callers halt the execution with empty return data. + * If all functions will use this modifier AND the contract will implement an empty payable fallback() + * then the contract will be indistinguishable from the EOA when called. + */ + modifier ignoreNonBootloader() { + if (msg.sender != BOOTLOADER_FORMAL_ADDRESS) { + // If function was called outside of the bootloader, behave like an EOA. + assembly { + return(0, 0) + } + } + // Continue execution if called from the bootloader. + _; + } + + /** + * @dev Simulate the behavior of the EOA if it is called via `delegatecall`. + * Thus, the default account on a delegate call behaves the same as EOA on Ethereum. + * If all functions will use this modifier AND the contract will implement an empty payable fallback() + * then the contract will be indistinguishable from the EOA when called. + */ + modifier ignoreInDelegateCall() { + address codeAddress = SystemContractHelper.getCodeAddress(); + if (codeAddress != address(this)) { + // If the function was delegate called, behave like an EOA. + assembly { + return(0, 0) + } + } + + // Continue execution if not delegate called. + _; + } + + /// @notice Validates the transaction & increments nonce. + /// @dev The transaction is considered accepted by the account if + /// the call to this function by the bootloader does not revert + /// and the nonce has been set as used. + /// @param _suggestedSignedHash The suggested hash of the transaction to be signed by the user. + /// This is the hash that is signed by the EOA by default. + /// @param _transaction The transaction structure itself. + /// @dev Besides the params above, it also accepts unused first paramter "_txHash", which + /// is the unique (canonical) hash of the transaction. + function validateTransaction( + bytes32, // _txHash + bytes32 _suggestedSignedHash, + Transaction calldata _transaction + ) external payable override ignoreNonBootloader ignoreInDelegateCall returns (bytes4 magic) { + magic = _validateTransaction(_suggestedSignedHash, _transaction); + } + + /// @notice Inner method for validating transaction and increasing the nonce + /// @param _suggestedSignedHash The hash of the transaction signed by the EOA + /// @param _transaction The transaction. + function _validateTransaction( + bytes32 _suggestedSignedHash, + Transaction calldata _transaction + ) internal returns (bytes4 magic) { + // Note, that nonce holder can only be called with "isSystem" flag. + SystemContractsCaller.systemCallWithPropagatedRevert( + uint32(gasleft()), + address(NONCE_HOLDER_SYSTEM_CONTRACT), + 0, + abi.encodeCall(INonceHolder.incrementMinNonceIfEquals, (_transaction.nonce)) + ); + + // Even though for the transaction types present in the system right now, + // we always provide the suggested signed hash, this should not be + // always expected. In case the bootloader has no clue what the default hash + // is, the bytes32(0) will be supplied. + bytes32 txHash = _suggestedSignedHash != bytes32(0) ? _suggestedSignedHash : _transaction.encodeHash(); + + // The fact there is are enough balance for the account + // should be checked explicitly to prevent user paying for fee for a + // transaction that wouldn't be included on Ethereum. + uint256 totalRequiredBalance = _transaction.totalRequiredBalance(); + require(totalRequiredBalance <= address(this).balance, "Not enough balance for fee + value"); + + if (_isValidSignature(txHash, _transaction.signature)) { + magic = ACCOUNT_VALIDATION_SUCCESS_MAGIC; + } + } + + /// + /// FOUNDRY SUPPORT START + /// + /// @notice Method called by the bootloader to execute the transaction. + /// @param _transaction The transaction to execute. + /// @dev It also accepts unused _txHash and _suggestedSignedHash parameters: + /// the unique (canonical) hash of the transaction and the suggested signed + /// hash of the transaction. + function executeTransaction( + bytes32, // _txHash + bytes32, // _suggestedSignedHash + Transaction calldata _transaction + ) external payable override ignoreNonBootloader ignoreInDelegateCall returns (bytes memory returnData) { + _execute(_transaction); + returnData = bytes(""); + /// + /// FOUNDRY SUPPORT END + /// + } + + /// @notice Method that should be used to initiate a transaction from this account by an external call. + /// @dev The custom account is supposed to implement this method to initiate a transaction on behalf + /// of the account via L1 -> L2 communication. However, the default account can initiate a transaction + /// from L1, so we formally implement the interface method, but it doesn't execute any logic. + /// @param _transaction The transaction to execute. + function executeTransactionFromOutside(Transaction calldata _transaction) external payable override { + // Behave the same as for fallback/receive, just execute nothing, returns nothing + } + + /// @notice Inner method for executing a transaction. + /// @param _transaction The transaction to execute. + function _execute(Transaction calldata _transaction) internal { + address to = address(uint160(_transaction.to)); + uint128 value = Utils.safeCastToU128(_transaction.value); + bytes calldata data = _transaction.data; + uint32 gas = Utils.safeCastToU32(gasleft()); + + // Note, that the deployment method from the deployer contract can only be called with a "systemCall" flag. + bool isSystemCall; + if (to == address(DEPLOYER_SYSTEM_CONTRACT) && data.length >= 4) { + bytes4 selector = bytes4(data[:4]); + // Check that called function is the deployment method, + // the others deployer method is not supposed to be called from the default account. + isSystemCall = + selector == DEPLOYER_SYSTEM_CONTRACT.create.selector || + selector == DEPLOYER_SYSTEM_CONTRACT.create2.selector || + selector == DEPLOYER_SYSTEM_CONTRACT.createAccount.selector || + selector == DEPLOYER_SYSTEM_CONTRACT.create2Account.selector; + } + bool success = EfficientCall.rawCall(gas, to, value, data, isSystemCall); + if (!success) { + EfficientCall.propagateRevert(); + } + } + + /// @notice Validation that the ECDSA signature of the transaction is correct. + /// @param _hash The hash of the transaction to be signed. + /// @param _signature The signature of the transaction. + /// @return EIP1271_SUCCESS_RETURN_VALUE if the signaure is correct. It reverts otherwise. + function _isValidSignature(bytes32 _hash, bytes memory _signature) internal view returns (bool) { + require(_signature.length == 65, "Signature length is incorrect"); + uint8 v; + bytes32 r; + bytes32 s; + // Signature loading code + // we jump 32 (0x20) as the first slot of bytes contains the length + // we jump 65 (0x41) per signature + // for v we load 32 bytes ending with v (the first 31 come from s) then apply a mask + assembly { + r := mload(add(_signature, 0x20)) + s := mload(add(_signature, 0x40)) + v := and(mload(add(_signature, 0x41)), 0xff) + } + require(v == 27 || v == 28, "v is neither 27 nor 28"); + + // EIP-2 still allows signature malleability for ecrecover(). Remove this possibility and make the signature + // unique. Appendix F in the Ethereum Yellow paper (https://ethereum.github.io/yellowpaper/paper.pdf), defines + // the valid range for s in (301): 0 < s < secp256k1n ÷ 2 + 1, and for v in (302): v ∈ {27, 28}. Most + // signatures from current libraries generate a unique signature with an s-value in the lower half order. + // + // If your library generates malleable signatures, such as s-values in the upper range, calculate a new s-value + // with 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 - s1 and flip v from 27 to 28 or + // vice versa. If your library also generates signatures with 0/1 for v instead 27/28, add 27 to v to accept + // these malleable signatures as well. + require(uint256(s) <= 0x7FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF5D576E7357A4501DDFE92F46681B20A0, "Invalid s"); + + address recoveredAddress = ecrecover(_hash, v, r, s); + + return recoveredAddress == address(this) && recoveredAddress != address(0); + } + + /// @notice Method for paying the bootloader for the transaction. + /// @param _transaction The transaction for which the fee is paid. + /// @dev It also accepts unused _txHash and _suggestedSignedHash parameters: + /// the unique (canonical) hash of the transaction and the suggested signed + /// hash of the transaction. + function payForTransaction( + bytes32, // _txHash + bytes32, // _suggestedSignedHash + Transaction calldata _transaction + ) external payable ignoreNonBootloader ignoreInDelegateCall { + bool success = _transaction.payToTheBootloader(); + require(success, "Failed to pay the fee to the operator"); + } + + /// @notice Method, where the user should prepare for the transaction to be + /// paid for by a paymaster. + /// @dev Here, the account should set the allowance for the smart contracts + /// @param _transaction The transaction. + /// @dev It also accepts unused _txHash and _suggestedSignedHash parameters: + /// the unique (canonical) hash of the transaction and the suggested signed + /// hash of the transaction. + function prepareForPaymaster( + bytes32, // _txHash + bytes32, // _suggestedSignedHash + Transaction calldata _transaction + ) external payable ignoreNonBootloader ignoreInDelegateCall { + _transaction.processPaymasterInput(); + } + + fallback() external payable ignoreInDelegateCall { + // fallback of default account shouldn't be called by bootloader under no circumstances + assert(msg.sender != BOOTLOADER_FORMAL_ADDRESS); + + // If the contract is called directly, behave like an EOA + } + + receive() external payable { + // If the contract is called directly, behave like an EOA + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/DefaultAccountNoSecurity.sol b/.test-node-subtree/etc/system-contracts/contracts/DefaultAccountNoSecurity.sol new file mode 100644 index 00000000..cb686996 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/DefaultAccountNoSecurity.sol @@ -0,0 +1,255 @@ +// SPDX-License-Identifier: MIT + +// TEST ONLY CODE +// DO NOT USE IN PRODUCTION +// ONLY FOR Hardhat / Forge testing. +pragma solidity ^0.8.0; + +import "./interfaces/IAccount.sol"; +import "./libraries/TransactionHelper.sol"; +import "./libraries/SystemContractHelper.sol"; +import "./libraries/EfficientCall.sol"; +import {BOOTLOADER_FORMAL_ADDRESS, NONCE_HOLDER_SYSTEM_CONTRACT, DEPLOYER_SYSTEM_CONTRACT, INonceHolder} from "./Constants.sol"; + +/** + * @author Matter Labs + * @notice Account implementation for TESTS ONLY + * @dev The bytecode of the contract is set by default for all addresses for which no other bytecodes are deployed. + * @notice If the caller is not a bootloader always returns empty data on call, just like EOA does. + * @notice If it is delegate called always returns empty data, just like EOA does. + * @notice This account implementation returns the transaction result. + */ +contract DefaultAccountNoSecurity is IAccount { + using TransactionHelper for *; + + /** + * @dev Simulate the behavior of the EOA if the caller is not the bootloader. + * Essentially, for all non-bootloader callers halt the execution with empty return data. + * If all functions will use this modifier AND the contract will implement an empty payable fallback() + * then the contract will be indistinguishable from the EOA when called. + */ + modifier ignoreNonBootloader() { + if (msg.sender != BOOTLOADER_FORMAL_ADDRESS) { + // If function was called outside of the bootloader, behave like an EOA. + assembly { + return(0, 0) + } + } + // Continue execution if called from the bootloader. + _; + } + + /** + * @dev Simulate the behavior of the EOA if it is called via `delegatecall`. + * Thus, the default account on a delegate call behaves the same as EOA on Ethereum. + * If all functions will use this modifier AND the contract will implement an empty payable fallback() + * then the contract will be indistinguishable from the EOA when called. + */ + modifier ignoreInDelegateCall() { + address codeAddress = SystemContractHelper.getCodeAddress(); + if (codeAddress != address(this)) { + // If the function was delegate called, behave like an EOA. + assembly { + return(0, 0) + } + } + + // Continue execution if not delegate called. + _; + } + + /// @notice Validates the transaction & increments nonce. + /// @dev The transaction is considered accepted by the account if + /// the call to this function by the bootloader does not revert + /// and the nonce has been set as used. + /// @param _suggestedSignedHash The suggested hash of the transaction to be signed by the user. + /// This is the hash that is signed by the EOA by default. + /// @param _transaction The transaction structure itself. + /// @dev Besides the params above, it also accepts unused first paramter "_txHash", which + /// is the unique (canonical) hash of the transaction. + function validateTransaction( + bytes32, // _txHash + bytes32 _suggestedSignedHash, + Transaction calldata _transaction + ) + external + payable + override + ignoreNonBootloader + ignoreInDelegateCall + returns (bytes4 magic) + { + magic = _validateTransaction(_suggestedSignedHash, _transaction); + } + + /// @notice Inner method for validating transaction and increasing the nonce + /// @param _suggestedSignedHash The hash of the transaction signed by the EOA + /// @param _transaction The transaction. + function _validateTransaction( + bytes32 _suggestedSignedHash, + Transaction calldata _transaction + ) internal returns (bytes4 magic) { + // Note, that nonce holder can only be called with "isSystem" flag. + SystemContractsCaller.systemCallWithPropagatedRevert( + uint32(gasleft()), + address(NONCE_HOLDER_SYSTEM_CONTRACT), + 0, + abi.encodeCall( + INonceHolder.incrementMinNonceIfEquals, + (_transaction.nonce) + ) + ); + + // Even though for the transaction types present in the system right now, + // we always provide the suggested signed hash, this should not be + // always expected. In case the bootloader has no clue what the default hash + // is, the bytes32(0) will be supplied. + bytes32 txHash = _suggestedSignedHash != bytes32(0) + ? _suggestedSignedHash + : _transaction.encodeHash(); + + // The fact there is enough balance for the account + // should be checked explicitly to prevent user paying for fee for a + // transaction that wouldn't be included on Ethereum. + uint256 totalRequiredBalance = _transaction.totalRequiredBalance(); + require( + totalRequiredBalance <= address(this).balance, + "Not enough balance for fee + value" + ); + + if (_isValidSignature(txHash, _transaction.signature)) { + magic = ACCOUNT_VALIDATION_SUCCESS_MAGIC; + } else { + magic = bytes4(0); + } + } + + /// @notice Method called by the bootloader to execute the transaction. + /// @param _transaction The transaction to execute. + /// @dev It also accepts unused _txHash and _suggestedSignedHash parameters: + /// the unique (canonical) hash of the transaction and the suggested signed + /// hash of the transaction. + function executeTransaction( + bytes32, // _txHash + bytes32, // _suggestedSignedHash + Transaction calldata _transaction + ) + external + payable + override + ignoreNonBootloader + ignoreInDelegateCall + returns (bytes memory returnData) + { + returnData = _execute(_transaction); + } + + /// @notice Method that should be used to initiate a transaction from this account by an external call. + /// @dev The custom account is supposed to implement this method to initiate a transaction on behalf + /// of the account via L1 -> L2 communication. However, the default account can initiate a transaction + /// from L1, so we formally implement the interface method, but it doesn't execute any logic. + /// @param _transaction The transaction to execute. + function executeTransactionFromOutside( + Transaction calldata _transaction + ) external payable override { + // Behave the same as for fallback/receive, just execute nothing, returns nothing + } + + /// @notice Inner method for executing a transaction. + /// @param _transaction The transaction to execute. + /// @return returnData The result bytes, if execution succeeds. + function _execute( + Transaction calldata _transaction + ) + internal + returns ( + /// + /// DEBUG SUPPORT START + /// + bytes memory returnData + ) + { + /// + /// DEBUG SUPPORT END + /// + address to = address(uint160(_transaction.to)); + uint128 value = Utils.safeCastToU128(_transaction.value); + bytes calldata data = _transaction.data; + uint32 gas = Utils.safeCastToU32(gasleft()); + + // Note, that the deployment method from the deployer contract can only be called with a "systemCall" flag. + bool isSystemCall; + if (to == address(DEPLOYER_SYSTEM_CONTRACT) && data.length >= 4) { + bytes4 selector = bytes4(data[:4]); + // Check that called function is the deployment method, + // the others deployer method is not supposed to be called from the default account. + isSystemCall = + selector == DEPLOYER_SYSTEM_CONTRACT.create.selector || + selector == DEPLOYER_SYSTEM_CONTRACT.create2.selector || + selector == DEPLOYER_SYSTEM_CONTRACT.createAccount.selector || + selector == DEPLOYER_SYSTEM_CONTRACT.create2Account.selector; + } + + /// + /// DEBUG SUPPORT START + /// + returnData = EfficientCall.call(gas, to, value, data, isSystemCall); + /// + /// DEBUG SUPPORT END + /// + } + + /// @notice TEST ONLY CODE - No validation is happening ! + /// @param _hash The hash of the transaction to be signed. + /// @param _signature The signature of the transaction. + /// @return EIP1271_SUCCESS_RETURN_VALUE Always - as this is TEST only code.. + function _isValidSignature( + bytes32 _hash, + bytes memory _signature + ) internal view returns (bool) { + // WARNING - THIS IS TEST ONLY CODE + // IT ACCEPTS ANY SIGNATURE AS A 'VALID' one. + // SHOULD BE USED ONLY FOR TESTING. + return true; + } + + /// @notice Method for paying the bootloader for the transaction. + /// @param _transaction The transaction for which the fee is paid. + /// @dev It also accepts unused _txHash and _suggestedSignedHash parameters: + /// the unique (canonical) hash of the transaction and the suggested signed + /// hash of the transaction. + function payForTransaction( + bytes32, // _txHash + bytes32, // _suggestedSignedHash + Transaction calldata _transaction + ) external payable ignoreNonBootloader ignoreInDelegateCall { + bool success = _transaction.payToTheBootloader(); + require(success, "Failed to pay the fee to the operator"); + } + + /// @notice Method, where the user should prepare for the transaction to be + /// paid for by a paymaster. + /// @dev Here, the account should set the allowance for the smart contracts + /// @param _transaction The transaction. + /// @dev It also accepts unused _txHash and _suggestedSignedHash parameters: + /// the unique (canonical) hash of the transaction and the suggested signed + /// hash of the transaction. + function prepareForPaymaster( + bytes32, // _txHash + bytes32, // _suggestedSignedHash + Transaction calldata _transaction + ) external payable ignoreNonBootloader ignoreInDelegateCall { + _transaction.processPaymasterInput(); + } + + fallback() external payable { + // fallback of default account shouldn't be called by bootloader under no circumstances + assert(msg.sender != BOOTLOADER_FORMAL_ADDRESS); + + // If the contract is called directly, behave like an EOA + } + + receive() external payable { + // If the contract is called directly, behave like an EOA + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/EmptyContract.sol b/.test-node-subtree/etc/system-contracts/contracts/EmptyContract.sol new file mode 100644 index 00000000..f0304beb --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/EmptyContract.sol @@ -0,0 +1,15 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice The "empty" contract that is put into some system contracts by default. + * @dev The bytecode of the contract is set by default for all addresses for which no other bytecodes are deployed. + */ +contract EmptyContract { + fallback() external payable {} + + receive() external payable {} +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/EventWriter.yul b/.test-node-subtree/etc/system-contracts/contracts/EventWriter.yul new file mode 100644 index 00000000..4cd4a381 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/EventWriter.yul @@ -0,0 +1,170 @@ +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice The contract responsible for decoding and writing events using low-level instructions. + * @dev The metadata and topics are passed via registers, and the first accessible register contains their number. + * The rest of the data is passed via calldata without copying. + */ +object "EventWriter" { + code { + return(0, 0) + } + object "EventWriter_deployed" { + code { + //////////////////////////////////////////////////////////////// + // HELPER FUNCTIONS + //////////////////////////////////////////////////////////////// + + // For the documentation of the helper functions, please refer to + // the corresponding functions in the SystemContractHelper.sol. + + /// @notice Returns the 0-th extraAbiParam for the current call. + /// @dev It is equal to the value of the 2-th register at the start of the call. + function getExtraAbiData_0() -> extraAbiData { + extraAbiData := verbatim_0i_1o("get_global::extra_abi_data_0") + } + + /// @notice Returns the 1-th extraAbiParam for the current call. + /// @dev It is equal to the value of the 3-th register at the start of the call. + function getExtraAbiData_1() -> extraAbiData { + extraAbiData := verbatim_0i_1o("get_global::extra_abi_data_1") + } + + /// @notice Returns the 2-th extraAbiParam for the current call. + /// @dev It is equal to the value of the 4-th register at the start of the call. + function getExtraAbiData_2() -> extraAbiData { + extraAbiData := verbatim_0i_1o("get_global::extra_abi_data_2") + } + + /// @notice Returns the 3-th extraAbiParam for the current call. + /// @dev It is equal to the value of the 5-th register at the start of the call. + function getExtraAbiData_3() -> extraAbiData { + extraAbiData := verbatim_0i_1o("get_global::extra_abi_data_3") + } + + /// @notice Returns the 4-th extraAbiParam for the current call. + /// @dev It is equal to the value of the 6-th register at the start of the call. + function getExtraAbiData_4() -> extraAbiData { + extraAbiData := verbatim_0i_1o("get_global::extra_abi_data_4") + } + + /// @notice Returns the call flags for the current call. + /// @dev Call flags is the value of the first register at the start of the call. + /// @dev The zero bit of the callFlags indicates whether the call is + /// a constructor call. The first bit of the callFlags indicates whether + /// the call is a system one. + function getCallFlags() -> ret { + ret := verbatim_0i_1o("get_global::call_flags") + } + + /// @notice Initialize a new event + /// @param initializer The event initializing value + /// @param value1 The first topic or data chunk. + function eventInitialize(initializer, value1) { + verbatim_2i_0o("event_initialize", initializer, value1) + } + + /// @notice Continue writing the previously initialized event. + /// @param value1 The first topic or data chunk. + /// @param value2 The second topic or data chunk. + function eventWrite(value1, value2) { + verbatim_2i_0o("event_write", value1, value2) + } + + // @dev Write 1-th topic and first data chunk + function writeFirstTopicWithDataChunk() { + let topic1 := getExtraAbiData_1() + let dataChunk := calldataload(0) + eventWrite(topic1, dataChunk) + } + + // @dev Write 1-th and 2-th event topics + function writeFirstTwoTopics() { + let topic1 := getExtraAbiData_1() + let topic2 := getExtraAbiData_2() + eventWrite(topic1, topic2) + } + + // @dev Write 3-th topic and first data chunk + function writeThirdTopicWithDataChunk() { + let topic3 := getExtraAbiData_3() + let dataChunk := calldataload(0) + eventWrite(topic3, dataChunk) + } + + // @dev Write 3-th and 4-th event topics + function writeSecondTwoTopics() { + let topic3 := getExtraAbiData_3() + let topic4 := getExtraAbiData_4() + eventWrite(topic3, topic4) + } + + // @dev Reverts the call if a caller hasn't set the "isSystem" flag before calling + // Note: this method is different from the `onlySystemCall` modifier that is used in system contracts. + function onlySystemCall() { + let callFlags := getCallFlags() + let isSystemCall := and(callFlags, 2) + + if iszero(isSystemCall) { + revert(0, 0) + } + } + + //////////////////////////////////////////////////////////////// + // FALLBACK + //////////////////////////////////////////////////////////////// + + // Ensure that contract is called on purpose + onlySystemCall() + + let numberOfTopics := getExtraAbiData_0() + // Only 4 indexed fields are allowed, same as on EVM + if gt(numberOfTopics, 4) { + revert(0, 0) + } + + let dataLength := calldatasize() + // Increment number of topics to include the `msg.sender` as a topic + let initializer := add(shl(32, dataLength), add(numberOfTopics, 1)) + eventInitialize(initializer, caller()) + + // Save the pointer to written data + let dataCursor + + // Handle every case separately, to save gas on loops (alternative approach) + switch numberOfTopics + case 0 { + // Nothing to publish + } + case 1 { + writeFirstTopicWithDataChunk() + dataCursor := add(dataCursor, 0x20) + } + case 2 { + writeFirstTwoTopics() + } + case 3 { + writeFirstTwoTopics() + writeThirdTopicWithDataChunk() + dataCursor := add(dataCursor, 0x20) + } + case 4 { + writeFirstTwoTopics() + writeSecondTwoTopics() + } + default { + // Unreachable + revert(0, 0) + } + + // Write all the event data, two words at a time + for {} lt(dataCursor, dataLength) { + dataCursor := add(dataCursor, 0x40) + } { + let chunk1 := calldataload(dataCursor) + let chunk2 := calldataload(add(dataCursor, 0x20)) + eventWrite(chunk1, chunk2) + } + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/ImmutableSimulator.sol b/.test-node-subtree/etc/system-contracts/contracts/ImmutableSimulator.sol new file mode 100644 index 00000000..a018c92a --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/ImmutableSimulator.sol @@ -0,0 +1,45 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "./interfaces/IImmutableSimulator.sol"; +import {DEPLOYER_SYSTEM_CONTRACT} from "./Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice System smart contract that simulates the behavior of immutable variables in Solidity. + * @dev The contract stores the immutable variables created during deployment by other contracts on his storage. + * @dev This simulator is needed so that smart contracts with the same Solidity code but different + * constructor parameters have the same bytecode. + * @dev The users are not expected to call this contract directly, only indirectly via the compiler simulations + * for the immutable variables in Solidity. + */ +contract ImmutableSimulator is IImmutableSimulator { + /// @dev mapping (contract address) => (index of immutable variable) => value + /// @notice that address uses `uint256` type to leave the option to introduce 32-byte address space in future. + mapping(uint256 => mapping(uint256 => bytes32)) internal immutableDataStorage; + + /// @notice Method that returns the immutable with a certain index for a user. + /// @param _dest The address which the immutable belongs to. + /// @param _index The index of the immutable. + /// @return The value of the immutables. + function getImmutable(address _dest, uint256 _index) external view override returns (bytes32) { + return immutableDataStorage[uint256(uint160(_dest))][_index]; + } + + /// @notice Method used by the contract deployer to store the immutables for an account + /// @param _dest The address which to store the immutables for. + /// @param _immutables The list of the immutables. + function setImmutables(address _dest, ImmutableData[] calldata _immutables) external override { + require(msg.sender == address(DEPLOYER_SYSTEM_CONTRACT), "Callable only by the deployer system contract"); + unchecked { + uint256 immutablesLength = _immutables.length; + for (uint256 i = 0; i < immutablesLength; ++i) { + uint256 index = _immutables[i].index; + bytes32 value = _immutables[i].value; + immutableDataStorage[uint256(uint160(_dest))][index] = value; + } + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/KnownCodesStorage.sol b/.test-node-subtree/etc/system-contracts/contracts/KnownCodesStorage.sol new file mode 100644 index 00000000..2dda7854 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/KnownCodesStorage.sol @@ -0,0 +1,81 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {IKnownCodesStorage} from "./interfaces/IKnownCodesStorage.sol"; +import {ISystemContract} from "./interfaces/ISystemContract.sol"; +import {Utils} from "./libraries/Utils.sol"; +import {SystemContractHelper} from "./libraries/SystemContractHelper.sol"; +import {COMPRESSOR_CONTRACT, L1_MESSENGER_CONTRACT} from "./Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice The storage of this contract will basically serve as a mapping for the known code hashes. + * @dev Code hash is not strictly a hash, it's a structure where the first byte denotes the version of the hash, + * the second byte denotes whether the contract is constructed, and the next two bytes denote the length in 32-byte words. + * words. And then the next 28 bytes is the truncated hash. + */ +contract KnownCodesStorage is IKnownCodesStorage, ISystemContract { + modifier onlyCompressor() { + require(msg.sender == address(COMPRESSOR_CONTRACT), "Callable only by the compressor"); + _; + } + + /// @notice The method that is used by the bootloader to mark several bytecode hashes as known. + /// @param _shouldSendToL1 Whether the bytecode should be sent on L1. + /// @param _hashes Hashes of the bytecodes to be marked as known. + function markFactoryDeps(bool _shouldSendToL1, bytes32[] calldata _hashes) external onlyCallFromBootloader { + unchecked { + uint256 hashesLen = _hashes.length; + for (uint256 i = 0; i < hashesLen; ++i) { + _markBytecodeAsPublished(_hashes[i], _shouldSendToL1); + } + } + } + + /// @notice The method used to mark a single bytecode hash as known. + /// @dev Only trusted contacts can call this method, currently only the bytecode compressor. + /// @param _bytecodeHash The hash of the bytecode that is marked as known. + function markBytecodeAsPublished(bytes32 _bytecodeHash) external onlyCompressor { + _markBytecodeAsPublished(_bytecodeHash, false); + } + + /// @notice The method used to mark a single bytecode hash as known + /// @param _bytecodeHash The hash of the bytecode that is marked as known + /// @param _shouldSendToL1 Whether the bytecode should be sent on L1 + function _markBytecodeAsPublished(bytes32 _bytecodeHash, bool _shouldSendToL1) internal { + if (getMarker(_bytecodeHash) == 0) { + _validateBytecode(_bytecodeHash); + + if (_shouldSendToL1) { + L1_MESSENGER_CONTRACT.requestBytecodeL1Publication(_bytecodeHash); + } + + // Save as known, to not resend the log to L1 + assembly { + sstore(_bytecodeHash, 1) + } + + emit MarkedAsKnown(_bytecodeHash, _shouldSendToL1); + } + } + + /// @notice Returns the marker stored for a bytecode hash. 1 means that the bytecode hash is known + /// and can be used for deploying contracts. 0 otherwise. + function getMarker(bytes32 _hash) public view override returns (uint256 marker) { + assembly { + marker := sload(_hash) + } + } + + /// @notice Validates the format of bytecodehash + /// @dev zk-circuit accepts & handles only valid format of bytecode hash, other input has undefined behavior + /// That's why we need to validate it + function _validateBytecode(bytes32 _bytecodeHash) internal pure { + uint8 version = uint8(_bytecodeHash[0]); + require(version == 1 && _bytecodeHash[1] == bytes1(0), "Incorrectly formatted bytecodeHash"); + + require(Utils.bytecodeLenInWords(_bytecodeHash) % 2 == 1, "Code length in words must be odd"); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/L1Messenger.sol b/.test-node-subtree/etc/system-contracts/contracts/L1Messenger.sol new file mode 100644 index 00000000..47ee3265 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/L1Messenger.sol @@ -0,0 +1,331 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {IL1Messenger, L2ToL1Log, L2_L1_LOGS_TREE_DEFAULT_LEAF_HASH, L2_TO_L1_LOG_SERIALIZE_SIZE, STATE_DIFF_COMPRESSION_VERSION_NUMBER} from "./interfaces/IL1Messenger.sol"; +import {ISystemContract} from "./interfaces/ISystemContract.sol"; +import {SystemContractHelper} from "./libraries/SystemContractHelper.sol"; +import {EfficientCall} from "./libraries/EfficientCall.sol"; +import {Utils} from "./libraries/Utils.sol"; +import {SystemLogKey, SYSTEM_CONTEXT_CONTRACT, KNOWN_CODE_STORAGE_CONTRACT, COMPRESSOR_CONTRACT, STATE_DIFF_ENTRY_SIZE, MAX_ALLOWED_PUBDATA_PER_BATCH, L2_TO_L1_LOGS_MERKLE_TREE_LEAVES} from "./Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice Smart contract for sending arbitrary length messages to L1 + * @dev by default ZkSync can send fixed length messages on L1. + * A fixed length message has 4 parameters `senderAddress` `isService`, `key`, `value`, + * the first one is taken from the context, the other three are chosen by the sender. + * @dev To send a variable length message we use this trick: + * - This system contract accepts a arbitrary length message and sends a fixed length message with + * parameters `senderAddress == this`, `marker == true`, `key == msg.sender`, `value == keccak256(message)`. + * - The contract on L1 accepts all sent messages and if the message came from this system contract + * it requires that the preimage of `value` be provided. + */ +contract L1Messenger is IL1Messenger, ISystemContract { + /// @notice Sequential hash of logs sent in the current block. + /// @dev Will be reset at the end of the block to zero value. + bytes32 internal chainedLogsHash; + + /// @notice Number of logs sent in the current block. + /// @dev Will be reset at the end of the block to zero value. + uint256 internal numberOfLogsToProcess; + + /// @notice Sequential hash of hashes of the messages sent in the current block. + /// @dev Will be reset at the end of the block to zero value. + bytes32 internal chainedMessagesHash; + + /// @notice Sequential hash of bytecode hashes that needs to published + /// according to the current block execution invariant. + /// @dev Will be reset at the end of the block to zero value. + bytes32 internal chainedL1BytecodesRevealDataHash; + + /// The gas cost of processing one keccak256 round. + uint256 internal constant KECCAK_ROUND_GAS_COST = 40; + + /// The number of bytes processed in one keccak256 round. + uint256 internal constant KECCAK_ROUND_NUMBER_OF_BYTES = 136; + + /// The gas cost of calculation of keccak256 of bytes array of such length. + function keccakGasCost(uint256 _length) internal pure returns (uint256) { + return KECCAK_ROUND_GAS_COST * (_length / KECCAK_ROUND_NUMBER_OF_BYTES + 1); + } + + /// The gas cost of processing one sha256 round. + uint256 internal constant SHA256_ROUND_GAS_COST = 7; + + /// The number of bytes processed in one sha256 round. + uint256 internal constant SHA256_ROUND_NUMBER_OF_BYTES = 64; + + /// The gas cost of calculation of sha256 of bytes array of such length. + function sha256GasCost(uint256 _length) internal pure returns (uint256) { + return SHA256_ROUND_GAS_COST * ((_length + 8) / SHA256_ROUND_NUMBER_OF_BYTES + 1); + } + + /// @notice Sends L2ToL1Log. + /// @dev Can be called only by a system contract. + function sendL2ToL1Log( + bool _isService, + bytes32 _key, + bytes32 _value + ) external onlyCallFromSystemContract returns (uint256 logIdInMerkleTree) { + L2ToL1Log memory l2ToL1Log = L2ToL1Log({ + l2ShardId: 0, + isService: _isService, + txNumberInBlock: SYSTEM_CONTEXT_CONTRACT.txNumberInBlock(), + sender: msg.sender, + key: _key, + value: _value + }); + logIdInMerkleTree = _processL2ToL1Log(l2ToL1Log); + + // We need to charge cost of hashing, as it will be used in `publishPubdataAndClearState`: + // - keccakGasCost(L2_TO_L1_LOG_SERIALIZE_SIZE) and keccakGasCost(64) when reconstructing L2ToL1Log + // - at most 1 time keccakGasCost(64) when building the Merkle tree (as merkle tree can contain + // ~2*N nodes, where the first N nodes are leaves the hash of which is calculated on the previous step). + uint256 gasToPay = keccakGasCost(L2_TO_L1_LOG_SERIALIZE_SIZE) + 2 * keccakGasCost(64); + SystemContractHelper.burnGas(Utils.safeCastToU32(gasToPay)); + } + + /// @notice Internal function to send L2ToL1Log. + function _processL2ToL1Log(L2ToL1Log memory _l2ToL1Log) internal returns (uint256 logIdInMerkleTree) { + bytes32 hashedLog = keccak256( + abi.encodePacked( + _l2ToL1Log.l2ShardId, + _l2ToL1Log.isService, + _l2ToL1Log.txNumberInBlock, + _l2ToL1Log.sender, + _l2ToL1Log.key, + _l2ToL1Log.value + ) + ); + + chainedLogsHash = keccak256(abi.encode(chainedLogsHash, hashedLog)); + + logIdInMerkleTree = numberOfLogsToProcess; + numberOfLogsToProcess++; + + emit L2ToL1LogSent(_l2ToL1Log); + } + + /// @notice Public functionality to send messages to L1. + function sendToL1(bytes calldata _message) external override returns (bytes32 hash) { + uint256 gasBeforeMessageHashing = gasleft(); + hash = EfficientCall.keccak(_message); + uint256 gasSpentOnMessageHashing = gasBeforeMessageHashing - gasleft(); + + /// Store message record + chainedMessagesHash = keccak256(abi.encode(chainedMessagesHash, hash)); + + /// Store log record + L2ToL1Log memory l2ToL1Log = L2ToL1Log({ + l2ShardId: 0, + isService: true, + txNumberInBlock: SYSTEM_CONTEXT_CONTRACT.txNumberInBlock(), + sender: address(this), + key: bytes32(uint256(uint160(msg.sender))), + value: hash + }); + _processL2ToL1Log(l2ToL1Log); + + // Get cost of one byte pubdata in gas from context. + uint256 meta = SystemContractHelper.getZkSyncMetaBytes(); + uint32 gasPerPubdataBytes = SystemContractHelper.getGasPerPubdataByteFromMeta(meta); + + uint256 pubdataLen; + unchecked { + // 4 bytes used to encode the length of the message (see `publishPubdataAndClearState`) + // L2_TO_L1_LOG_SERIALIZE_SIZE bytes used to encode L2ToL1Log + pubdataLen = 4 + _message.length + L2_TO_L1_LOG_SERIALIZE_SIZE; + } + + // We need to charge cost of hashing, as it will be used in `publishPubdataAndClearState`: + // - keccakGasCost(L2_TO_L1_LOG_SERIALIZE_SIZE) and keccakGasCost(64) when reconstructing L2ToL1Log + // - keccakGasCost(64) and gasSpentOnMessageHashing when reconstructing Messages + // - at most 1 time keccakGasCost(64) when building the Merkle tree (as merkle tree can contain + // ~2*N nodes, where the first N nodes are leaves the hash of which is calculated on the previous step). + uint256 gasToPay = pubdataLen * + gasPerPubdataBytes + + keccakGasCost(L2_TO_L1_LOG_SERIALIZE_SIZE) + + 3 * + keccakGasCost(64) + + gasSpentOnMessageHashing; + SystemContractHelper.burnGas(Utils.safeCastToU32(gasToPay)); + + emit L1MessageSent(msg.sender, hash, _message); + } + + /// @dev Can be called only by KnownCodesStorage system contract. + function requestBytecodeL1Publication( + bytes32 _bytecodeHash + ) external override onlyCallFrom(address(KNOWN_CODE_STORAGE_CONTRACT)) { + chainedL1BytecodesRevealDataHash = keccak256(abi.encode(chainedL1BytecodesRevealDataHash, _bytecodeHash)); + + uint256 bytecodeLen = Utils.bytecodeLenInBytes(_bytecodeHash); + + // Get cost of one byte pubdata in gas from context. + uint256 meta = SystemContractHelper.getZkSyncMetaBytes(); + uint32 gasPerPubdataBytes = SystemContractHelper.getGasPerPubdataByteFromMeta(meta); + + uint256 pubdataLen; + unchecked { + // 4 bytes used to encode the length of the bytecode (see `publishPubdataAndClearState`) + pubdataLen = 4 + bytecodeLen; + } + + // We need to charge cost of hashing, as it will be used in `publishPubdataAndClearState` + uint256 gasToPay = pubdataLen * gasPerPubdataBytes + sha256GasCost(bytecodeLen) + keccakGasCost(64); + SystemContractHelper.burnGas(Utils.safeCastToU32(gasToPay)); + + emit BytecodeL1PublicationRequested(_bytecodeHash); + } + + /// @notice Verifies that the {_totalL2ToL1PubdataAndStateDiffs} reflects what occurred within the L1Batch and that + /// the compressed statediffs are equivalent to the full state diffs. + /// @param _totalL2ToL1PubdataAndStateDiffs The total pubdata and uncompressed state diffs of transactions that were + /// processed in the current L1 Batch. Pubdata consists of L2 to L1 Logs, messages, deployed bytecode, and state diffs. + /// @dev Function that should be called exactly once per L1 Batch by the bootloader. + /// @dev Checks that totalL2ToL1Pubdata is strictly packed data that should to be published to L1. + /// @dev The data passed in also contains the encoded state diffs to be checked again, however this is aux data that is not + /// part of the committed pubdata. + /// @dev Performs calculation of L2ToL1Logs merkle tree root, "sends" such root and keccak256(totalL2ToL1Pubdata) + /// to L1 using low-level (VM) L2Log. + function publishPubdataAndClearState( + bytes calldata _totalL2ToL1PubdataAndStateDiffs + ) external onlyCallFromBootloader { + uint256 calldataPtr = 0; + + /// Check logs + uint32 numberOfL2ToL1Logs = uint32(bytes4(_totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + 4])); + require(numberOfL2ToL1Logs <= L2_TO_L1_LOGS_MERKLE_TREE_LEAVES, "Too many L2->L1 logs"); + calldataPtr += 4; + + bytes32[] memory l2ToL1LogsTreeArray = new bytes32[](L2_TO_L1_LOGS_MERKLE_TREE_LEAVES); + bytes32 reconstructedChainedLogsHash; + for (uint256 i = 0; i < numberOfL2ToL1Logs; ++i) { + bytes32 hashedLog = EfficientCall.keccak( + _totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + L2_TO_L1_LOG_SERIALIZE_SIZE] + ); + calldataPtr += L2_TO_L1_LOG_SERIALIZE_SIZE; + l2ToL1LogsTreeArray[i] = hashedLog; + reconstructedChainedLogsHash = keccak256(abi.encode(reconstructedChainedLogsHash, hashedLog)); + } + require( + reconstructedChainedLogsHash == chainedLogsHash, + "reconstructedChainedLogsHash is not equal to chainedLogsHash" + ); + for (uint256 i = numberOfL2ToL1Logs; i < L2_TO_L1_LOGS_MERKLE_TREE_LEAVES; ++i) { + l2ToL1LogsTreeArray[i] = L2_L1_LOGS_TREE_DEFAULT_LEAF_HASH; + } + uint256 nodesOnCurrentLevel = L2_TO_L1_LOGS_MERKLE_TREE_LEAVES; + while (nodesOnCurrentLevel > 1) { + nodesOnCurrentLevel /= 2; + for (uint256 i = 0; i < nodesOnCurrentLevel; ++i) { + l2ToL1LogsTreeArray[i] = keccak256( + abi.encode(l2ToL1LogsTreeArray[2 * i], l2ToL1LogsTreeArray[2 * i + 1]) + ); + } + } + bytes32 l2ToL1LogsTreeRoot = l2ToL1LogsTreeArray[0]; + + /// Check messages + uint32 numberOfMessages = uint32(bytes4(_totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + 4])); + calldataPtr += 4; + bytes32 reconstructedChainedMessagesHash; + for (uint256 i = 0; i < numberOfMessages; ++i) { + uint32 currentMessageLength = uint32(bytes4(_totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + 4])); + calldataPtr += 4; + bytes32 hashedMessage = EfficientCall.keccak( + _totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + currentMessageLength] + ); + calldataPtr += currentMessageLength; + reconstructedChainedMessagesHash = keccak256(abi.encode(reconstructedChainedMessagesHash, hashedMessage)); + } + require( + reconstructedChainedMessagesHash == chainedMessagesHash, + "reconstructedChainedMessagesHash is not equal to chainedMessagesHash" + ); + + /// Check bytecodes + uint32 numberOfBytecodes = uint32(bytes4(_totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + 4])); + calldataPtr += 4; + bytes32 reconstructedChainedL1BytecodesRevealDataHash; + for (uint256 i = 0; i < numberOfBytecodes; ++i) { + uint32 currentBytecodeLength = uint32( + bytes4(_totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + 4]) + ); + calldataPtr += 4; + reconstructedChainedL1BytecodesRevealDataHash = keccak256( + abi.encode( + reconstructedChainedL1BytecodesRevealDataHash, + Utils.hashL2Bytecode( + _totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + currentBytecodeLength] + ) + ) + ); + calldataPtr += currentBytecodeLength; + } + require( + reconstructedChainedL1BytecodesRevealDataHash == chainedL1BytecodesRevealDataHash, + "reconstructedChainedL1BytecodesRevealDataHash is not equal to chainedL1BytecodesRevealDataHash" + ); + + /// Check State Diffs + /// encoding is as follows: + /// header (1 byte version, 3 bytes total len of compressed, 1 byte enumeration index size, 2 bytes number of initial writes) + /// body (N bytes of initial writes [32 byte derived key || compressed value], M bytes repeated writes [enumeration index || compressed value]) + /// encoded state diffs: [20bytes address][32bytes key][32bytes derived key][8bytes enum index][32bytes initial value][32bytes final value] + require( + uint256(uint8(bytes1(_totalL2ToL1PubdataAndStateDiffs[calldataPtr]))) == + STATE_DIFF_COMPRESSION_VERSION_NUMBER, + "state diff compression version mismatch" + ); + calldataPtr++; + + uint24 compressedStateDiffSize = uint24(bytes3(_totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + 3])); + calldataPtr += 3; + + uint8 enumerationIndexSize = uint8(bytes1(_totalL2ToL1PubdataAndStateDiffs[calldataPtr])); + calldataPtr++; + + bytes calldata compressedStateDiffs = _totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + + compressedStateDiffSize]; + calldataPtr += compressedStateDiffSize; + + bytes calldata totalL2ToL1Pubdata = _totalL2ToL1PubdataAndStateDiffs[:calldataPtr]; + + require(calldataPtr <= MAX_ALLOWED_PUBDATA_PER_BATCH, "L1 Messenger pubdata is too long"); + + uint32 numberOfStateDiffs = uint32(bytes4(_totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + 4])); + calldataPtr += 4; + + bytes calldata stateDiffs = _totalL2ToL1PubdataAndStateDiffs[calldataPtr:calldataPtr + + (numberOfStateDiffs * STATE_DIFF_ENTRY_SIZE)]; + calldataPtr += numberOfStateDiffs * STATE_DIFF_ENTRY_SIZE; + + bytes32 stateDiffHash = COMPRESSOR_CONTRACT.verifyCompressedStateDiffs( + numberOfStateDiffs, + enumerationIndexSize, + stateDiffs, + compressedStateDiffs + ); + + /// Check for calldata strict format + require(calldataPtr == _totalL2ToL1PubdataAndStateDiffs.length, "Extra data in the totalL2ToL1Pubdata array"); + + /// Native (VM) L2 to L1 log + SystemContractHelper.toL1(true, bytes32(uint256(SystemLogKey.L2_TO_L1_LOGS_TREE_ROOT_KEY)), l2ToL1LogsTreeRoot); + SystemContractHelper.toL1( + true, + bytes32(uint256(SystemLogKey.TOTAL_L2_TO_L1_PUBDATA_KEY)), + EfficientCall.keccak(totalL2ToL1Pubdata) + ); + SystemContractHelper.toL1(true, bytes32(uint256(SystemLogKey.STATE_DIFF_HASH_KEY)), stateDiffHash); + + /// Clear logs state + chainedLogsHash = bytes32(0); + numberOfLogsToProcess = 0; + chainedMessagesHash = bytes32(0); + chainedL1BytecodesRevealDataHash = bytes32(0); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/L2EthToken.sol b/.test-node-subtree/etc/system-contracts/contracts/L2EthToken.sol new file mode 100644 index 00000000..fbd63ae2 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/L2EthToken.sol @@ -0,0 +1,143 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {IEthToken} from "./interfaces/IEthToken.sol"; +import {ISystemContract} from "./interfaces/ISystemContract.sol"; +import {MSG_VALUE_SYSTEM_CONTRACT, DEPLOYER_SYSTEM_CONTRACT, BOOTLOADER_FORMAL_ADDRESS, L1_MESSENGER_CONTRACT} from "./Constants.sol"; +import {IMailbox} from "./interfaces/IMailbox.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice Native ETH contract. + * @dev It does NOT provide interfaces for personal interaction with tokens like `transfer`, `approve`, and `transferFrom`. + * Instead, this contract is used by the bootloader and `MsgValueSimulator`/`ContractDeployer` system contracts + * to perform the balance changes while simulating the `msg.value` Ethereum behavior. + */ +contract L2EthToken is IEthToken, ISystemContract { + /// @notice The balances of the users. + mapping(address => uint256) internal balance; + + /// @notice The total amount of tokens that have been minted. + uint256 public override totalSupply; + + /// @notice Transfer tokens from one address to another. + /// @param _from The address to transfer the ETH from. + /// @param _to The address to transfer the ETH to. + /// @param _amount The amount of ETH in wei being transferred. + /// @dev This function can be called only by trusted system contracts. + /// @dev This function also emits "Transfer" event, which might be removed + /// later on. + function transferFromTo(address _from, address _to, uint256 _amount) external override { + require( + msg.sender == MSG_VALUE_SYSTEM_CONTRACT || + msg.sender == address(DEPLOYER_SYSTEM_CONTRACT) || + msg.sender == BOOTLOADER_FORMAL_ADDRESS, + "Only system contracts with special access can call this method" + ); + + uint256 fromBalance = balance[_from]; + require(fromBalance >= _amount, "Transfer amount exceeds balance"); + unchecked { + balance[_from] = fromBalance - _amount; + // Overflow not possible: the sum of all balances is capped by totalSupply, and the sum is preserved by + // decrementing then incrementing. + balance[_to] += _amount; + } + + emit Transfer(_from, _to, _amount); + } + + /// @notice Returns ETH balance of an account + /// @dev It takes `uint256` as an argument to be able to properly simulate the behaviour of the + /// Ethereum's `BALANCE` opcode that accepts uint256 as an argument and truncates any upper bits + /// @param _account The address of the account to return the balance of. + function balanceOf(uint256 _account) external view override returns (uint256) { + return balance[address(uint160(_account))]; + } + + /// @notice Increase the total supply of tokens and balance of the receiver. + /// @dev This method is only callable by the bootloader. + /// @param _account The address which to mint the funds to. + /// @param _amount The amount of ETH in wei to be minted. + function mint(address _account, uint256 _amount) external override onlyCallFromBootloader { + totalSupply += _amount; + balance[_account] += _amount; + emit Mint(_account, _amount); + } + + /// @notice Initiate the ETH withdrawal, funds will be available to claim on L1 `finalizeEthWithdrawal` method. + /// @param _l1Receiver The address on L1 to receive the funds. + function withdraw(address _l1Receiver) external payable override { + uint256 amount = _burnMsgValue(); + + // Send the L2 log, a user could use it as proof of the withdrawal + bytes memory message = _getL1WithdrawMessage(_l1Receiver, amount); + L1_MESSENGER_CONTRACT.sendToL1(message); + + emit Withdrawal(msg.sender, _l1Receiver, amount); + } + + /// @notice Initiate the ETH withdrawal, with the sent message. The funds will be available to claim on L1 `finalizeEthWithdrawal` method. + /// @param _l1Receiver The address on L1 to receive the funds. + /// @param _additionalData Additional data to be sent to L1 with the withdrawal. + function withdrawWithMessage(address _l1Receiver, bytes memory _additionalData) external payable override { + uint256 amount = _burnMsgValue(); + + // Send the L2 log, a user could use it as proof of the withdrawal + bytes memory message = _getExtendedWithdrawMessage(_l1Receiver, amount, msg.sender, _additionalData); + L1_MESSENGER_CONTRACT.sendToL1(message); + + emit WithdrawalWithMessage(msg.sender, _l1Receiver, amount, _additionalData); + } + + /// @dev The function burn the sent `msg.value`. + /// NOTE: Since this contract holds the mapping of all ether balances of the system, + /// the sent `msg.value` is added to the `this` balance before the call. + /// So the balance of `address(this)` is always bigger or equal to the `msg.value`! + function _burnMsgValue() internal returns (uint256 amount) { + amount = msg.value; + + // Silent burning of the ether + unchecked { + // This is safe, since this contract holds the ether balances, and if user + // send a `msg.value` it will be added to the contract (`this`) balance. + balance[address(this)] -= amount; + totalSupply -= amount; + } + } + + /// @dev Get the message to be sent to L1 to initiate a withdrawal. + function _getL1WithdrawMessage(address _to, uint256 _amount) internal pure returns (bytes memory) { + return abi.encodePacked(IMailbox.finalizeEthWithdrawal.selector, _to, _amount); + } + + /// @dev Get the message to be sent to L1 to initiate a withdrawal. + function _getExtendedWithdrawMessage( + address _to, + uint256 _amount, + address _sender, + bytes memory _additionalData + ) internal pure returns (bytes memory) { + return abi.encodePacked(IMailbox.finalizeEthWithdrawal.selector, _to, _amount, _sender, _additionalData); + } + + /// @dev This method has not been stabilized and might be + /// removed later on. + function name() external pure override returns (string memory) { + return "Ether"; + } + + /// @dev This method has not been stabilized and might be + /// removed later on. + function symbol() external pure override returns (string memory) { + return "ETH"; + } + + /// @dev This method has not been stabilized and might be + /// removed later on. + function decimals() external pure override returns (uint8) { + return 18; + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/MsgValueSimulator.sol b/.test-node-subtree/etc/system-contracts/contracts/MsgValueSimulator.sol new file mode 100644 index 00000000..07ed23d4 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/MsgValueSimulator.sol @@ -0,0 +1,59 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "./libraries/Utils.sol"; +import "./libraries/EfficientCall.sol"; +import "./interfaces/ISystemContract.sol"; +import {SystemContractHelper} from "./libraries/SystemContractHelper.sol"; +import {MSG_VALUE_SIMULATOR_IS_SYSTEM_BIT, ETH_TOKEN_SYSTEM_CONTRACT} from "./Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice The contract responsible for simulating transactions with `msg.value` inside zkEVM. + * @dev It accepts value and whether the call should be system in the first extraAbi param and + * the address to call in the second extraAbi param, transfers the funds and uses `mimicCall` to continue the + * call with the same msg.sender. + */ +contract MsgValueSimulator is ISystemContract { + /// @notice Extract value, isSystemCall and to from the extraAbi params. + /// @dev The contract accepts value, the callee and whether the call should a system one via its ABI params. + /// @dev The first ABI param contains the value in the [0..127] bits. The 128th contains + /// the flag whether or not the call should be a system one. + /// The second ABI params contains the callee. + function _getAbiParams() internal view returns (uint256 value, bool isSystemCall, address to) { + value = SystemContractHelper.getExtraAbiData(0); + uint256 addressAsUint = SystemContractHelper.getExtraAbiData(1); + uint256 mask = SystemContractHelper.getExtraAbiData(2); + + isSystemCall = (mask & MSG_VALUE_SIMULATOR_IS_SYSTEM_BIT) != 0; + + to = address(uint160(addressAsUint)); + } + + fallback(bytes calldata _data) external onlySystemCall returns (bytes memory) { + (uint256 value, bool isSystemCall, address to) = _getAbiParams(); + + // Prevent mimic call to the MsgValueSimulator to prevent an unexpected change of callee. + require(to != address(this), "MsgValueSimulator calls itself"); + + if (value != 0) { + (bool success, ) = address(ETH_TOKEN_SYSTEM_CONTRACT).call( + abi.encodeCall(ETH_TOKEN_SYSTEM_CONTRACT.transferFromTo, (msg.sender, to, value)) + ); + + // If the transfer of ETH fails, we do the most Ethereum-like behaviour in such situation: revert(0,0) + if (!success) { + assembly { + revert(0, 0) + } + } + } + + // For the next call this `msg.value` will be used. + SystemContractHelper.setValueForNextFarCall(Utils.safeCastToU128(value)); + + return EfficientCall.mimicCall(gasleft(), to, _data, msg.sender, false, isSystemCall); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/NonceHolder.sol b/.test-node-subtree/etc/system-contracts/contracts/NonceHolder.sol new file mode 100644 index 00000000..b2775f1c --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/NonceHolder.sol @@ -0,0 +1,179 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "./interfaces/INonceHolder.sol"; +import "./interfaces/IContractDeployer.sol"; +import {ISystemContract} from "./interfaces/ISystemContract.sol"; +import {DEPLOYER_SYSTEM_CONTRACT} from "./Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice A contract used for managing nonces for accounts. Together with bootloader, + * this contract ensures that the pair (sender, nonce) is always unique, ensuring + * unique transaction hashes. + * @dev The account allows for both ascending growth in nonces and mapping nonces to specific + * stored values in them. + * The users can either marked a range of nonces by increasing the `minNonce`. This way all the nonces + * less than `minNonce` will become used. The other way to mark a certain 256-bit key as nonce is to set + * some value under it in this contract. + * @dev Apart from transaction nonces, this contract also stores the deployment nonce for accounts, that + * will be used for address derivation using CREATE. For the economy of space, this nonce is stored tightly + * packed with the `minNonce`. + * @dev The behavior of some of the methods depends on the nonce ordering of the account. Nonce ordering is a mere suggestion and all the checks that are present + * here serve more as a help to users to prevent from doing mistakes, rather than any invariants. + */ +contract NonceHolder is INonceHolder, ISystemContract { + uint256 constant DEPLOY_NONCE_MULTIPLIER = 2 ** 128; + /// The minNonce can be increased by at 2^32 at a time to prevent it from + /// overflowing beyond 2**128. + uint256 constant MAXIMAL_MIN_NONCE_INCREMENT = 2 ** 32; + + /// RawNonces for accounts are stored in format + /// minNonce + 2^128 * deploymentNonce, where deploymentNonce + /// is the nonce used for deploying smart contracts. + mapping(uint256 => uint256) internal rawNonces; + + /// Mapping of values under nonces for accounts. + /// The main key of the mapping is the 256-bit address of the account, while the + /// inner mapping is a mapping from a nonce to the value stored there. + mapping(uint256 => mapping(uint256 => uint256)) internal nonceValues; + + /// @notice Returns the current minimal nonce for account. + /// @param _address The account to return the minimal nonce for + /// @return The current minimal nonce for this account. + function getMinNonce(address _address) public view returns (uint256) { + uint256 addressAsKey = uint256(uint160(_address)); + (, uint256 minNonce) = _splitRawNonce(rawNonces[addressAsKey]); + + return minNonce; + } + + /// @notice Returns the raw version of the current minimal nonce + /// @dev It is equal to minNonce + 2^128 * deployment nonce. + /// @param _address The account to return the raw nonce for + /// @return The raw nonce for this account. + function getRawNonce(address _address) public view returns (uint256) { + uint256 addressAsKey = uint256(uint160(_address)); + return rawNonces[addressAsKey]; + } + + /// @notice Increases the minimal nonce for the msg.sender and returns the previous one. + /// @param _value The number by which to increase the minimal nonce for msg.sender. + /// @return oldMinNonce The value of the minimal nonce for msg.sender before the increase. + function increaseMinNonce(uint256 _value) public onlySystemCall returns (uint256 oldMinNonce) { + require(_value <= MAXIMAL_MIN_NONCE_INCREMENT, "The value for incrementing the nonce is too high"); + + uint256 addressAsKey = uint256(uint160(msg.sender)); + uint256 oldRawNonce = rawNonces[addressAsKey]; + + unchecked { + rawNonces[addressAsKey] = (oldRawNonce + _value); + } + + (, oldMinNonce) = _splitRawNonce(oldRawNonce); + } + + /// @notice Sets the nonce value `key` for the msg.sender as used. + /// @param _key The nonce key under which the value will be set. + /// @param _value The value to store under the _key. + /// @dev The value must be non-zero. + function setValueUnderNonce(uint256 _key, uint256 _value) public onlySystemCall { + IContractDeployer.AccountInfo memory accountInfo = DEPLOYER_SYSTEM_CONTRACT.getAccountInfo(msg.sender); + + require(_value != 0, "Nonce value cannot be set to 0"); + // If an account has sequential nonce ordering, we enforce that the previous + // nonce has already been used. + if (accountInfo.nonceOrdering == IContractDeployer.AccountNonceOrdering.Sequential && _key != 0) { + require(isNonceUsed(msg.sender, _key - 1), "Previous nonce has not been used"); + } + + uint256 addressAsKey = uint256(uint160(msg.sender)); + + nonceValues[addressAsKey][_key] = _value; + + emit ValueSetUnderNonce(msg.sender, _key, _value); + } + + /// @notice Gets the value stored under a custom nonce for msg.sender. + /// @param _key The key under which to get the stored value. + /// @return The value stored under the `_key` for the msg.sender. + function getValueUnderNonce(uint256 _key) public view returns (uint256) { + uint256 addressAsKey = uint256(uint160(msg.sender)); + return nonceValues[addressAsKey][_key]; + } + + /// @notice A convenience method to increment the minimal nonce if it is equal + /// to the `_expectedNonce`. + /// @param _expectedNonce The expected minimal nonce for the account. + function incrementMinNonceIfEquals(uint256 _expectedNonce) external onlySystemCall { + uint256 addressAsKey = uint256(uint160(msg.sender)); + uint256 oldRawNonce = rawNonces[addressAsKey]; + + (, uint256 oldMinNonce) = _splitRawNonce(oldRawNonce); + require(oldMinNonce == _expectedNonce, "Incorrect nonce"); + + unchecked { + rawNonces[addressAsKey] = oldRawNonce + 1; + } + } + + /// @notice Returns the deployment nonce for the accounts used for CREATE opcode. + /// @param _address The address to return the deploy nonce of. + /// @return deploymentNonce The deployment nonce of the account. + function getDeploymentNonce(address _address) external view returns (uint256 deploymentNonce) { + uint256 addressAsKey = uint256(uint160(_address)); + (deploymentNonce, ) = _splitRawNonce(rawNonces[addressAsKey]); + + return deploymentNonce; + } + + /// @notice Increments the deployment nonce for the account and returns the previous one. + /// @param _address The address of the account which to return the deploy nonce for. + /// @return prevDeploymentNonce The deployment nonce at the time this function is called. + function incrementDeploymentNonce(address _address) external returns (uint256 prevDeploymentNonce) { + require( + msg.sender == address(DEPLOYER_SYSTEM_CONTRACT), + "Only the contract deployer can increment the deployment nonce" + ); + uint256 addressAsKey = uint256(uint160(_address)); + uint256 oldRawNonce = rawNonces[addressAsKey]; + + unchecked { + rawNonces[addressAsKey] = (oldRawNonce + DEPLOY_NONCE_MULTIPLIER); + } + + (prevDeploymentNonce, ) = _splitRawNonce(oldRawNonce); + } + + function isNonceUsed(address _address, uint256 _nonce) public view returns (bool) { + uint256 addressAsKey = uint256(uint160(_address)); + return (_nonce < getMinNonce(_address) || nonceValues[addressAsKey][_nonce] > 0); + } + + /// @notice Checks and reverts based on whether the nonce is used (not used). + /// @param _address The address the nonce of which is being checked. + /// @param _key The nonce value which is tested. + /// @param _shouldBeUsed The flag for the method. If `true`, the method checks that whether this nonce + /// is marked as used and reverts if this is not the case. If `false`, this method will check that the nonce + /// has *not* been used yet, and revert otherwise. + /// @dev This method should be used by the bootloader. + function validateNonceUsage(address _address, uint256 _key, bool _shouldBeUsed) external view { + bool isUsed = isNonceUsed(_address, _key); + + if (isUsed && !_shouldBeUsed) { + revert("Reusing the same nonce twice"); + } else if (!isUsed && _shouldBeUsed) { + revert("The nonce was not set as used"); + } + } + + /// @notice Splits the raw nonce value into the deployment nonce and the minimal nonce. + /// @param _rawMinNonce The value of the raw minimal nonce (equal to minNonce + deploymentNonce* 2**128). + /// @return deploymentNonce and minNonce. + function _splitRawNonce(uint256 _rawMinNonce) internal pure returns (uint256 deploymentNonce, uint256 minNonce) { + deploymentNonce = _rawMinNonce / DEPLOY_NONCE_MULTIPLIER; + minNonce = _rawMinNonce % DEPLOY_NONCE_MULTIPLIER; + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/SystemContext.sol b/.test-node-subtree/etc/system-contracts/contracts/SystemContext.sol new file mode 100644 index 00000000..67f9248e --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/SystemContext.sol @@ -0,0 +1,483 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {ISystemContext} from "./interfaces/ISystemContext.sol"; +import {ISystemContract} from "./interfaces/ISystemContract.sol"; +import {ISystemContextDeprecated} from "./interfaces/ISystemContextDeprecated.sol"; +import {SystemContractHelper} from "./libraries/SystemContractHelper.sol"; +import {BOOTLOADER_FORMAL_ADDRESS, SystemLogKey} from "./Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice Contract that stores some of the context variables, that may be either + * block-scoped, tx-scoped or system-wide. + */ +contract SystemContext is ISystemContext, ISystemContextDeprecated, ISystemContract { + /// @notice The number of latest L2 blocks to store. + /// @dev EVM requires us to be able to query the hashes of previous 256 blocks. + /// We could either: + /// - Store the latest 256 hashes (and strictly rely that we do not accidentally override the hash of the block 256 blocks ago) + /// - Store the latest 257 blocks's hashes. + uint256 internal constant MINIBLOCK_HASHES_TO_STORE = 257; + + /// @notice The chainId of the network. It is set at the genesis. + uint256 public chainId; + + /// @notice The `tx.origin` in the current transaction. + /// @dev It is updated before each transaction by the bootloader + address public origin; + + /// @notice The `tx.gasPrice` in the current transaction. + /// @dev It is updated before each transaction by the bootloader + uint256 public gasPrice; + + /// @notice The current block's gasLimit. + uint256 public blockGasLimit = type(uint32).max; + + /// @notice The `block.coinbase` in the current transaction. + /// @dev For the support of coinbase, we will use the bootloader formal address for now + address public coinbase = BOOTLOADER_FORMAL_ADDRESS; + + /// @notice Formal `block.difficulty` parameter. + uint256 public difficulty = 2500000000000000; + + /// @notice The `block.basefee`. + /// @dev It is currently a constant. + uint256 public baseFee; + + /// @notice The number and the timestamp of the current L1 batch stored packed. + BlockInfo internal currentBatchInfo; + + /// @notice The hashes of batches. + /// @dev It stores batch hashes for all previous batches. + mapping(uint256 => bytes32) internal batchHash; + + /// @notice The number and the timestamp of the current L2 block. + BlockInfo internal currentL2BlockInfo; + + /// @notice The rolling hash of the transactions in the current L2 block. + bytes32 internal currentL2BlockTxsRollingHash; + + /// @notice The hashes of L2 blocks. + /// @dev It stores block hashes for previous L2 blocks. Note, in order to make publishing the hashes + /// of the miniblocks cheaper, we only store the previous MINIBLOCK_HASHES_TO_STORE ones. Since whenever we need to publish a state + /// diff, a pair of is published and for cached keys only 8-byte id is used instead of 32 bytes. + /// By having this data in a cyclic array of MINIBLOCK_HASHES_TO_STORE blocks, we bring the costs down by 40% (i.e. 40 bytes per miniblock instead of 64 bytes). + /// @dev The hash of a miniblock with number N would be stored under slot N%MINIBLOCK_HASHES_TO_STORE. + /// @dev Hashes of the blocks older than the ones which are stored here can be calculated as _calculateLegacyL2BlockHash(blockNumber). + bytes32[MINIBLOCK_HASHES_TO_STORE] internal l2BlockHash; + + /// @notice To make migration to L2 blocks smoother, we introduce a temporary concept of virtual L2 blocks, the data + /// about which will be returned by the EVM-like methods: block.number/block.timestamp/blockhash. + /// - Their number will start from being equal to the number of the batch and it will increase until it reaches the L2 block number. + /// - Their timestamp is updated each time a new virtual block is created. + /// - Their hash is calculated as `keccak256(uint256(number))` + BlockInfo internal currentVirtualL2BlockInfo; + + /// @notice The information about the virtual blocks upgrade, which tracks when the migration to the L2 blocks has started and finished. + VirtualBlockUpgradeInfo internal virtualBlockUpgradeInfo; + + /// @notice Number of current transaction in block. + uint16 public txNumberInBlock; + + /// @notice Set the current tx origin. + /// @param _newOrigin The new tx origin. + function setTxOrigin(address _newOrigin) external onlyCallFromBootloader { + origin = _newOrigin; + } + + /// @notice Set the the current gas price. + /// @param _gasPrice The new tx gasPrice. + function setGasPrice(uint256 _gasPrice) external onlyCallFromBootloader { + gasPrice = _gasPrice; + } + + /// @notice The method that emulates `blockhash` opcode in EVM. + /// @dev Just like the blockhash in the EVM, it returns bytes32(0), + /// when queried about hashes that are older than 256 blocks ago. + /// @dev Since zksolc compiler calls this method to emulate `blockhash`, + /// its signature can not be changed to `getL2BlockHashEVM`. + /// @return hash The blockhash of the block with the given number. + function getBlockHashEVM(uint256 _block) external view returns (bytes32 hash) { + uint128 blockNumber = currentVirtualL2BlockInfo.number; + + VirtualBlockUpgradeInfo memory currentVirtualBlockUpgradeInfo = virtualBlockUpgradeInfo; + + // Due to virtual blocks upgrade, we'll have to use the following logic for retreiving the blockhash: + // 1. If the block number is out of the 256-block supported range, return 0. + // 2. If the block was created before the upgrade for the virtual blocks (i.e. there we used to use hashes of the batches), + // we return the hash of the batch. + // 3. If the block was created after the day when the virtual blocks have caught up with the L2 blocks, i.e. + // all the information which is returned for users should be for L2 blocks, we return the hash of the corresponding L2 block. + // 4. If the block queried is a virtual blocks, calculate it on the fly. + if (blockNumber <= _block || blockNumber - _block > 256) { + hash = bytes32(0); + } else if (_block < currentVirtualBlockUpgradeInfo.virtualBlockStartBatch) { + // Note, that we will get into this branch only for a brief moment of time, right after the upgrade + // for virtual blocks before 256 virtual blocks are produced. + hash = batchHash[_block]; + } else if ( + _block >= currentVirtualBlockUpgradeInfo.virtualBlockFinishL2Block && + currentVirtualBlockUpgradeInfo.virtualBlockFinishL2Block > 0 + ) { + hash = _getLatest257L2blockHash(_block); + } else { + // Important: we do not want this number to ever collide with the L2 block hash (either new or old one) and so + // that's why the legacy L2 blocks' hashes are keccak256(abi.encodePacked(uint32(_block))), while these are equivalent to + // keccak256(abi.encodePacked(_block)) + hash = keccak256(abi.encode(_block)); + } + } + + /// @notice Returns the hash of the given batch. + /// @param _batchNumber The number of the batch. + /// @return hash The hash of the batch. + function getBatchHash(uint256 _batchNumber) external view returns (bytes32 hash) { + hash = batchHash[_batchNumber]; + } + + /// @notice Returns the current batch's number and timestamp. + /// @return batchNumber and batchTimestamp tuple of the current batch's number and the current batch's timestamp + function getBatchNumberAndTimestamp() public view returns (uint128 batchNumber, uint128 batchTimestamp) { + BlockInfo memory batchInfo = currentBatchInfo; + batchNumber = batchInfo.number; + batchTimestamp = batchInfo.timestamp; + } + + /// @notice Returns the current block's number and timestamp. + /// @return blockNumber and blockTimestamp tuple of the current L2 block's number and the current block's timestamp + function getL2BlockNumberAndTimestamp() public view returns (uint128 blockNumber, uint128 blockTimestamp) { + BlockInfo memory blockInfo = currentL2BlockInfo; + blockNumber = blockInfo.number; + blockTimestamp = blockInfo.timestamp; + } + + /// @notice Returns the current L2 block's number. + /// @dev Since zksolc compiler calls this method to emulate `block.number`, + /// its signature can not be changed to `getL2BlockNumber`. + /// @return blockNumber The current L2 block's number. + function getBlockNumber() public view returns (uint128) { + return currentVirtualL2BlockInfo.number; + } + + /// @notice Returns the current L2 block's timestamp. + /// @dev Since zksolc compiler calls this method to emulate `block.timestamp`, + /// its signature can not be changed to `getL2BlockTimestamp`. + /// @return timestamp The current L2 block's timestamp. + function getBlockTimestamp() public view returns (uint128) { + return currentVirtualL2BlockInfo.timestamp; + } + + /// @notice Assuming that block is one of the last MINIBLOCK_HASHES_TO_STORE ones, returns its hash. + /// @param _block The number of the block. + /// @return hash The hash of the block. + function _getLatest257L2blockHash(uint256 _block) internal view returns (bytes32) { + return l2BlockHash[_block % MINIBLOCK_HASHES_TO_STORE]; + } + + /// @notice Assuming that the block is one of the last MINIBLOCK_HASHES_TO_STORE ones, sets its hash. + /// @param _block The number of the block. + /// @param _hash The hash of the block. + function _setL2BlockHash(uint256 _block, bytes32 _hash) internal { + l2BlockHash[_block % MINIBLOCK_HASHES_TO_STORE] = _hash; + } + + /// @notice Calculates the hash of an L2 block. + /// @param _blockNumber The number of the L2 block. + /// @param _blockTimestamp The timestamp of the L2 block. + /// @param _prevL2BlockHash The hash of the previous L2 block. + /// @param _blockTxsRollingHash The rolling hash of the transactions in the L2 block. + function _calculateL2BlockHash( + uint128 _blockNumber, + uint128 _blockTimestamp, + bytes32 _prevL2BlockHash, + bytes32 _blockTxsRollingHash + ) internal pure returns (bytes32) { + return keccak256(abi.encode(_blockNumber, _blockTimestamp, _prevL2BlockHash, _blockTxsRollingHash)); + } + + /// @notice Calculates the legacy block hash of L2 block, which were used before the upgrade where + /// the advanced block hashes were introduced. + /// @param _blockNumber The number of the L2 block. + function _calculateLegacyL2BlockHash(uint128 _blockNumber) internal pure returns (bytes32) { + return keccak256(abi.encodePacked(uint32(_blockNumber))); + } + + /// @notice Performs the upgrade where we transition to the L2 blocks. + /// @param _l2BlockNumber The number of the new L2 block. + /// @param _expectedPrevL2BlockHash The expected hash of the previous L2 block. + /// @param _isFirstInBatch Whether this method is called for the first time in the batch. + function _upgradeL2Blocks(uint128 _l2BlockNumber, bytes32 _expectedPrevL2BlockHash, bool _isFirstInBatch) internal { + require(_isFirstInBatch, "Upgrade transaction must be first"); + + // This is how it will be commonly done in practice, but it will simplify some logic later + require(_l2BlockNumber > 0, "L2 block number is never expected to be zero"); + + unchecked { + bytes32 correctPrevBlockHash = _calculateLegacyL2BlockHash(_l2BlockNumber - 1); + require(correctPrevBlockHash == _expectedPrevL2BlockHash, "The previous L2 block hash is incorrect"); + + // Whenever we'll be queried about the hashes of the blocks before the upgrade, + // we'll use batches' hashes, so we don't need to store 256 previous hashes. + // However, we do need to store the last previous hash in order to be able to correctly calculate the + // hash of the new L2 block. + _setL2BlockHash(_l2BlockNumber - 1, correctPrevBlockHash); + } + } + + /// @notice Creates new virtual blocks, while ensuring they don't exceed the L2 block number. + /// @param _l2BlockNumber The number of the new L2 block. + /// @param _maxVirtualBlocksToCreate The maximum number of virtual blocks to create with this L2 block. + /// @param _newTimestamp The timestamp of the new L2 block, which is also the timestamp of the new virtual block. + function _setVirtualBlock( + uint128 _l2BlockNumber, + uint128 _maxVirtualBlocksToCreate, + uint128 _newTimestamp + ) internal { + if (virtualBlockUpgradeInfo.virtualBlockFinishL2Block != 0) { + // No need to to do anything about virtual blocks anymore + // All the info is the same as for L2 blocks. + currentVirtualL2BlockInfo = currentL2BlockInfo; + return; + } + + BlockInfo memory virtualBlockInfo = currentVirtualL2BlockInfo; + + if (currentVirtualL2BlockInfo.number == 0 && virtualBlockInfo.timestamp == 0) { + uint128 currentBatchNumber = currentBatchInfo.number; + + // The virtual block is set for the first time. We can count it as 1 creation of a virtual block. + // Note, that when setting the virtual block number we use the batch number to make a smoother upgrade from batch number to + // the L2 block number. + virtualBlockInfo.number = currentBatchNumber; + // Remembering the batch number on which the upgrade to the virtual blocks has been done. + virtualBlockUpgradeInfo.virtualBlockStartBatch = currentBatchNumber; + + require(_maxVirtualBlocksToCreate > 0, "Can't initialize the first virtual block"); + _maxVirtualBlocksToCreate -= 1; + } else if (_maxVirtualBlocksToCreate == 0) { + // The virtual blocks have been already initialized, but the operator didn't ask to create + // any new virtual blocks. So we can just return. + return; + } + + virtualBlockInfo.number += _maxVirtualBlocksToCreate; + virtualBlockInfo.timestamp = _newTimestamp; + + // The virtual block number must never exceed the L2 block number. + // We do not use a `require` here, since the virtual blocks are a temporary solution to let the Solidity's `block.number` + // catch up with the L2 block number and so the situation where virtualBlockInfo.number starts getting larger + // than _l2BlockNumber is expected once virtual blocks have caught up the L2 blocks. + if (virtualBlockInfo.number >= _l2BlockNumber) { + virtualBlockUpgradeInfo.virtualBlockFinishL2Block = _l2BlockNumber; + virtualBlockInfo.number = _l2BlockNumber; + } + + currentVirtualL2BlockInfo = virtualBlockInfo; + } + + /// @notice Sets the current block number and timestamp of the L2 block. + /// @param _l2BlockNumber The number of the new L2 block. + /// @param _l2BlockTimestamp The timestamp of the new L2 block. + /// @param _prevL2BlockHash The hash of the previous L2 block. + function _setNewL2BlockData(uint128 _l2BlockNumber, uint128 _l2BlockTimestamp, bytes32 _prevL2BlockHash) internal { + // In the unsafe version we do not check that the block data is correct + currentL2BlockInfo = BlockInfo({number: _l2BlockNumber, timestamp: _l2BlockTimestamp}); + + // It is always assumed in production that _l2BlockNumber > 0 + _setL2BlockHash(_l2BlockNumber - 1, _prevL2BlockHash); + + // Reseting the rolling hash + currentL2BlockTxsRollingHash = bytes32(0); + } + + /// @notice Sets the current block number and timestamp of the L2 block. + /// @dev Called by the bootloader before each transaction. This is needed to ensure + /// that the data about the block is consistent with the sequencer. + /// @dev If the new block number is the same as the current one, we ensure that the block's data is + /// consistent with the one in the current block. + /// @dev If the new block number is greater than the current one by 1, + /// then we ensure that timestamp has increased. + /// @dev If the currently stored number is 0, we assume that it is the first upgrade transaction + /// and so we will fill up the old data. + /// @param _l2BlockNumber The number of the new L2 block. + /// @param _l2BlockTimestamp The timestamp of the new L2 block. + /// @param _expectedPrevL2BlockHash The expected hash of the previous L2 block. + /// @param _isFirstInBatch Whether this method is called for the first time in the batch. + /// @param _maxVirtualBlocksToCreate The maximum number of virtual block to create with this L2 block. + /// @dev It is a strict requirement that a new virtual block is created at the start of the batch. + /// @dev It is also enforced that the number of the current virtual L2 block can not exceed the number of the L2 block. + function setL2Block( + uint128 _l2BlockNumber, + uint128 _l2BlockTimestamp, + bytes32 _expectedPrevL2BlockHash, + bool _isFirstInBatch, + uint128 _maxVirtualBlocksToCreate + ) external onlyCallFromBootloader { + // We check that the timestamp of the L2 block is consistent with the timestamp of the batch. + if (_isFirstInBatch) { + uint128 currentBatchTimestamp = currentBatchInfo.timestamp; + require( + _l2BlockTimestamp >= currentBatchTimestamp, + "The timestamp of the L2 block must be greater than or equal to the timestamp of the current batch" + ); + require(_maxVirtualBlocksToCreate > 0, "There must be a virtual block created at the start of the batch"); + } + + (uint128 currentL2BlockNumber, uint128 currentL2BlockTimestamp) = getL2BlockNumberAndTimestamp(); + + if (currentL2BlockNumber == 0 && currentL2BlockTimestamp == 0) { + // Since currentL2BlockNumber and currentL2BlockTimestamp are zero it means that it is + // the first ever batch with L2 blocks, so we need to initialize those. + _upgradeL2Blocks(_l2BlockNumber, _expectedPrevL2BlockHash, _isFirstInBatch); + + _setNewL2BlockData(_l2BlockNumber, _l2BlockTimestamp, _expectedPrevL2BlockHash); + } else if (currentL2BlockNumber == _l2BlockNumber) { + require(!_isFirstInBatch, "Can not reuse L2 block number from the previous batch"); + require(currentL2BlockTimestamp == _l2BlockTimestamp, "The timestamp of the same L2 block must be same"); + require( + _expectedPrevL2BlockHash == _getLatest257L2blockHash(_l2BlockNumber - 1), + "The previous hash of the same L2 block must be same" + ); + require(_maxVirtualBlocksToCreate == 0, "Can not create virtual blocks in the middle of the miniblock"); + } else if (currentL2BlockNumber + 1 == _l2BlockNumber) { + // From the checks in _upgradeL2Blocks it is known that currentL2BlockNumber can not be 0 + bytes32 prevL2BlockHash = _getLatest257L2blockHash(currentL2BlockNumber - 1); + + bytes32 pendingL2BlockHash = _calculateL2BlockHash( + currentL2BlockNumber, + currentL2BlockTimestamp, + prevL2BlockHash, + currentL2BlockTxsRollingHash + ); + + require(_expectedPrevL2BlockHash == pendingL2BlockHash, "The current L2 block hash is incorrect"); + require( + _l2BlockTimestamp > currentL2BlockTimestamp, + "The timestamp of the new L2 block must be greater than the timestamp of the previous L2 block" + ); + + // Since the new block is created, we'll clear out the rolling hash + _setNewL2BlockData(_l2BlockNumber, _l2BlockTimestamp, _expectedPrevL2BlockHash); + } else { + revert("Invalid new L2 block number"); + } + + _setVirtualBlock(_l2BlockNumber, _maxVirtualBlocksToCreate, _l2BlockTimestamp); + } + + /// @notice Appends the transaction hash to the rolling hash of the current L2 block. + /// @param _txHash The hash of the transaction. + function appendTransactionToCurrentL2Block(bytes32 _txHash) external onlyCallFromBootloader { + currentL2BlockTxsRollingHash = keccak256(abi.encode(currentL2BlockTxsRollingHash, _txHash)); + } + + /// @notice Publishes L2->L1 logs needed to verify the validity of this batch on L1. + /// @dev Should be called at the end of the current batch. + function publishTimestampDataToL1() external onlyCallFromBootloader { + (uint128 currentBatchNumber, uint128 currentBatchTimestamp) = getBatchNumberAndTimestamp(); + (, uint128 currentL2BlockTimestamp) = getL2BlockNumberAndTimestamp(); + + // The structure of the "setNewBatch" implies that currentBatchNumber > 0, but we still double check it + require(currentBatchNumber > 0, "The current batch number must be greater than 0"); + + // In order to spend less pubdata, the packed version is published + uint256 packedTimestamps = (uint256(currentBatchTimestamp) << 128) | currentL2BlockTimestamp; + + SystemContractHelper.toL1( + false, + bytes32(uint256(SystemLogKey.PACKED_BATCH_AND_L2_BLOCK_TIMESTAMP_KEY)), + bytes32(packedTimestamps) + ); + } + + /// @notice Ensures that the timestamp of the batch is greater than the timestamp of the last L2 block. + /// @param _newTimestamp The timestamp of the new batch. + function _ensureBatchConsistentWithL2Block(uint128 _newTimestamp) internal view { + uint128 currentBlockTimestamp = currentL2BlockInfo.timestamp; + require( + _newTimestamp > currentBlockTimestamp, + "The timestamp of the batch must be greater than the timestamp of the previous block" + ); + } + + /// @notice Increments the current batch number and sets the new timestamp + /// @dev Called by the bootloader at the start of the batch. + /// @param _prevBatchHash The hash of the previous batch. + /// @param _newTimestamp The timestamp of the new batch. + /// @param _expectedNewNumber The new batch's number. + /// @param _baseFee The new batch's base fee + /// @dev While _expectedNewNumber can be derived as prevBatchNumber + 1, we still + /// manually supply it here for consistency checks. + /// @dev The correctness of the _prevBatchHash and _newTimestamp should be enforced on L1. + function setNewBatch( + bytes32 _prevBatchHash, + uint128 _newTimestamp, + uint128 _expectedNewNumber, + uint256 _baseFee + ) external onlyCallFromBootloader { + (uint128 previousBatchNumber, uint128 previousBatchTimestamp) = getBatchNumberAndTimestamp(); + require(_newTimestamp > previousBatchTimestamp, "Timestamps should be incremental"); + require(previousBatchNumber + 1 == _expectedNewNumber, "The provided block number is not correct"); + + _ensureBatchConsistentWithL2Block(_newTimestamp); + + batchHash[previousBatchNumber] = _prevBatchHash; + + // Setting new block number and timestamp + BlockInfo memory newBlockInfo = BlockInfo({number: previousBatchNumber + 1, timestamp: _newTimestamp}); + + currentBatchInfo = newBlockInfo; + + baseFee = _baseFee; + + // The correctness of this block hash: + SystemContractHelper.toL1(false, bytes32(uint256(SystemLogKey.PREV_BATCH_HASH_KEY)), _prevBatchHash); + } + + /// @notice A testing method that manually sets the current blocks' number and timestamp. + /// @dev Should be used only for testing / ethCalls and should never be used in production. + function unsafeOverrideBatch( + uint256 _newTimestamp, + uint256 _number, + uint256 _baseFee + ) external onlyCallFromBootloader { + BlockInfo memory newBlockInfo = BlockInfo({number: uint128(_number), timestamp: uint128(_newTimestamp)}); + currentBatchInfo = newBlockInfo; + + baseFee = _baseFee; + } + + function incrementTxNumberInBatch() external onlyCallFromBootloader { + txNumberInBlock += 1; + } + + function resetTxNumberInBatch() external onlyCallFromBootloader { + txNumberInBlock = 0; + } + + /*////////////////////////////////////////////////////////////// + DEPRECATED METHODS + //////////////////////////////////////////////////////////////*/ + + /// @notice Returns the current batch's number and timestamp. + /// @dev Deprecated in favor of getBatchNumberAndTimestamp. + function currentBlockInfo() external view returns (uint256 blockInfo) { + (uint128 blockNumber, uint128 blockTimestamp) = getBatchNumberAndTimestamp(); + blockInfo = (uint256(blockNumber) << 128) | uint256(blockTimestamp); + } + + /// @notice Returns the current batch's number and timestamp. + /// @dev Deprecated in favor of getBatchNumberAndTimestamp. + function getBlockNumberAndTimestamp() external view returns (uint256 blockNumber, uint256 blockTimestamp) { + (blockNumber, blockTimestamp) = getBatchNumberAndTimestamp(); + } + + /// @notice Returns the hash of the given batch. + /// @dev Deprecated in favor of getBatchHash. + function blockHash(uint256 _blockNumber) external view returns (bytes32 hash) { + hash = batchHash[_blockNumber]; + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IAccount.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IAccount.sol new file mode 100644 index 00000000..fcbc0083 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IAccount.sol @@ -0,0 +1,53 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "../libraries/TransactionHelper.sol"; + +bytes4 constant ACCOUNT_VALIDATION_SUCCESS_MAGIC = IAccount.validateTransaction.selector; + +interface IAccount { + /// @notice Called by the bootloader to validate that an account agrees to process the transaction + /// (and potentially pay for it). + /// @param _txHash The hash of the transaction to be used in the explorer + /// @param _suggestedSignedHash The hash of the transaction is signed by EOAs + /// @param _transaction The transaction itself + /// @return magic The magic value that should be equal to the signature of this function + /// if the user agrees to proceed with the transaction. + /// @dev The developer should strive to preserve as many steps as possible both for valid + /// and invalid transactions as this very method is also used during the gas fee estimation + /// (without some of the necessary data, e.g. signature). + function validateTransaction( + bytes32 _txHash, + bytes32 _suggestedSignedHash, + Transaction calldata _transaction + ) external payable returns (bytes4 magic); + + /// + /// FOUNDRY SUPPORT START + /// + function executeTransaction( + bytes32 _txHash, + bytes32 _suggestedSignedHash, + Transaction calldata _transaction + ) external payable returns ( bytes memory returnData ); + /// + /// FOUNDRY SUPPORT END + /// + + // There is no point in providing possible signed hash in the `executeTransactionFromOutside` method, + // since it typically should not be trusted. + function executeTransactionFromOutside(Transaction calldata _transaction) external payable; + + function payForTransaction( + bytes32 _txHash, + bytes32 _suggestedSignedHash, + Transaction calldata _transaction + ) external payable; + + function prepareForPaymaster( + bytes32 _txHash, + bytes32 _possibleSignedHash, + Transaction calldata _transaction + ) external payable; +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IAccountCodeStorage.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IAccountCodeStorage.sol new file mode 100644 index 00000000..c266774e --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IAccountCodeStorage.sol @@ -0,0 +1,17 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +interface IAccountCodeStorage { + function storeAccountConstructingCodeHash(address _address, bytes32 _hash) external; + + function storeAccountConstructedCodeHash(address _address, bytes32 _hash) external; + + function markAccountCodeHashAsConstructed(address _address) external; + + function getRawCodeHash(address _address) external view returns (bytes32 codeHash); + + function getCodeHash(uint256 _input) external view returns (bytes32 codeHash); + + function getCodeSize(uint256 _input) external view returns (uint256 codeSize); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IBootloaderUtilities.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IBootloaderUtilities.sol new file mode 100644 index 00000000..e995295e --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IBootloaderUtilities.sol @@ -0,0 +1,11 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "../libraries/TransactionHelper.sol"; + +interface IBootloaderUtilities { + function getTransactionHashes( + Transaction calldata _transaction + ) external view returns (bytes32 txHash, bytes32 signedTxHash); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IComplexUpgrader.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IComplexUpgrader.sol new file mode 100644 index 00000000..ebc26dd2 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IComplexUpgrader.sol @@ -0,0 +1,7 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +interface IComplexUpgrader { + function upgrade(address _delegateTo, bytes calldata _calldata) external payable; +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/ICompressor.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/ICompressor.sol new file mode 100644 index 00000000..16e02d97 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/ICompressor.sol @@ -0,0 +1,24 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +// The bitmask by applying which to the compressed state diff metadata we retrieve its operation. +uint8 constant OPERATION_BITMASK = 7; +// The number of bits shifting the compressed state diff metadata by which we retrieve its length. +uint8 constant LENGTH_BITS_OFFSET = 3; +// The maximal length in bytes that an enumeration index can have. +uint8 constant MAX_ENUMERATION_INDEX_SIZE = 8; + +interface ICompressor { + function publishCompressedBytecode( + bytes calldata _bytecode, + bytes calldata _rawCompressedData + ) external payable returns (bytes32 bytecodeHash); + + function verifyCompressedStateDiffs( + uint256 _numberOfStateDiffs, + uint256 _enumerationIndexSize, + bytes calldata _stateDiffs, + bytes calldata _compressedStateDiffs + ) external payable returns (bytes32 stateDiffHash); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IContractDeployer.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IContractDeployer.sol new file mode 100644 index 00000000..3f84672d --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IContractDeployer.sol @@ -0,0 +1,91 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +interface IContractDeployer { + /// @notice Defines the version of the account abstraction protocol + /// that a contract claims to follow. + /// - `None` means that the account is just a contract and it should never be interacted + /// with as a custom account + /// - `Version1` means that the account follows the first version of the account abstraction protocol + enum AccountAbstractionVersion { + None, + Version1 + } + + /// @notice Defines the nonce ordering used by the account + /// - `Sequential` means that it is expected that the nonces are monotonic and increment by 1 + /// at a time (the same as EOAs). + /// - `Arbitrary` means that the nonces for the accounts can be arbitrary. The operator + /// should serve the transactions from such an account on a first-come-first-serve basis. + /// @dev This ordering is more of a suggestion to the operator on how the AA expects its transactions + /// to be processed and is not considered as a system invariant. + enum AccountNonceOrdering { + Sequential, + Arbitrary + } + + struct AccountInfo { + AccountAbstractionVersion supportedAAVersion; + AccountNonceOrdering nonceOrdering; + } + + event ContractDeployed( + address indexed deployerAddress, + bytes32 indexed bytecodeHash, + address indexed contractAddress + ); + + event AccountNonceOrderingUpdated(address indexed accountAddress, AccountNonceOrdering nonceOrdering); + + event AccountVersionUpdated(address indexed accountAddress, AccountAbstractionVersion aaVersion); + + function getNewAddressCreate2( + address _sender, + bytes32 _bytecodeHash, + bytes32 _salt, + bytes calldata _input + ) external view returns (address newAddress); + + function getNewAddressCreate(address _sender, uint256 _senderNonce) external pure returns (address newAddress); + + function create2( + bytes32 _salt, + bytes32 _bytecodeHash, + bytes calldata _input + ) external payable returns (address newAddress); + + function create2Account( + bytes32 _salt, + bytes32 _bytecodeHash, + bytes calldata _input, + AccountAbstractionVersion _aaVersion + ) external payable returns (address newAddress); + + /// @dev While the `_salt` parameter is not used anywhere here, + /// it is still needed for consistency between `create` and + /// `create2` functions (required by the compiler). + function create( + bytes32 _salt, + bytes32 _bytecodeHash, + bytes calldata _input + ) external payable returns (address newAddress); + + /// @dev While `_salt` is never used here, we leave it here as a parameter + /// for the consistency with the `create` function. + function createAccount( + bytes32 _salt, + bytes32 _bytecodeHash, + bytes calldata _input, + AccountAbstractionVersion _aaVersion + ) external payable returns (address newAddress); + + /// @notice Returns the information about a certain AA. + function getAccountInfo(address _address) external view returns (AccountInfo memory info); + + /// @notice Can be called by an account to update its account version + function updateAccountVersion(AccountAbstractionVersion _version) external; + + /// @notice Can be called by an account to update its nonce ordering + function updateNonceOrdering(AccountNonceOrdering _nonceOrdering) external; +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IEthToken.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IEthToken.sol new file mode 100644 index 00000000..ec9b399f --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IEthToken.sol @@ -0,0 +1,36 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +interface IEthToken { + function balanceOf(uint256) external view returns (uint256); + + function transferFromTo(address _from, address _to, uint256 _amount) external; + + function totalSupply() external view returns (uint256); + + function name() external pure returns (string memory); + + function symbol() external pure returns (string memory); + + function decimals() external pure returns (uint8); + + function mint(address _account, uint256 _amount) external; + + function withdraw(address _l1Receiver) external payable; + + function withdrawWithMessage(address _l1Receiver, bytes calldata _additionalData) external payable; + + event Mint(address indexed account, uint256 amount); + + event Transfer(address indexed from, address indexed to, uint256 value); + + event Withdrawal(address indexed _l2Sender, address indexed _l1Receiver, uint256 _amount); + + event WithdrawalWithMessage( + address indexed _l2Sender, + address indexed _l1Receiver, + uint256 _amount, + bytes _additionalData + ); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IImmutableSimulator.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IImmutableSimulator.sol new file mode 100644 index 00000000..d30ac9b9 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IImmutableSimulator.sol @@ -0,0 +1,14 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +struct ImmutableData { + uint256 index; + bytes32 value; +} + +interface IImmutableSimulator { + function getImmutable(address _dest, uint256 _index) external view returns (bytes32); + + function setImmutables(address _dest, ImmutableData[] calldata _immutables) external; +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IKnownCodesStorage.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IKnownCodesStorage.sol new file mode 100644 index 00000000..b5a783ba --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IKnownCodesStorage.sol @@ -0,0 +1,13 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +interface IKnownCodesStorage { + event MarkedAsKnown(bytes32 indexed bytecodeHash, bool indexed sendBytecodeToL1); + + function markFactoryDeps(bool _shouldSendToL1, bytes32[] calldata _hashes) external; + + function markBytecodeAsPublished(bytes32 _bytecodeHash) external; + + function getMarker(bytes32 _hash) external view returns (uint256); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IL1Messenger.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IL1Messenger.sol new file mode 100644 index 00000000..ab6a670f --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IL1Messenger.sol @@ -0,0 +1,50 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +/// @dev The log passed from L2 +/// @param l2ShardId The shard identifier, 0 - rollup, 1 - porter. All other values are not used but are reserved for the future +/// @param isService A boolean flag that is part of the log along with `key`, `value`, and `sender` address. +/// This field is required formally but does not have any special meaning. +/// @param txNumberInBlock The L2 transaction number in a block, in which the log was sent +/// @param sender The L2 address which sent the log +/// @param key The 32 bytes of information that was sent in the log +/// @param value The 32 bytes of information that was sent in the log +// Both `key` and `value` are arbitrary 32-bytes selected by the log sender +struct L2ToL1Log { + uint8 l2ShardId; + bool isService; + uint16 txNumberInBlock; + address sender; + bytes32 key; + bytes32 value; +} + +/// @dev Bytes in raw L2 to L1 log +/// @dev Equal to the bytes size of the tuple - (uint8 ShardId, bool isService, uint16 txNumberInBlock, address sender, bytes32 key, bytes32 value) +uint256 constant L2_TO_L1_LOG_SERIALIZE_SIZE = 88; + +/// @dev The value of default leaf hash for L2 to L1 logs Merkle tree +/// @dev An incomplete fixed-size tree is filled with this value to be a full binary tree +/// @dev Actually equal to the `keccak256(new bytes(L2_TO_L1_LOG_SERIALIZE_SIZE))` +bytes32 constant L2_L1_LOGS_TREE_DEFAULT_LEAF_HASH = 0x72abee45b59e344af8a6e520241c4744aff26ed411f4c4b00f8af09adada43ba; + +/// @dev The current version of state diff compression being used. +uint256 constant STATE_DIFF_COMPRESSION_VERSION_NUMBER = 1; + +interface IL1Messenger { + // Possibly in the future we will be able to track the messages sent to L1 with + // some hooks in the VM. For now, it is much easier to track them with L2 events. + event L1MessageSent(address indexed _sender, bytes32 indexed _hash, bytes _message); + + event L2ToL1LogSent(L2ToL1Log _l2log); + + event BytecodeL1PublicationRequested(bytes32 _bytecodeHash); + + function sendToL1(bytes memory _message) external returns (bytes32); + + function sendL2ToL1Log(bool _isService, bytes32 _key, bytes32 _value) external returns (uint256 logIdInMerkleTree); + + // This function is expected to be called only by the KnownCodesStorage system contract + function requestBytecodeL1Publication(bytes32 _bytecodeHash) external; +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IL2StandardToken.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IL2StandardToken.sol new file mode 100644 index 00000000..3d75c8ed --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IL2StandardToken.sol @@ -0,0 +1,17 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +interface IL2StandardToken { + event BridgeMint(address indexed _account, uint256 _amount); + + event BridgeBurn(address indexed _account, uint256 _amount); + + function bridgeMint(address _account, uint256 _amount) external; + + function bridgeBurn(address _account, uint256 _amount) external; + + function l1Address() external view returns (address); + + function l2Bridge() external view returns (address); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IMailbox.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IMailbox.sol new file mode 100644 index 00000000..ba673058 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IMailbox.sol @@ -0,0 +1,13 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +interface IMailbox { + function finalizeEthWithdrawal( + uint256 _l2BatchNumber, + uint256 _l2MessageIndex, + uint16 _l2TxNumberInBlock, + bytes calldata _message, + bytes32[] calldata _merkleProof + ) external; +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/INonceHolder.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/INonceHolder.sol new file mode 100644 index 00000000..1213fbea --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/INonceHolder.sol @@ -0,0 +1,47 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +/** + * @author Matter Labs + * @dev Interface of the nonce holder contract -- a contract used by the system to ensure + * that there is always a unique identifier for a transaction with a particular account (we call it nonce). + * In other words, the pair of (address, nonce) should always be unique. + * @dev Custom accounts should use methods of this contract to store nonces or other possible unique identifiers + * for the transaction. + */ +interface INonceHolder { + event ValueSetUnderNonce(address indexed accountAddress, uint256 indexed key, uint256 value); + + /// @dev Returns the current minimal nonce for account. + function getMinNonce(address _address) external view returns (uint256); + + /// @dev Returns the raw version of the current minimal nonce + /// (equal to minNonce + 2^128 * deployment nonce). + function getRawNonce(address _address) external view returns (uint256); + + /// @dev Increases the minimal nonce for the msg.sender. + function increaseMinNonce(uint256 _value) external returns (uint256); + + /// @dev Sets the nonce value `key` as used. + function setValueUnderNonce(uint256 _key, uint256 _value) external; + + /// @dev Gets the value stored inside a custom nonce. + function getValueUnderNonce(uint256 _key) external view returns (uint256); + + /// @dev A convenience method to increment the minimal nonce if it is equal + /// to the `_expectedNonce`. + function incrementMinNonceIfEquals(uint256 _expectedNonce) external; + + /// @dev Returns the deployment nonce for the accounts used for CREATE opcode. + function getDeploymentNonce(address _address) external view returns (uint256); + + /// @dev Increments the deployment nonce for the account and returns the previous one. + function incrementDeploymentNonce(address _address) external returns (uint256); + + /// @dev Determines whether a certain nonce has been already used for an account. + function validateNonceUsage(address _address, uint256 _key, bool _shouldBeUsed) external view; + + /// @dev Returns whether a nonce has been used for an account. + function isNonceUsed(address _address, uint256 _nonce) external view returns (bool); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IPaymaster.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IPaymaster.sol new file mode 100644 index 00000000..928f19ed --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IPaymaster.sol @@ -0,0 +1,51 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "../libraries/TransactionHelper.sol"; + +enum ExecutionResult { + Revert, + Success +} + +bytes4 constant PAYMASTER_VALIDATION_SUCCESS_MAGIC = IPaymaster.validateAndPayForPaymasterTransaction.selector; + +interface IPaymaster { + /// @dev Called by the bootloader to verify that the paymaster agrees to pay for the + /// fee for the transaction. This transaction should also send the necessary amount of funds onto the bootloader + /// address. + /// @param _txHash The hash of the transaction + /// @param _suggestedSignedHash The hash of the transaction that is signed by an EOA + /// @param _transaction The transaction itself. + /// @return magic The value that should be equal to the signature of the validateAndPayForPaymasterTransaction + /// if the paymaster agrees to pay for the transaction. + /// @return context The "context" of the transaction: an array of bytes of length at most 1024 bytes, which will be + /// passed to the `postTransaction` method of the account. + /// @dev The developer should strive to preserve as many steps as possible both for valid + /// and invalid transactions as this very method is also used during the gas fee estimation + /// (without some of the necessary data, e.g. signature). + function validateAndPayForPaymasterTransaction( + bytes32 _txHash, + bytes32 _suggestedSignedHash, + Transaction calldata _transaction + ) external payable returns (bytes4 magic, bytes memory context); + + /// @dev Called by the bootloader after the execution of the transaction. Please note that + /// there is no guarantee that this method will be called at all. Unlike the original EIP4337, + /// this method won't be called if the transaction execution results in out-of-gas. + /// @param _context, the context of the execution, returned by the "validateAndPayForPaymasterTransaction" method. + /// @param _transaction, the users' transaction. + /// @param _txResult, the result of the transaction execution (success or failure). + /// @param _maxRefundedGas, the upper bound on the amout of gas that could be refunded to the paymaster. + /// @dev The exact amount refunded depends on the gas spent by the "postOp" itself and so the developers should + /// take that into account. + function postTransaction( + bytes calldata _context, + Transaction calldata _transaction, + bytes32 _txHash, + bytes32 _suggestedSignedHash, + ExecutionResult _txResult, + uint256 _maxRefundedGas + ) external payable; +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/IPaymasterFlow.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IPaymasterFlow.sol new file mode 100644 index 00000000..59352f23 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/IPaymasterFlow.sol @@ -0,0 +1,16 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +/** + * @author Matter Labs + * @dev The interface that is used for encoding/decoding of + * different types of paymaster flows. + * @notice This is NOT an interface to be implementated + * by contracts. It is just used for encoding. + */ +interface IPaymasterFlow { + function general(bytes calldata input) external; + + function approvalBased(address _token, uint256 _minAllowance, bytes calldata _innerInput) external; +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/ISystemContext.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/ISystemContext.sol new file mode 100644 index 00000000..d8a98292 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/ISystemContext.sol @@ -0,0 +1,56 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +/** + * @author Matter Labs + * @notice Contract that stores some of the context variables, that may be either + * block-scoped, tx-scoped or system-wide. + */ +interface ISystemContext { + struct BlockInfo { + uint128 timestamp; + uint128 number; + } + + /// @notice A structure representing the timeline for the upgrade from the batch numbers to the L2 block numbers. + /// @dev It will used for the L1 batch -> L2 block migration in Q3 2023 only. + struct VirtualBlockUpgradeInfo { + /// @notice In order to maintain consistent results for `blockhash` requests, we'll + /// have to remember the number of the batch when the upgrade to the virtual blocks has been done. + /// The hashes for virtual blocks before the upgrade are identical to the hashes of the corresponding batches. + uint128 virtualBlockStartBatch; + /// @notice L2 block when the virtual blocks have caught up with the L2 blocks. Starting from this block, + /// all the information returned to users for block.timestamp/number, etc should be the information about the L2 blocks and + /// not virtual blocks. + uint128 virtualBlockFinishL2Block; + } + + function chainId() external view returns (uint256); + + function origin() external view returns (address); + + function gasPrice() external view returns (uint256); + + function blockGasLimit() external view returns (uint256); + + function coinbase() external view returns (address); + + function difficulty() external view returns (uint256); + + function baseFee() external view returns (uint256); + + function txNumberInBlock() external view returns (uint16); + + function getBlockHashEVM(uint256 _block) external view returns (bytes32); + + function getBatchHash(uint256 _batchNumber) external view returns (bytes32 hash); + + function getBlockNumber() external view returns (uint128); + + function getBlockTimestamp() external view returns (uint128); + + function getBatchNumberAndTimestamp() external view returns (uint128 blockNumber, uint128 blockTimestamp); + + function getL2BlockNumberAndTimestamp() external view returns (uint128 blockNumber, uint128 blockTimestamp); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/ISystemContextDeprecated.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/ISystemContextDeprecated.sol new file mode 100644 index 00000000..b51faeed --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/ISystemContextDeprecated.sol @@ -0,0 +1,15 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +/** + * @author Matter Labs + * @notice The interface with deprecated functions of the SystemContext contract. It is aimed for backward compatibility. + */ +interface ISystemContextDeprecated { + function currentBlockInfo() external view returns (uint256); + + function getBlockNumberAndTimestamp() external view returns (uint256 blockNumber, uint256 blockTimestamp); + + function blockHash(uint256 _blockNumber) external view returns (bytes32 hash); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/interfaces/ISystemContract.sol b/.test-node-subtree/etc/system-contracts/contracts/interfaces/ISystemContract.sol new file mode 100644 index 00000000..c486abc9 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/interfaces/ISystemContract.sol @@ -0,0 +1,46 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {SystemContractHelper} from "../libraries/SystemContractHelper.sol"; +import {BOOTLOADER_FORMAL_ADDRESS} from "../Constants.sol"; + +/// @dev Solidity does not allow exporting modifiers via libraries, so +/// the only way to do reuse modifiers is to have a base contract +/// @dev Never add storage variables into this contract as some +/// system contracts rely on this abstract contract as on interface! +abstract contract ISystemContract { + /// @notice Modifier that makes sure that the method + /// can only be called via a system call. + modifier onlySystemCall() { + require( + SystemContractHelper.isSystemCall() || SystemContractHelper.isSystemContract(msg.sender), + "This method require system call flag" + ); + _; + } + + /// @notice Modifier that makes sure that the method + /// can only be called from a system contract. + modifier onlyCallFromSystemContract() { + require( + SystemContractHelper.isSystemContract(msg.sender), + "This method require the caller to be system contract" + ); + _; + } + + /// @notice Modifier that makes sure that the method + /// can only be called from a special given address. + modifier onlyCallFrom(address caller) { + require(msg.sender == caller, "Inappropriate caller"); + _; + } + + /// @notice Modifier that makes sure that the method + /// can only be called from the bootloader. + modifier onlyCallFromBootloader() { + require(msg.sender == BOOTLOADER_FORMAL_ADDRESS, "Callable only by the bootloader"); + _; + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/libraries/EfficientCall.sol b/.test-node-subtree/etc/system-contracts/contracts/libraries/EfficientCall.sol new file mode 100644 index 00000000..22801d6f --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/libraries/EfficientCall.sol @@ -0,0 +1,275 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "./SystemContractHelper.sol"; +import "./Utils.sol"; +import {SHA256_SYSTEM_CONTRACT, KECCAK256_SYSTEM_CONTRACT, MSG_VALUE_SYSTEM_CONTRACT} from "../Constants.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice This library is used to perform ultra-efficient calls using zkEVM-specific features. + * @dev EVM calls always accept a memory slice as input and return a memory slice as output. + * Therefore, even if the user has a ready-made calldata slice, they still need to copy it to memory + * before calling. This is especially inefficient for large inputs (proxies, multi-calls, etc.). + * In turn, zkEVM operates over a fat pointer, which is a set of (memory page, offset, start, length) in the memory/calldata/returndata. + * This allows forwarding the calldata slice as is, without copying it to memory. + * @dev Fat pointer is not just an integer, it is an extended data type supported on the VM level. + * zkEVM creates the wellformed fat pointers for all the calldata/returndata regions, later + * the contract may manipulate the already created fat pointers to forward a slice of the data, but not + * to create new fat pointers! + * @dev The allowed operation on fat pointers are: + * 1. `ptr.add` - Transforms `ptr.offset` into `ptr.offset + u32(_value)`. If overflow happens then it panics. + * 2. `ptr.sub` - Transforms `ptr.offset` into `ptr.offset - u32(_value)`. If underflow happens then it panics. + * 3. `ptr.pack` - Do the concatenation between the lowest 128 bits of the pointer itself and the highest 128 bits of `_value`. It is typically used to prepare the ABI for external calls. + * 4. `ptr.shrink` - Transforms `ptr.length` into `ptr.length - u32(_shrink)`. If underflow happens then it panics. + * @dev The call opcodes accept the fat pointer and change it to its canonical form before passing it to the child call + * 1. `ptr.start` is transformed into `ptr.offset + ptr.start` + * 2. `ptr.length` is transformed into `ptr.length - ptr.offset` + * 3. `ptr.offset` is transformed into `0` + */ +library EfficientCall { + /// @notice Call the `keccak256` without copying calldata to memory. + /// @param _data The preimage data. + /// @return The `keccak256` hash. + function keccak(bytes calldata _data) internal view returns (bytes32) { + bytes memory returnData = staticCall(gasleft(), KECCAK256_SYSTEM_CONTRACT, _data); + require(returnData.length == 32, "keccak256 returned invalid data"); + return bytes32(returnData); + } + + /// @notice Call the `sha256` precompile without copying calldata to memory. + /// @param _data The preimage data. + /// @return The `sha256` hash. + function sha(bytes calldata _data) internal view returns (bytes32) { + bytes memory returnData = staticCall(gasleft(), SHA256_SYSTEM_CONTRACT, _data); + require(returnData.length == 32, "sha returned invalid data"); + return bytes32(returnData); + } + + /// @notice Perform a `call` without copying calldata to memory. + /// @param _gas The gas to use for the call. + /// @param _address The address to call. + /// @param _value The `msg.value` to send. + /// @param _data The calldata to use for the call. + /// @param _isSystem Whether the call should contain the `isSystem` flag. + /// @return returnData The copied to memory return data. + function call( + uint256 _gas, + address _address, + uint256 _value, + bytes calldata _data, + bool _isSystem + ) internal returns (bytes memory returnData) { + bool success = rawCall(_gas, _address, _value, _data, _isSystem); + returnData = _verifyCallResult(success); + } + + /// @notice Perform a `staticCall` without copying calldata to memory. + /// @param _gas The gas to use for the call. + /// @param _address The address to call. + /// @param _data The calldata to use for the call. + /// @return returnData The copied to memory return data. + function staticCall( + uint256 _gas, + address _address, + bytes calldata _data + ) internal view returns (bytes memory returnData) { + bool success = rawStaticCall(_gas, _address, _data); + returnData = _verifyCallResult(success); + } + + /// @notice Perform a `delegateCall` without copying calldata to memory. + /// @param _gas The gas to use for the call. + /// @param _address The address to call. + /// @param _data The calldata to use for the call. + /// @return returnData The copied to memory return data. + function delegateCall( + uint256 _gas, + address _address, + bytes calldata _data + ) internal returns (bytes memory returnData) { + bool success = rawDelegateCall(_gas, _address, _data); + returnData = _verifyCallResult(success); + } + + /// @notice Perform a `mimicCall` (a call with custom msg.sender) without copying calldata to memory. + /// @param _gas The gas to use for the call. + /// @param _address The address to call. + /// @param _data The calldata to use for the call. + /// @param _whoToMimic The `msg.sender` for the next call. + /// @param _isConstructor Whether the call should contain the `isConstructor` flag. + /// @param _isSystem Whether the call should contain the `isSystem` flag. + /// @return returnData The copied to memory return data. + function mimicCall( + uint256 _gas, + address _address, + bytes calldata _data, + address _whoToMimic, + bool _isConstructor, + bool _isSystem + ) internal returns (bytes memory returnData) { + bool success = rawMimicCall(_gas, _address, _data, _whoToMimic, _isConstructor, _isSystem); + returnData = _verifyCallResult(success); + } + + /// @notice Perform a `call` without copying calldata to memory. + /// @param _gas The gas to use for the call. + /// @param _address The address to call. + /// @param _value The `msg.value` to send. + /// @param _data The calldata to use for the call. + /// @param _isSystem Whether the call should contain the `isSystem` flag. + /// @return success whether the call was successful. + function rawCall( + uint256 _gas, + address _address, + uint256 _value, + bytes calldata _data, + bool _isSystem + ) internal returns (bool success) { + if (_value == 0) { + _loadFarCallABIIntoActivePtr(_gas, _data, false, _isSystem); + + address callAddr = RAW_FAR_CALL_BY_REF_CALL_ADDRESS; + assembly { + success := call(_address, callAddr, 0, 0, 0xFFFF, 0, 0) + } + } else { + _loadFarCallABIIntoActivePtr(_gas, _data, false, true); + + // If there is provided `msg.value` call the `MsgValueSimulator` to forward ether. + address msgValueSimulator = MSG_VALUE_SYSTEM_CONTRACT; + address callAddr = SYSTEM_CALL_BY_REF_CALL_ADDRESS; + // We need to supply the mask to the MsgValueSimulator to denote + // that the call should be a system one. + uint256 forwardMask = _isSystem ? MSG_VALUE_SIMULATOR_IS_SYSTEM_BIT : 0; + + assembly { + success := call(msgValueSimulator, callAddr, _value, _address, 0xFFFF, forwardMask, 0) + } + } + } + + /// @notice Perform a `staticCall` without copying calldata to memory. + /// @param _gas The gas to use for the call. + /// @param _address The address to call. + /// @param _data The calldata to use for the call. + /// @return success whether the call was successful. + function rawStaticCall(uint256 _gas, address _address, bytes calldata _data) internal view returns (bool success) { + _loadFarCallABIIntoActivePtr(_gas, _data, false, false); + + address callAddr = RAW_FAR_CALL_BY_REF_CALL_ADDRESS; + assembly { + success := staticcall(_address, callAddr, 0, 0xFFFF, 0, 0) + } + } + + /// @notice Perform a `delegatecall` without copying calldata to memory. + /// @param _gas The gas to use for the call. + /// @param _address The address to call. + /// @param _data The calldata to use for the call. + /// @return success whether the call was successful. + function rawDelegateCall(uint256 _gas, address _address, bytes calldata _data) internal returns (bool success) { + _loadFarCallABIIntoActivePtr(_gas, _data, false, false); + + address callAddr = RAW_FAR_CALL_BY_REF_CALL_ADDRESS; + assembly { + success := delegatecall(_address, callAddr, 0, 0xFFFF, 0, 0) + } + } + + /// @notice Perform a `mimicCall` (call with custom msg.sender) without copying calldata to memory. + /// @param _gas The gas to use for the call. + /// @param _address The address to call. + /// @param _data The calldata to use for the call. + /// @param _whoToMimic The `msg.sender` for the next call. + /// @param _isConstructor Whether the call should contain the `isConstructor` flag. + /// @param _isSystem Whether the call should contain the `isSystem` flag. + /// @return success whether the call was successful. + /// @dev If called not in kernel mode, it will result in a revert (enforced by the VM) + function rawMimicCall( + uint256 _gas, + address _address, + bytes calldata _data, + address _whoToMimic, + bool _isConstructor, + bool _isSystem + ) internal returns (bool success) { + _loadFarCallABIIntoActivePtr(_gas, _data, _isConstructor, _isSystem); + + address callAddr = MIMIC_CALL_BY_REF_CALL_ADDRESS; + uint256 cleanupMask = ADDRESS_MASK; + assembly { + // Clearing values before usage in assembly, since Solidity + // doesn't do it by default + _whoToMimic := and(_whoToMimic, cleanupMask) + + success := call(_address, callAddr, 0, 0, _whoToMimic, 0, 0) + } + } + + /// @dev Verify that a low-level call was successful, and revert if it wasn't, by bubbling the revert reason. + /// @param _success Whether the call was successful. + /// @return returnData The copied to memory return data. + function _verifyCallResult(bool _success) private pure returns (bytes memory returnData) { + if (_success) { + uint256 size; + assembly { + size := returndatasize() + } + + returnData = new bytes(size); + assembly { + returndatacopy(add(returnData, 0x20), 0, size) + } + } else { + propagateRevert(); + } + } + + /// @dev Propagate the revert reason from the current call to the caller. + function propagateRevert() internal pure { + assembly { + let size := returndatasize() + returndatacopy(0, 0, size) + revert(0, size) + } + } + + /// @dev Load the far call ABI into active ptr, that will be used for the next call by reference. + /// @param _gas The gas to be passed to the call. + /// @param _data The calldata to be passed to the call. + /// @param _isConstructor Whether the call is a constructor call. + /// @param _isSystem Whether the call is a system call. + function _loadFarCallABIIntoActivePtr( + uint256 _gas, + bytes calldata _data, + bool _isConstructor, + bool _isSystem + ) private view { + SystemContractHelper.loadCalldataIntoActivePtr(); + + uint256 dataOffset; + assembly { + dataOffset := _data.offset + } + + // Safe to cast, offset is never bigger than `type(uint32).max` + SystemContractHelper.ptrAddIntoActive(uint32(dataOffset)); + // Safe to cast, `data.length` is never bigger than `type(uint32).max` + uint32 shrinkTo = uint32(msg.data.length - (_data.length + dataOffset)); + SystemContractHelper.ptrShrinkIntoActive(shrinkTo); + + uint32 gas = Utils.safeCastToU32(_gas); + uint256 farCallAbi = SystemContractsCaller.getFarCallABIWithEmptyFatPointer( + gas, + // Only rollup is supported for now + 0, + CalldataForwardingMode.ForwardFatPointer, + _isConstructor, + _isSystem + ); + SystemContractHelper.ptrPackIntoActivePtr(farCallAbi); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/libraries/RLPEncoder.sol b/.test-node-subtree/etc/system-contracts/contracts/libraries/RLPEncoder.sol new file mode 100644 index 00000000..8e32ea9b --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/libraries/RLPEncoder.sol @@ -0,0 +1,107 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice This library provides RLP encoding functionality. + */ +library RLPEncoder { + function encodeAddress(address _val) internal pure returns (bytes memory encoded) { + // The size is equal to 20 bytes of the address itself + 1 for encoding bytes length in RLP. + encoded = new bytes(0x15); + + bytes20 shiftedVal = bytes20(_val); + assembly { + // In the first byte we write the encoded length as 0x80 + 0x14 == 0x94. + mstore(add(encoded, 0x20), 0x9400000000000000000000000000000000000000000000000000000000000000) + // Write address data without stripping zeros. + mstore(add(encoded, 0x21), shiftedVal) + } + } + + function encodeUint256(uint256 _val) internal pure returns (bytes memory encoded) { + unchecked { + if (_val < 128) { + encoded = new bytes(1); + // Handle zero as a non-value, since stripping zeroes results in an empty byte array + encoded[0] = (_val == 0) ? bytes1(uint8(128)) : bytes1(uint8(_val)); + } else { + uint256 hbs = _highestByteSet(_val); + + encoded = new bytes(hbs + 2); + encoded[0] = bytes1(uint8(hbs + 0x81)); + + uint256 lbs = 31 - hbs; + uint256 shiftedVal = _val << (lbs * 8); + + assembly { + mstore(add(encoded, 0x21), shiftedVal) + } + } + } + } + + /// @notice Encodes the size of bytes in RLP format. + /// @param _len The length of the bytes to encode. It has a `uint64` type since as larger values are not supported. + /// NOTE: panics if the length is 1 since the length encoding is ambiguous in this case. + function encodeNonSingleBytesLen(uint64 _len) internal pure returns (bytes memory) { + assert(_len != 1); + return _encodeLength(_len, 0x80); + } + + /// @notice Encodes the size of list items in RLP format. + /// @param _len The length of the bytes to encode. It has a `uint64` type since as larger values are not supported. + function encodeListLen(uint64 _len) internal pure returns (bytes memory) { + return _encodeLength(_len, 0xc0); + } + + function _encodeLength(uint64 _len, uint256 _offset) private pure returns (bytes memory encoded) { + unchecked { + if (_len < 56) { + encoded = new bytes(1); + encoded[0] = bytes1(uint8(_len + _offset)); + } else { + uint256 hbs = _highestByteSet(uint256(_len)); + + encoded = new bytes(hbs + 2); + encoded[0] = bytes1(uint8(_offset + hbs + 56)); + + uint256 lbs = 31 - hbs; + uint256 shiftedVal = uint256(_len) << (lbs * 8); + + assembly { + mstore(add(encoded, 0x21), shiftedVal) + } + } + } + } + + /// @notice Computes the index of the highest byte set in number. + /// @notice Uses little endian ordering (The least significant byte has index `0`). + /// NOTE: returns `0` for `0` + function _highestByteSet(uint256 _number) private pure returns (uint256 hbs) { + unchecked { + if (_number > type(uint128).max) { + _number >>= 128; + hbs += 16; + } + if (_number > type(uint64).max) { + _number >>= 64; + hbs += 8; + } + if (_number > type(uint32).max) { + _number >>= 32; + hbs += 4; + } + if (_number > type(uint16).max) { + _number >>= 16; + hbs += 2; + } + if (_number > type(uint8).max) { + hbs += 1; + } + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/libraries/SystemContractHelper.sol b/.test-node-subtree/etc/system-contracts/contracts/libraries/SystemContractHelper.sol new file mode 100644 index 00000000..a66b9670 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/libraries/SystemContractHelper.sol @@ -0,0 +1,342 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {MAX_SYSTEM_CONTRACT_ADDRESS} from "../Constants.sol"; + +import {SystemContractsCaller, CalldataForwardingMode, CALLFLAGS_CALL_ADDRESS, CODE_ADDRESS_CALL_ADDRESS, EVENT_WRITE_ADDRESS, EVENT_INITIALIZE_ADDRESS, GET_EXTRA_ABI_DATA_ADDRESS, LOAD_CALLDATA_INTO_ACTIVE_PTR_CALL_ADDRESS, META_CODE_SHARD_ID_OFFSET, META_CALLER_SHARD_ID_OFFSET, META_SHARD_ID_OFFSET, META_AUX_HEAP_SIZE_OFFSET, META_HEAP_SIZE_OFFSET, META_GAS_PER_PUBDATA_BYTE_OFFSET, MIMIC_CALL_BY_REF_CALL_ADDRESS, META_CALL_ADDRESS, MSG_VALUE_SIMULATOR_IS_SYSTEM_BIT, PTR_CALLDATA_CALL_ADDRESS, PTR_ADD_INTO_ACTIVE_CALL_ADDRESS, PTR_SHRINK_INTO_ACTIVE_CALL_ADDRESS, PTR_PACK_INTO_ACTIVE_CALL_ADDRESS, RAW_FAR_CALL_BY_REF_CALL_ADDRESS, PRECOMPILE_CALL_ADDRESS, SET_CONTEXT_VALUE_CALL_ADDRESS, SYSTEM_CALL_BY_REF_CALL_ADDRESS, TO_L1_CALL_ADDRESS} from "./SystemContractsCaller.sol"; + +uint256 constant UINT32_MASK = 0xffffffff; +uint256 constant UINT128_MASK = 0xffffffffffffffffffffffffffffffff; +/// @dev The mask that is used to convert any uint256 to a proper address. +/// It needs to be padded with `00` to be treated as uint256 by Solidity +uint256 constant ADDRESS_MASK = 0x00ffffffffffffffffffffffffffffffffffffffff; + +struct ZkSyncMeta { + uint32 gasPerPubdataByte; + uint32 heapSize; + uint32 auxHeapSize; + uint8 shardId; + uint8 callerShardId; + uint8 codeShardId; +} + +enum Global { + CalldataPtr, + CallFlags, + ExtraABIData1, + ExtraABIData2, + ReturndataPtr +} + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice Library used for accessing zkEVM-specific opcodes, needed for the development + * of system contracts. + * @dev While this library will be eventually available to public, some of the provided + * methods won't work for non-system contracts. We will not recommend this library + * for external use. + */ +library SystemContractHelper { + /// @notice Send an L2Log to L1. + /// @param _isService The `isService` flag. + /// @param _key The `key` part of the L2Log. + /// @param _value The `value` part of the L2Log. + /// @dev The meaning of all these parameters is context-dependent, but they + /// have no intrinsic meaning per se. + function toL1(bool _isService, bytes32 _key, bytes32 _value) internal { + address callAddr = TO_L1_CALL_ADDRESS; + assembly { + // Ensuring that the type is bool + _isService := and(_isService, 1) + // This `success` is always 0, but the method always succeeds + // (except for the cases when there is not enough gas) + let success := call(_isService, callAddr, _key, _value, 0xFFFF, 0, 0) + } + } + + /// @notice Get address of the currently executed code. + /// @dev This allows differentiating between `call` and `delegatecall`. + /// During the former `this` and `codeAddress` are the same, while + /// during the latter they are not. + function getCodeAddress() internal view returns (address addr) { + address callAddr = CODE_ADDRESS_CALL_ADDRESS; + assembly { + addr := staticcall(0, callAddr, 0, 0xFFFF, 0, 0) + } + } + + /// @notice Provide a compiler hint, by placing calldata fat pointer into virtual `ACTIVE_PTR`, + /// that can be manipulated by `ptr.add`/`ptr.sub`/`ptr.pack`/`ptr.shrink` later. + /// @dev This allows making a call by forwarding calldata pointer to the child call. + /// It is a much more efficient way to forward calldata, than standard EVM bytes copying. + function loadCalldataIntoActivePtr() internal view { + address callAddr = LOAD_CALLDATA_INTO_ACTIVE_PTR_CALL_ADDRESS; + assembly { + pop(staticcall(0, callAddr, 0, 0xFFFF, 0, 0)) + } + } + + /// @notice Compiler simulation of the `ptr.pack` opcode for the virtual `ACTIVE_PTR` pointer. + /// @dev Do the concatenation between lowest part of `ACTIVE_PTR` and highest part of `_farCallAbi` + /// forming packed fat pointer for a far call or ret ABI when necessary. + /// Note: Panics if the lowest 128 bits of `_farCallAbi` are not zeroes. + function ptrPackIntoActivePtr(uint256 _farCallAbi) internal view { + address callAddr = PTR_PACK_INTO_ACTIVE_CALL_ADDRESS; + assembly { + pop(staticcall(_farCallAbi, callAddr, 0, 0xFFFF, 0, 0)) + } + } + + /// @notice Compiler simulation of the `ptr.add` opcode for the virtual `ACTIVE_PTR` pointer. + /// @dev Transforms `ACTIVE_PTR.offset` into `ACTIVE_PTR.offset + u32(_value)`. If overflow happens then it panics. + function ptrAddIntoActive(uint32 _value) internal view { + address callAddr = PTR_ADD_INTO_ACTIVE_CALL_ADDRESS; + uint256 cleanupMask = UINT32_MASK; + assembly { + // Clearing input params as they are not cleaned by Solidity by default + _value := and(_value, cleanupMask) + pop(staticcall(_value, callAddr, 0, 0xFFFF, 0, 0)) + } + } + + /// @notice Compiler simulation of the `ptr.shrink` opcode for the virtual `ACTIVE_PTR` pointer. + /// @dev Transforms `ACTIVE_PTR.length` into `ACTIVE_PTR.length - u32(_shrink)`. If underflow happens then it panics. + function ptrShrinkIntoActive(uint32 _shrink) internal view { + address callAddr = PTR_SHRINK_INTO_ACTIVE_CALL_ADDRESS; + uint256 cleanupMask = UINT32_MASK; + assembly { + // Clearing input params as they are not cleaned by Solidity by default + _shrink := and(_shrink, cleanupMask) + pop(staticcall(_shrink, callAddr, 0, 0xFFFF, 0, 0)) + } + } + + /// @notice packs precompile parameters into one word + /// @param _inputMemoryOffset The memory offset in 32-byte words for the input data for calling the precompile. + /// @param _inputMemoryLength The length of the input data in words. + /// @param _outputMemoryOffset The memory offset in 32-byte words for the output data. + /// @param _outputMemoryLength The length of the output data in words. + /// @param _perPrecompileInterpreted The constant, the meaning of which is defined separately for + /// each precompile. For information, please read the documentation of the precompilecall log in + /// the VM. + function packPrecompileParams( + uint32 _inputMemoryOffset, + uint32 _inputMemoryLength, + uint32 _outputMemoryOffset, + uint32 _outputMemoryLength, + uint64 _perPrecompileInterpreted + ) internal pure returns (uint256 rawParams) { + rawParams = _inputMemoryOffset; + rawParams |= uint256(_inputMemoryLength) << 32; + rawParams |= uint256(_outputMemoryOffset) << 64; + rawParams |= uint256(_outputMemoryLength) << 96; + rawParams |= uint256(_perPrecompileInterpreted) << 192; + } + + /// @notice Call precompile with given parameters. + /// @param _rawParams The packed precompile params. They can be retrieved by + /// the `packPrecompileParams` method. + /// @param _gasToBurn The number of gas to burn during this call. + /// @return success Whether the call was successful. + /// @dev The list of currently available precompiles sha256, keccak256, ecrecover. + /// NOTE: The precompile type depends on `this` which calls precompile, which means that only + /// system contracts corresponding to the list of precompiles above can do `precompileCall`. + /// @dev If used not in the `sha256`, `keccak256` or `ecrecover` contracts, it will just burn the gas provided. + /// @dev This method is `unsafe` because it does not check whether there is enough gas to burn. + function unsafePrecompileCall(uint256 _rawParams, uint32 _gasToBurn) internal view returns (bool success) { + address callAddr = PRECOMPILE_CALL_ADDRESS; + + uint256 cleanupMask = UINT32_MASK; + assembly { + // Clearing input params as they are not cleaned by Solidity by default + _gasToBurn := and(_gasToBurn, cleanupMask) + success := staticcall(_rawParams, callAddr, _gasToBurn, 0xFFFF, 0, 0) + } + } + + /// @notice Set `msg.value` to next far call. + /// @param _value The msg.value that will be used for the *next* call. + /// @dev If called not in kernel mode, it will result in a revert (enforced by the VM) + function setValueForNextFarCall(uint128 _value) internal returns (bool success) { + uint256 cleanupMask = UINT128_MASK; + address callAddr = SET_CONTEXT_VALUE_CALL_ADDRESS; + assembly { + // Clearing input params as they are not cleaned by Solidity by default + _value := and(_value, cleanupMask) + success := call(0, callAddr, _value, 0, 0xFFFF, 0, 0) + } + } + + /// @notice Initialize a new event. + /// @param initializer The event initializing value. + /// @param value1 The first topic or data chunk. + function eventInitialize(uint256 initializer, uint256 value1) internal { + address callAddr = EVENT_INITIALIZE_ADDRESS; + assembly { + pop(call(initializer, callAddr, value1, 0, 0xFFFF, 0, 0)) + } + } + + /// @notice Continue writing the previously initialized event. + /// @param value1 The first topic or data chunk. + /// @param value2 The second topic or data chunk. + function eventWrite(uint256 value1, uint256 value2) internal { + address callAddr = EVENT_WRITE_ADDRESS; + assembly { + pop(call(value1, callAddr, value2, 0, 0xFFFF, 0, 0)) + } + } + + /// @notice Get the packed representation of the `ZkSyncMeta` from the current context. + /// @return meta The packed representation of the ZkSyncMeta. + /// @dev The fields in ZkSyncMeta are NOT tightly packed, i.e. there is a special rule on how + /// they are packed. For more information, please read the documentation on ZkSyncMeta. + function getZkSyncMetaBytes() internal view returns (uint256 meta) { + address callAddr = META_CALL_ADDRESS; + assembly { + meta := staticcall(0, callAddr, 0, 0xFFFF, 0, 0) + } + } + + /// @notice Returns the bits [offset..offset+size-1] of the meta. + /// @param meta Packed representation of the ZkSyncMeta. + /// @param offset The offset of the bits. + /// @param size The size of the extracted number in bits. + /// @return result The extracted number. + function extractNumberFromMeta(uint256 meta, uint256 offset, uint256 size) internal pure returns (uint256 result) { + // Firstly, we delete all the bits after the field + uint256 shifted = (meta << (256 - size - offset)); + // Then we shift everything back + result = (shifted >> (256 - size)); + } + + /// @notice Given the packed representation of `ZkSyncMeta`, retrieves the number of gas + /// that a single byte sent to L1 as pubdata costs. + /// @param meta Packed representation of the ZkSyncMeta. + /// @return gasPerPubdataByte The current price in gas per pubdata byte. + function getGasPerPubdataByteFromMeta(uint256 meta) internal pure returns (uint32 gasPerPubdataByte) { + gasPerPubdataByte = uint32(extractNumberFromMeta(meta, META_GAS_PER_PUBDATA_BYTE_OFFSET, 32)); + } + + /// @notice Given the packed representation of `ZkSyncMeta`, retrieves the number of the current size + /// of the heap in bytes. + /// @param meta Packed representation of the ZkSyncMeta. + /// @return heapSize The size of the memory in bytes byte. + /// @dev The following expression: getHeapSizeFromMeta(getZkSyncMetaBytes()) is + /// equivalent to the MSIZE in Solidity. + function getHeapSizeFromMeta(uint256 meta) internal pure returns (uint32 heapSize) { + heapSize = uint32(extractNumberFromMeta(meta, META_HEAP_SIZE_OFFSET, 32)); + } + + /// @notice Given the packed representation of `ZkSyncMeta`, retrieves the number of the current size + /// of the auxilary heap in bytes. + /// @param meta Packed representation of the ZkSyncMeta. + /// @return auxHeapSize The size of the auxilary memory in bytes byte. + /// @dev You can read more on auxilary memory in the VM1.2 documentation. + function getAuxHeapSizeFromMeta(uint256 meta) internal pure returns (uint32 auxHeapSize) { + auxHeapSize = uint32(extractNumberFromMeta(meta, META_AUX_HEAP_SIZE_OFFSET, 32)); + } + + /// @notice Given the packed representation of `ZkSyncMeta`, retrieves the shardId of `this`. + /// @param meta Packed representation of the ZkSyncMeta. + /// @return shardId The shardId of `this`. + /// @dev Currently only shard 0 (zkRollup) is supported. + function getShardIdFromMeta(uint256 meta) internal pure returns (uint8 shardId) { + shardId = uint8(extractNumberFromMeta(meta, META_SHARD_ID_OFFSET, 8)); + } + + /// @notice Given the packed representation of `ZkSyncMeta`, retrieves the shardId of + /// the msg.sender. + /// @param meta Packed representation of the ZkSyncMeta. + /// @return callerShardId The shardId of the msg.sender. + /// @dev Currently only shard 0 (zkRollup) is supported. + function getCallerShardIdFromMeta(uint256 meta) internal pure returns (uint8 callerShardId) { + callerShardId = uint8(extractNumberFromMeta(meta, META_CALLER_SHARD_ID_OFFSET, 8)); + } + + /// @notice Given the packed representation of `ZkSyncMeta`, retrieves the shardId of + /// the currently executed code. + /// @param meta Packed representation of the ZkSyncMeta. + /// @return codeShardId The shardId of the currently executed code. + /// @dev Currently only shard 0 (zkRollup) is supported. + function getCodeShardIdFromMeta(uint256 meta) internal pure returns (uint8 codeShardId) { + codeShardId = uint8(extractNumberFromMeta(meta, META_CODE_SHARD_ID_OFFSET, 8)); + } + + /// @notice Retrieves the ZkSyncMeta structure. + /// @return meta The ZkSyncMeta execution context parameters. + function getZkSyncMeta() internal view returns (ZkSyncMeta memory meta) { + uint256 metaPacked = getZkSyncMetaBytes(); + meta.gasPerPubdataByte = getGasPerPubdataByteFromMeta(metaPacked); + meta.heapSize = getHeapSizeFromMeta(metaPacked); + meta.auxHeapSize = getAuxHeapSizeFromMeta(metaPacked); + meta.shardId = getShardIdFromMeta(metaPacked); + meta.callerShardId = getCallerShardIdFromMeta(metaPacked); + meta.codeShardId = getCodeShardIdFromMeta(metaPacked); + } + + /// @notice Returns the call flags for the current call. + /// @return callFlags The bitmask of the callflags. + /// @dev Call flags is the value of the first register + /// at the start of the call. + /// @dev The zero bit of the callFlags indicates whether the call is + /// a constructor call. The first bit of the callFlags indicates whether + /// the call is a system one. + function getCallFlags() internal view returns (uint256 callFlags) { + address callAddr = CALLFLAGS_CALL_ADDRESS; + assembly { + callFlags := staticcall(0, callAddr, 0, 0xFFFF, 0, 0) + } + } + + /// @notice Returns the current calldata pointer. + /// @return ptr The current calldata pointer. + /// @dev NOTE: This file is just an integer and it cannot be used + /// to forward the calldata to the next calls in any way. + function getCalldataPtr() internal view returns (uint256 ptr) { + address callAddr = PTR_CALLDATA_CALL_ADDRESS; + assembly { + ptr := staticcall(0, callAddr, 0, 0xFFFF, 0, 0) + } + } + + /// @notice Returns the N-th extraAbiParam for the current call. + /// @return extraAbiData The value of the N-th extraAbiParam for this call. + /// @dev It is equal to the value of the (N+2)-th register + /// at the start of the call. + function getExtraAbiData(uint256 index) internal view returns (uint256 extraAbiData) { + require(index < 10, "There are only 10 accessible registers"); + + address callAddr = GET_EXTRA_ABI_DATA_ADDRESS; + assembly { + extraAbiData := staticcall(index, callAddr, 0, 0xFFFF, 0, 0) + } + } + + /// @notice Retuns whether the current call is a system call. + /// @return `true` or `false` based on whether the current call is a system call. + function isSystemCall() internal view returns (bool) { + uint256 callFlags = getCallFlags(); + // When the system call is passed, the 2-bit it set to 1 + return (callFlags & 2) != 0; + } + + /// @notice Returns whether the address is a system contract. + /// @param _address The address to test + /// @return `true` or `false` based on whether the `_address` is a system contract. + function isSystemContract(address _address) internal pure returns (bool) { + return uint160(_address) <= uint160(MAX_SYSTEM_CONTRACT_ADDRESS); + } + + /// @notice Method used for burning a certain amount of gas. + /// @param _gasToPay The number of gas to burn. + function burnGas(uint32 _gasToPay) internal view { + bool precompileCallSuccess = unsafePrecompileCall( + 0, // The precompile parameters are formal ones. We only need the precompile call to burn gas. + _gasToPay + ); + require(precompileCallSuccess, "Failed to charge gas"); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/libraries/SystemContractsCaller.sol b/.test-node-subtree/etc/system-contracts/contracts/libraries/SystemContractsCaller.sol new file mode 100644 index 00000000..7be17992 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/libraries/SystemContractsCaller.sol @@ -0,0 +1,267 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {MSG_VALUE_SYSTEM_CONTRACT, MSG_VALUE_SIMULATOR_IS_SYSTEM_BIT} from "../Constants.sol"; +import "./Utils.sol"; + +// Addresses used for the compiler to be replaced with the +// zkSync-specific opcodes during the compilation. +// IMPORTANT: these are just compile-time constants and are used +// only if used in-place by Yul optimizer. +address constant TO_L1_CALL_ADDRESS = address((1 << 16) - 1); +address constant CODE_ADDRESS_CALL_ADDRESS = address((1 << 16) - 2); +address constant PRECOMPILE_CALL_ADDRESS = address((1 << 16) - 3); +address constant META_CALL_ADDRESS = address((1 << 16) - 4); +address constant MIMIC_CALL_CALL_ADDRESS = address((1 << 16) - 5); +address constant SYSTEM_MIMIC_CALL_CALL_ADDRESS = address((1 << 16) - 6); +address constant MIMIC_CALL_BY_REF_CALL_ADDRESS = address((1 << 16) - 7); +address constant SYSTEM_MIMIC_CALL_BY_REF_CALL_ADDRESS = address((1 << 16) - 8); +address constant RAW_FAR_CALL_CALL_ADDRESS = address((1 << 16) - 9); +address constant RAW_FAR_CALL_BY_REF_CALL_ADDRESS = address((1 << 16) - 10); +address constant SYSTEM_CALL_CALL_ADDRESS = address((1 << 16) - 11); +address constant SYSTEM_CALL_BY_REF_CALL_ADDRESS = address((1 << 16) - 12); +address constant SET_CONTEXT_VALUE_CALL_ADDRESS = address((1 << 16) - 13); +address constant SET_PUBDATA_PRICE_CALL_ADDRESS = address((1 << 16) - 14); +address constant INCREMENT_TX_COUNTER_CALL_ADDRESS = address((1 << 16) - 15); +address constant PTR_CALLDATA_CALL_ADDRESS = address((1 << 16) - 16); +address constant CALLFLAGS_CALL_ADDRESS = address((1 << 16) - 17); +address constant PTR_RETURNDATA_CALL_ADDRESS = address((1 << 16) - 18); +address constant EVENT_INITIALIZE_ADDRESS = address((1 << 16) - 19); +address constant EVENT_WRITE_ADDRESS = address((1 << 16) - 20); +address constant LOAD_CALLDATA_INTO_ACTIVE_PTR_CALL_ADDRESS = address((1 << 16) - 21); +address constant LOAD_LATEST_RETURNDATA_INTO_ACTIVE_PTR_CALL_ADDRESS = address((1 << 16) - 22); +address constant PTR_ADD_INTO_ACTIVE_CALL_ADDRESS = address((1 << 16) - 23); +address constant PTR_SHRINK_INTO_ACTIVE_CALL_ADDRESS = address((1 << 16) - 24); +address constant PTR_PACK_INTO_ACTIVE_CALL_ADDRESS = address((1 << 16) - 25); +address constant MULTIPLICATION_HIGH_ADDRESS = address((1 << 16) - 26); +address constant GET_EXTRA_ABI_DATA_ADDRESS = address((1 << 16) - 27); + +// All the offsets are in bits +uint256 constant META_GAS_PER_PUBDATA_BYTE_OFFSET = 0 * 8; +uint256 constant META_HEAP_SIZE_OFFSET = 8 * 8; +uint256 constant META_AUX_HEAP_SIZE_OFFSET = 12 * 8; +uint256 constant META_SHARD_ID_OFFSET = 28 * 8; +uint256 constant META_CALLER_SHARD_ID_OFFSET = 29 * 8; +uint256 constant META_CODE_SHARD_ID_OFFSET = 30 * 8; + +/// @notice The way to forward the calldata: +/// - Use the current heap (i.e. the same as on EVM). +/// - Use the auxiliary heap. +/// - Forward via a pointer +/// @dev Note, that currently, users do not have access to the auxiliary +/// heap and so the only type of forwarding that will be used by the users +/// are UseHeap and ForwardFatPointer for forwarding a slice of the current calldata +/// to the next call. +enum CalldataForwardingMode { + UseHeap, + ForwardFatPointer, + UseAuxHeap +} + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice A library that allows calling contracts with the `isSystem` flag. + * @dev It is needed to call ContractDeployer and NonceHolder. + */ +library SystemContractsCaller { + /// @notice Makes a call with the `isSystem` flag. + /// @param gasLimit The gas limit for the call. + /// @param to The address to call. + /// @param value The value to pass with the transaction. + /// @param data The calldata. + /// @return success Whether the transaction has been successful. + /// @dev Note, that the `isSystem` flag can only be set when calling system contracts. + function systemCall(uint32 gasLimit, address to, uint256 value, bytes memory data) internal returns (bool success) { + address callAddr = SYSTEM_CALL_CALL_ADDRESS; + + uint32 dataStart; + assembly { + dataStart := add(data, 0x20) + } + uint32 dataLength = uint32(Utils.safeCastToU32(data.length)); + + uint256 farCallAbi = SystemContractsCaller.getFarCallABI( + 0, + 0, + dataStart, + dataLength, + gasLimit, + // Only rollup is supported for now + 0, + CalldataForwardingMode.UseHeap, + false, + true + ); + + if (value == 0) { + // Doing the system call directly + assembly { + success := call(to, callAddr, 0, 0, farCallAbi, 0, 0) + } + } else { + address msgValueSimulator = MSG_VALUE_SYSTEM_CONTRACT; + // We need to supply the mask to the MsgValueSimulator to denote + // that the call should be a system one. + uint256 forwardMask = MSG_VALUE_SIMULATOR_IS_SYSTEM_BIT; + + assembly { + success := call(msgValueSimulator, callAddr, value, to, farCallAbi, forwardMask, 0) + } + } + } + + /// @notice Makes a call with the `isSystem` flag. + /// @param gasLimit The gas limit for the call. + /// @param to The address to call. + /// @param value The value to pass with the transaction. + /// @param data The calldata. + /// @return success Whether the transaction has been successful. + /// @return returnData The returndata of the transaction (revert reason in case the transaction has failed). + /// @dev Note, that the `isSystem` flag can only be set when calling system contracts. + function systemCallWithReturndata( + uint32 gasLimit, + address to, + uint128 value, + bytes memory data + ) internal returns (bool success, bytes memory returnData) { + success = systemCall(gasLimit, to, value, data); + + uint256 size; + assembly { + size := returndatasize() + } + + returnData = new bytes(size); + assembly { + returndatacopy(add(returnData, 0x20), 0, size) + } + } + + /// @notice Makes a call with the `isSystem` flag. + /// @param gasLimit The gas limit for the call. + /// @param to The address to call. + /// @param value The value to pass with the transaction. + /// @param data The calldata. + /// @return returnData The returndata of the transaction. In case the transaction reverts, the error + /// bubbles up to the parent frame. + /// @dev Note, that the `isSystem` flag can only be set when calling system contracts. + function systemCallWithPropagatedRevert( + uint32 gasLimit, + address to, + uint128 value, + bytes memory data + ) internal returns (bytes memory returnData) { + bool success; + (success, returnData) = systemCallWithReturndata(gasLimit, to, value, data); + + if (!success) { + assembly { + let size := mload(returnData) + revert(add(returnData, 0x20), size) + } + } + } + + /// @notice Calculates the packed representation of the FarCallABI. + /// @param dataOffset Calldata offset in memory. Provide 0 unless using custom pointer. + /// @param memoryPage Memory page to use. Provide 0 unless using custom pointer. + /// @param dataStart The start of the calldata slice. Provide the offset in memory + /// if not using custom pointer. + /// @param dataLength The calldata length. Provide the length of the calldata in bytes + /// unless using custom pointer. + /// @param gasPassed The gas to pass with the call. + /// @param shardId Of the account to call. Currently only 0 is supported. + /// @param forwardingMode The forwarding mode to use: + /// - provide CalldataForwardingMode.UseHeap when using your current memory + /// - provide CalldataForwardingMode.ForwardFatPointer when using custom pointer. + /// @param isConstructorCall Whether the call will be a call to the constructor + /// (ignored when the caller is not a system contract). + /// @param isSystemCall Whether the call will have the `isSystem` flag. + /// @return farCallAbi The far call ABI. + /// @dev The `FarCallABI` has the following structure: + /// pub struct FarCallABI { + /// pub memory_quasi_fat_pointer: FatPointer, + /// pub gas_passed: u32, + /// pub shard_id: u8, + /// pub forwarding_mode: FarCallForwardPageType, + /// pub constructor_call: bool, + /// pub to_system: bool, + /// } + /// + /// The FatPointer struct: + /// + /// pub struct FatPointer { + /// pub offset: u32, // offset relative to `start` + /// pub memory_page: u32, // memory page where slice is located + /// pub start: u32, // absolute start of the slice + /// pub length: u32, // length of the slice + /// } + /// + /// @dev Note, that the actual layout is the following: + /// + /// [0..32) bits -- the calldata offset + /// [32..64) bits -- the memory page to use. Can be left blank in most of the cases. + /// [64..96) bits -- the absolute start of the slice + /// [96..128) bits -- the length of the slice. + /// [128..192) bits -- empty bits. + /// [192..224) bits -- gasPassed. + /// [224..232) bits -- forwarding_mode + /// [232..240) bits -- shard id. + /// [240..248) bits -- constructor call flag + /// [248..256] bits -- system call flag + function getFarCallABI( + uint32 dataOffset, + uint32 memoryPage, + uint32 dataStart, + uint32 dataLength, + uint32 gasPassed, + uint8 shardId, + CalldataForwardingMode forwardingMode, + bool isConstructorCall, + bool isSystemCall + ) internal pure returns (uint256 farCallAbi) { + // Fill in the call parameter fields + farCallAbi = getFarCallABIWithEmptyFatPointer( + gasPassed, + shardId, + forwardingMode, + isConstructorCall, + isSystemCall + ); + // Fill in the fat pointer fields + farCallAbi |= dataOffset; + farCallAbi |= (uint256(memoryPage) << 32); + farCallAbi |= (uint256(dataStart) << 64); + farCallAbi |= (uint256(dataLength) << 96); + } + + /// @notice Calculates the packed representation of the FarCallABI with zero fat pointer fields. + /// @param gasPassed The gas to pass with the call. + /// @param shardId Of the account to call. Currently only 0 is supported. + /// @param forwardingMode The forwarding mode to use: + /// - provide CalldataForwardingMode.UseHeap when using your current memory + /// - provide CalldataForwardingMode.ForwardFatPointer when using custom pointer. + /// @param isConstructorCall Whether the call will be a call to the constructor + /// (ignored when the caller is not a system contract). + /// @param isSystemCall Whether the call will have the `isSystem` flag. + /// @return farCallAbiWithEmptyFatPtr The far call ABI with zero fat pointer fields. + function getFarCallABIWithEmptyFatPointer( + uint32 gasPassed, + uint8 shardId, + CalldataForwardingMode forwardingMode, + bool isConstructorCall, + bool isSystemCall + ) internal pure returns (uint256 farCallAbiWithEmptyFatPtr) { + farCallAbiWithEmptyFatPtr |= (uint256(gasPassed) << 192); + farCallAbiWithEmptyFatPtr |= (uint256(forwardingMode) << 224); + farCallAbiWithEmptyFatPtr |= (uint256(shardId) << 232); + if (isConstructorCall) { + farCallAbiWithEmptyFatPtr |= (1 << 240); + } + if (isSystemCall) { + farCallAbiWithEmptyFatPtr |= (1 << 248); + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/libraries/TransactionHelper.sol b/.test-node-subtree/etc/system-contracts/contracts/libraries/TransactionHelper.sol new file mode 100644 index 00000000..e0578197 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/libraries/TransactionHelper.sol @@ -0,0 +1,414 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "../openzeppelin/token/ERC20/IERC20.sol"; +import "../openzeppelin/token/ERC20/utils/SafeERC20.sol"; + +import "../interfaces/IPaymasterFlow.sol"; +import "../interfaces/IContractDeployer.sol"; +import {ETH_TOKEN_SYSTEM_CONTRACT, BOOTLOADER_FORMAL_ADDRESS} from "../Constants.sol"; +import "./RLPEncoder.sol"; +import "./EfficientCall.sol"; + +/// @dev The type id of zkSync's EIP-712-signed transaction. +uint8 constant EIP_712_TX_TYPE = 0x71; + +/// @dev The type id of legacy transactions. +uint8 constant LEGACY_TX_TYPE = 0x0; +/// @dev The type id of legacy transactions. +uint8 constant EIP_2930_TX_TYPE = 0x01; +/// @dev The type id of EIP1559 transactions. +uint8 constant EIP_1559_TX_TYPE = 0x02; + +/// @notice Structure used to represent zkSync transaction. +struct Transaction { + // The type of the transaction. + uint256 txType; + // The caller. + uint256 from; + // The callee. + uint256 to; + // The gasLimit to pass with the transaction. + // It has the same meaning as Ethereum's gasLimit. + uint256 gasLimit; + // The maximum amount of gas the user is willing to pay for a byte of pubdata. + uint256 gasPerPubdataByteLimit; + // The maximum fee per gas that the user is willing to pay. + // It is akin to EIP1559's maxFeePerGas. + uint256 maxFeePerGas; + // The maximum priority fee per gas that the user is willing to pay. + // It is akin to EIP1559's maxPriorityFeePerGas. + uint256 maxPriorityFeePerGas; + // The transaction's paymaster. If there is no paymaster, it is equal to 0. + uint256 paymaster; + // The nonce of the transaction. + uint256 nonce; + // The value to pass with the transaction. + uint256 value; + // In the future, we might want to add some + // new fields to the struct. The `txData` struct + // is to be passed to account and any changes to its structure + // would mean a breaking change to these accounts. In order to prevent this, + // we should keep some fields as "reserved". + // It is also recommended that their length is fixed, since + // it would allow easier proof integration (in case we will need + // some special circuit for preprocessing transactions). + uint256[4] reserved; + // The transaction's calldata. + bytes data; + // The signature of the transaction. + bytes signature; + // The properly formatted hashes of bytecodes that must be published on L1 + // with the inclusion of this transaction. Note, that a bytecode has been published + // before, the user won't pay fees for its republishing. + bytes32[] factoryDeps; + // The input to the paymaster. + bytes paymasterInput; + // Reserved dynamic type for the future use-case. Using it should be avoided, + // But it is still here, just in case we want to enable some additional functionality. + bytes reservedDynamic; +} + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice Library is used to help custom accounts to work with common methods for the Transaction type. + */ +library TransactionHelper { + using SafeERC20 for IERC20; + + /// @notice The EIP-712 typehash for the contract's domain + bytes32 constant EIP712_DOMAIN_TYPEHASH = keccak256("EIP712Domain(string name,string version,uint256 chainId)"); + + bytes32 constant EIP712_TRANSACTION_TYPE_HASH = + keccak256( + "Transaction(uint256 txType,uint256 from,uint256 to,uint256 gasLimit,uint256 gasPerPubdataByteLimit,uint256 maxFeePerGas,uint256 maxPriorityFeePerGas,uint256 paymaster,uint256 nonce,uint256 value,bytes data,bytes32[] factoryDeps,bytes paymasterInput)" + ); + + /// @notice Whether the token is Ethereum. + /// @param _addr The address of the token + /// @return `true` or `false` based on whether the token is Ether. + /// @dev This method assumes that address is Ether either if the address is 0 (for convenience) + /// or if the address is the address of the L2EthToken system contract. + function isEthToken(uint256 _addr) internal pure returns (bool) { + return _addr == uint256(uint160(address(ETH_TOKEN_SYSTEM_CONTRACT))) || _addr == 0; + } + + /// @notice Calculate the suggested signed hash of the transaction, + /// i.e. the hash that is signed by EOAs and is recommended to be signed by other accounts. + function encodeHash(Transaction calldata _transaction) internal view returns (bytes32 resultHash) { + if (_transaction.txType == LEGACY_TX_TYPE) { + resultHash = _encodeHashLegacyTransaction(_transaction); + } else if (_transaction.txType == EIP_712_TX_TYPE) { + resultHash = _encodeHashEIP712Transaction(_transaction); + } else if (_transaction.txType == EIP_1559_TX_TYPE) { + resultHash = _encodeHashEIP1559Transaction(_transaction); + } else if (_transaction.txType == EIP_2930_TX_TYPE) { + resultHash = _encodeHashEIP2930Transaction(_transaction); + } else { + // Currently no other transaction types are supported. + // Any new transaction types will be processed in a similar manner. + revert("Encoding unsupported tx"); + } + } + + /// @notice Encode hash of the zkSync native transaction type. + /// @return keccak256 hash of the EIP-712 encoded representation of transaction + function _encodeHashEIP712Transaction(Transaction calldata _transaction) private view returns (bytes32) { + bytes32 structHash = keccak256( + abi.encode( + EIP712_TRANSACTION_TYPE_HASH, + _transaction.txType, + _transaction.from, + _transaction.to, + _transaction.gasLimit, + _transaction.gasPerPubdataByteLimit, + _transaction.maxFeePerGas, + _transaction.maxPriorityFeePerGas, + _transaction.paymaster, + _transaction.nonce, + _transaction.value, + EfficientCall.keccak(_transaction.data), + keccak256(abi.encodePacked(_transaction.factoryDeps)), + EfficientCall.keccak(_transaction.paymasterInput) + ) + ); + + bytes32 domainSeparator = keccak256( + abi.encode(EIP712_DOMAIN_TYPEHASH, keccak256("zkSync"), keccak256("2"), block.chainid) + ); + + return keccak256(abi.encodePacked("\x19\x01", domainSeparator, structHash)); + } + + /// @notice Encode hash of the legacy transaction type. + /// @return keccak256 of the serialized RLP encoded representation of transaction + function _encodeHashLegacyTransaction(Transaction calldata _transaction) private view returns (bytes32) { + // Hash of legacy transactions are encoded as one of the: + // - RLP(nonce, gasPrice, gasLimit, to, value, data, chainId, 0, 0) + // - RLP(nonce, gasPrice, gasLimit, to, value, data) + // + // In this RLP encoding, only the first one above list appears, so we encode each element + // inside list and then concatenate the length of all elements with them. + + bytes memory encodedNonce = RLPEncoder.encodeUint256(_transaction.nonce); + // Encode `gasPrice` and `gasLimit` together to prevent "stack too deep error". + bytes memory encodedGasParam; + { + bytes memory encodedGasPrice = RLPEncoder.encodeUint256(_transaction.maxFeePerGas); + bytes memory encodedGasLimit = RLPEncoder.encodeUint256(_transaction.gasLimit); + encodedGasParam = bytes.concat(encodedGasPrice, encodedGasLimit); + } + + bytes memory encodedTo = RLPEncoder.encodeAddress(address(uint160(_transaction.to))); + bytes memory encodedValue = RLPEncoder.encodeUint256(_transaction.value); + // Encode only the length of the transaction data, and not the data itself, + // so as not to copy to memory a potentially huge transaction data twice. + bytes memory encodedDataLength; + { + // Safe cast, because the length of the transaction data can't be so large. + uint64 txDataLen = uint64(_transaction.data.length); + if (txDataLen != 1) { + // If the length is not equal to one, then only using the length can it be encoded definitely. + encodedDataLength = RLPEncoder.encodeNonSingleBytesLen(txDataLen); + } else if (_transaction.data[0] >= 0x80) { + // If input is a byte in [0x80, 0xff] range, RLP encoding will concatenates 0x81 with the byte. + encodedDataLength = hex"81"; + } + // Otherwise the length is not encoded at all. + } + + // Encode `chainId` according to EIP-155, but only if the `chainId` is specified in the transaction. + bytes memory encodedChainId; + if (_transaction.reserved[0] != 0) { + encodedChainId = bytes.concat(RLPEncoder.encodeUint256(block.chainid), hex"80_80"); + } + + bytes memory encodedListLength; + unchecked { + uint256 listLength = encodedNonce.length + + encodedGasParam.length + + encodedTo.length + + encodedValue.length + + encodedDataLength.length + + _transaction.data.length + + encodedChainId.length; + + // Safe cast, because the length of the list can't be so large. + encodedListLength = RLPEncoder.encodeListLen(uint64(listLength)); + } + + return + keccak256( + bytes.concat( + encodedListLength, + encodedNonce, + encodedGasParam, + encodedTo, + encodedValue, + encodedDataLength, + _transaction.data, + encodedChainId + ) + ); + } + + /// @notice Encode hash of the EIP2930 transaction type. + /// @return keccak256 of the serialized RLP encoded representation of transaction + function _encodeHashEIP2930Transaction(Transaction calldata _transaction) private view returns (bytes32) { + // Hash of EIP2930 transactions is encoded the following way: + // H(0x01 || RLP(chain_id, nonce, gas_price, gas_limit, destination, amount, data, access_list)) + // + // Note, that on zkSync access lists are not supported and should always be empty. + + // Encode all fixed-length params to avoid "stack too deep error" + bytes memory encodedFixedLengthParams; + { + bytes memory encodedChainId = RLPEncoder.encodeUint256(block.chainid); + bytes memory encodedNonce = RLPEncoder.encodeUint256(_transaction.nonce); + bytes memory encodedGasPrice = RLPEncoder.encodeUint256(_transaction.maxFeePerGas); + bytes memory encodedGasLimit = RLPEncoder.encodeUint256(_transaction.gasLimit); + bytes memory encodedTo = RLPEncoder.encodeAddress(address(uint160(_transaction.to))); + bytes memory encodedValue = RLPEncoder.encodeUint256(_transaction.value); + encodedFixedLengthParams = bytes.concat( + encodedChainId, + encodedNonce, + encodedGasPrice, + encodedGasLimit, + encodedTo, + encodedValue + ); + } + + // Encode only the length of the transaction data, and not the data itself, + // so as not to copy to memory a potentially huge transaction data twice. + bytes memory encodedDataLength; + { + // Safe cast, because the length of the transaction data can't be so large. + uint64 txDataLen = uint64(_transaction.data.length); + if (txDataLen != 1) { + // If the length is not equal to one, then only using the length can it be encoded definitely. + encodedDataLength = RLPEncoder.encodeNonSingleBytesLen(txDataLen); + } else if (_transaction.data[0] >= 0x80) { + // If input is a byte in [0x80, 0xff] range, RLP encoding will concatenates 0x81 with the byte. + encodedDataLength = hex"81"; + } + // Otherwise the length is not encoded at all. + } + + // On zkSync, access lists are always zero length (at least for now). + bytes memory encodedAccessListLength = RLPEncoder.encodeListLen(0); + + bytes memory encodedListLength; + unchecked { + uint256 listLength = encodedFixedLengthParams.length + + encodedDataLength.length + + _transaction.data.length + + encodedAccessListLength.length; + + // Safe cast, because the length of the list can't be so large. + encodedListLength = RLPEncoder.encodeListLen(uint64(listLength)); + } + + return + keccak256( + bytes.concat( + "\x01", + encodedListLength, + encodedFixedLengthParams, + encodedDataLength, + _transaction.data, + encodedAccessListLength + ) + ); + } + + /// @notice Encode hash of the EIP1559 transaction type. + /// @return keccak256 of the serialized RLP encoded representation of transaction + function _encodeHashEIP1559Transaction(Transaction calldata _transaction) private view returns (bytes32) { + // Hash of EIP1559 transactions is encoded the following way: + // H(0x02 || RLP(chain_id, nonce, max_priority_fee_per_gas, max_fee_per_gas, gas_limit, destination, amount, data, access_list)) + // + // Note, that on zkSync access lists are not supported and should always be empty. + + // Encode all fixed-length params to avoid "stack too deep error" + bytes memory encodedFixedLengthParams; + { + bytes memory encodedChainId = RLPEncoder.encodeUint256(block.chainid); + bytes memory encodedNonce = RLPEncoder.encodeUint256(_transaction.nonce); + bytes memory encodedMaxPriorityFeePerGas = RLPEncoder.encodeUint256(_transaction.maxPriorityFeePerGas); + bytes memory encodedMaxFeePerGas = RLPEncoder.encodeUint256(_transaction.maxFeePerGas); + bytes memory encodedGasLimit = RLPEncoder.encodeUint256(_transaction.gasLimit); + bytes memory encodedTo = RLPEncoder.encodeAddress(address(uint160(_transaction.to))); + bytes memory encodedValue = RLPEncoder.encodeUint256(_transaction.value); + encodedFixedLengthParams = bytes.concat( + encodedChainId, + encodedNonce, + encodedMaxPriorityFeePerGas, + encodedMaxFeePerGas, + encodedGasLimit, + encodedTo, + encodedValue + ); + } + + // Encode only the length of the transaction data, and not the data itself, + // so as not to copy to memory a potentially huge transaction data twice. + bytes memory encodedDataLength; + { + // Safe cast, because the length of the transaction data can't be so large. + uint64 txDataLen = uint64(_transaction.data.length); + if (txDataLen != 1) { + // If the length is not equal to one, then only using the length can it be encoded definitely. + encodedDataLength = RLPEncoder.encodeNonSingleBytesLen(txDataLen); + } else if (_transaction.data[0] >= 0x80) { + // If input is a byte in [0x80, 0xff] range, RLP encoding will concatenates 0x81 with the byte. + encodedDataLength = hex"81"; + } + // Otherwise the length is not encoded at all. + } + + // On zkSync, access lists are always zero length (at least for now). + bytes memory encodedAccessListLength = RLPEncoder.encodeListLen(0); + + bytes memory encodedListLength; + unchecked { + uint256 listLength = encodedFixedLengthParams.length + + encodedDataLength.length + + _transaction.data.length + + encodedAccessListLength.length; + + // Safe cast, because the length of the list can't be so large. + encodedListLength = RLPEncoder.encodeListLen(uint64(listLength)); + } + + return + keccak256( + bytes.concat( + "\x02", + encodedListLength, + encodedFixedLengthParams, + encodedDataLength, + _transaction.data, + encodedAccessListLength + ) + ); + } + + /// @notice Processes the common paymaster flows, e.g. setting proper allowance + /// for tokens, etc. For more information on the expected behavior, check out + /// the "Paymaster flows" section in the documentation. + function processPaymasterInput(Transaction calldata _transaction) internal { + require(_transaction.paymasterInput.length >= 4, "The standard paymaster input must be at least 4 bytes long"); + + bytes4 paymasterInputSelector = bytes4(_transaction.paymasterInput[0:4]); + if (paymasterInputSelector == IPaymasterFlow.approvalBased.selector) { + require( + _transaction.paymasterInput.length >= 68, + "The approvalBased paymaster input must be at least 68 bytes long" + ); + + // While the actual data consists of address, uint256 and bytes data, + // the data is needed only for the paymaster, so we ignore it here for the sake of optimization + (address token, uint256 minAllowance) = abi.decode(_transaction.paymasterInput[4:68], (address, uint256)); + address paymaster = address(uint160(_transaction.paymaster)); + + uint256 currentAllowance = IERC20(token).allowance(address(this), paymaster); + if (currentAllowance < minAllowance) { + // Some tokens, e.g. USDT require that the allowance is firsty set to zero + // and only then updated to the new value. + + IERC20(token).safeApprove(paymaster, 0); + IERC20(token).safeApprove(paymaster, minAllowance); + } + } else if (paymasterInputSelector == IPaymasterFlow.general.selector) { + // Do nothing. general(bytes) paymaster flow means that the paymaster must interpret these bytes on his own. + } else { + revert("Unsupported paymaster flow"); + } + } + + /// @notice Pays the required fee for the transaction to the bootloader. + /// @dev Currently it pays the maximum amount "_transaction.maxFeePerGas * _transaction.gasLimit", + /// it will change in the future. + function payToTheBootloader(Transaction calldata _transaction) internal returns (bool success) { + address bootloaderAddr = BOOTLOADER_FORMAL_ADDRESS; + uint256 amount = _transaction.maxFeePerGas * _transaction.gasLimit; + + assembly { + success := call(gas(), bootloaderAddr, amount, 0, 0, 0, 0) + } + } + + // Returns the balance required to process the transaction. + function totalRequiredBalance(Transaction calldata _transaction) internal pure returns (uint256 requiredBalance) { + if (address(uint160(_transaction.paymaster)) != address(0)) { + // Paymaster pays for the fee + requiredBalance = _transaction.value; + } else { + // The user should have enough balance for both the fee and the value of the transaction + requiredBalance = _transaction.maxFeePerGas * _transaction.gasLimit + _transaction.value; + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/libraries/UnsafeBytesCalldata.sol b/.test-node-subtree/etc/system-contracts/contracts/libraries/UnsafeBytesCalldata.sol new file mode 100644 index 00000000..4ce65f5f --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/libraries/UnsafeBytesCalldata.sol @@ -0,0 +1,51 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @dev The library provides a set of functions that help read data from calldata bytes. + * @dev Each of the functions accepts the `bytes calldata` and the offset where data should be read and returns a value of a certain type. + * + * @dev WARNING! + * 1) Functions don't check the length of the bytes array, so it can go out of bounds. + * The user of the library must check for bytes length before using any functions from the library! + * + * 2) Read variables are not cleaned up - https://docs.soliditylang.org/en/v0.8.16/internals/variable_cleanup.html. + * Using data in inline assembly can lead to unexpected behavior! + */ +library UnsafeBytesCalldata { + function readUint16(bytes calldata _bytes, uint256 _start) internal pure returns (uint16 result) { + assembly { + let offset := sub(_bytes.offset, 30) + result := calldataload(add(offset, _start)) + } + } + + function readUint32(bytes calldata _bytes, uint256 _start) internal pure returns (uint32 result) { + assembly { + let offset := sub(_bytes.offset, 28) + result := calldataload(add(offset, _start)) + } + } + + function readUint64(bytes calldata _bytes, uint256 _start) internal pure returns (uint64 result) { + assembly { + let offset := sub(_bytes.offset, 24) + result := calldataload(add(offset, _start)) + } + } + + function readBytes32(bytes calldata _bytes, uint256 _start) internal pure returns (bytes32 result) { + assembly { + result := calldataload(add(_bytes.offset, _start)) + } + } + + function readUint256(bytes calldata _bytes, uint256 _start) internal pure returns (uint256 result) { + assembly { + result := calldataload(add(_bytes.offset, _start)) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/libraries/Utils.sol b/.test-node-subtree/etc/system-contracts/contracts/libraries/Utils.sol new file mode 100644 index 00000000..a2791520 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/libraries/Utils.sol @@ -0,0 +1,97 @@ +// SPDX-License-Identifier: MIT +pragma solidity 0.8.20; + +import "./EfficientCall.sol"; + +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @dev Common utilities used in zkSync system contracts + */ +library Utils { + /// @dev Bit mask of bytecode hash "isConstructor" marker + bytes32 constant IS_CONSTRUCTOR_BYTECODE_HASH_BIT_MASK = + 0x00ff000000000000000000000000000000000000000000000000000000000000; + + /// @dev Bit mask to set the "isConstructor" marker in the bytecode hash + bytes32 constant SET_IS_CONSTRUCTOR_MARKER_BIT_MASK = + 0x0001000000000000000000000000000000000000000000000000000000000000; + + function safeCastToU128(uint256 _x) internal pure returns (uint128) { + require(_x <= type(uint128).max, "Overflow"); + + return uint128(_x); + } + + function safeCastToU32(uint256 _x) internal pure returns (uint32) { + require(_x <= type(uint32).max, "Overflow"); + + return uint32(_x); + } + + function safeCastToU24(uint256 _x) internal pure returns (uint24) { + require(_x <= type(uint24).max, "Overflow"); + + return uint24(_x); + } + + /// @return codeLength The bytecode length in bytes + function bytecodeLenInBytes(bytes32 _bytecodeHash) internal pure returns (uint256 codeLength) { + codeLength = bytecodeLenInWords(_bytecodeHash) << 5; // _bytecodeHash * 32 + } + + /// @return codeLengthInWords The bytecode length in machine words + function bytecodeLenInWords(bytes32 _bytecodeHash) internal pure returns (uint256 codeLengthInWords) { + unchecked { + codeLengthInWords = uint256(uint8(_bytecodeHash[2])) * 256 + uint256(uint8(_bytecodeHash[3])); + } + } + + /// @notice Denotes whether bytecode hash corresponds to a contract that already constructed + function isContractConstructed(bytes32 _bytecodeHash) internal pure returns (bool) { + return _bytecodeHash[1] == 0x00; + } + + /// @notice Denotes whether bytecode hash corresponds to a contract that is on constructor or has already been constructed + function isContractConstructing(bytes32 _bytecodeHash) internal pure returns (bool) { + return _bytecodeHash[1] == 0x01; + } + + /// @notice Sets "isConstructor" flag to TRUE for the bytecode hash + /// @param _bytecodeHash The bytecode hash for which it is needed to set the constructing flag + /// @return The bytecode hash with "isConstructor" flag set to TRUE + function constructingBytecodeHash(bytes32 _bytecodeHash) internal pure returns (bytes32) { + // Clear the "isConstructor" marker and set it to 0x01. + return constructedBytecodeHash(_bytecodeHash) | SET_IS_CONSTRUCTOR_MARKER_BIT_MASK; + } + + /// @notice Sets "isConstructor" flag to FALSE for the bytecode hash + /// @param _bytecodeHash The bytecode hash for which it is needed to set the constructing flag + /// @return The bytecode hash with "isConstructor" flag set to FALSE + function constructedBytecodeHash(bytes32 _bytecodeHash) internal pure returns (bytes32) { + return _bytecodeHash & ~IS_CONSTRUCTOR_BYTECODE_HASH_BIT_MASK; + } + + /// @notice Validate the bytecode format and calculate its hash. + /// @param _bytecode The bytecode to hash. + /// @return hashedBytecode The 32-byte hash of the bytecode. + /// Note: The function reverts the execution if the bytecode has non expected format: + /// - Bytecode bytes length is not a multiple of 32 + /// - Bytecode bytes length is not less than 2^21 bytes (2^16 words) + /// - Bytecode words length is not odd + function hashL2Bytecode(bytes calldata _bytecode) internal view returns (bytes32 hashedBytecode) { + // Note that the length of the bytecode must be provided in 32-byte words. + require(_bytecode.length % 32 == 0, "po"); + + uint256 lengthInWords = _bytecode.length / 32; + require(lengthInWords < 2 ** 16, "pp"); // bytecode length must be less than 2^16 words + require(lengthInWords % 2 == 1, "pr"); // bytecode length in words must be odd + hashedBytecode = + EfficientCall.sha(_bytecode) & + 0x00000000FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF; + // Setting the version of the hash + hashedBytecode = (hashedBytecode | bytes32(uint256(1 << 248))); + // Setting the length + hashedBytecode = hashedBytecode | bytes32(lengthInWords << 224); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/token/ERC20/IERC20.sol b/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/token/ERC20/IERC20.sol new file mode 100644 index 00000000..b816bfed --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/token/ERC20/IERC20.sol @@ -0,0 +1,82 @@ +// SPDX-License-Identifier: MIT +// OpenZeppelin Contracts (last updated v4.6.0) (token/ERC20/IERC20.sol) + +pragma solidity ^0.8.0; + +/** + * @dev Interface of the ERC20 standard as defined in the EIP. + */ +interface IERC20 { + /** + * @dev Emitted when `value` tokens are moved from one account (`from`) to + * another (`to`). + * + * Note that `value` may be zero. + */ + event Transfer(address indexed from, address indexed to, uint256 value); + + /** + * @dev Emitted when the allowance of a `spender` for an `owner` is set by + * a call to {approve}. `value` is the new allowance. + */ + event Approval(address indexed owner, address indexed spender, uint256 value); + + /** + * @dev Returns the amount of tokens in existence. + */ + function totalSupply() external view returns (uint256); + + /** + * @dev Returns the amount of tokens owned by `account`. + */ + function balanceOf(address account) external view returns (uint256); + + /** + * @dev Moves `amount` tokens from the caller's account to `to`. + * + * Returns a boolean value indicating whether the operation succeeded. + * + * Emits a {Transfer} event. + */ + function transfer(address to, uint256 amount) external returns (bool); + + /** + * @dev Returns the remaining number of tokens that `spender` will be + * allowed to spend on behalf of `owner` through {transferFrom}. This is + * zero by default. + * + * This value changes when {approve} or {transferFrom} are called. + */ + function allowance(address owner, address spender) external view returns (uint256); + + /** + * @dev Sets `amount` as the allowance of `spender` over the caller's tokens. + * + * Returns a boolean value indicating whether the operation succeeded. + * + * IMPORTANT: Beware that changing an allowance with this method brings the risk + * that someone may use both the old and the new allowance by unfortunate + * transaction ordering. One possible solution to mitigate this race + * condition is to first reduce the spender's allowance to 0 and set the + * desired value afterwards: + * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729 + * + * Emits an {Approval} event. + */ + function approve(address spender, uint256 amount) external returns (bool); + + /** + * @dev Moves `amount` tokens from `from` to `to` using the + * allowance mechanism. `amount` is then deducted from the caller's + * allowance. + * + * Returns a boolean value indicating whether the operation succeeded. + * + * Emits a {Transfer} event. + */ + function transferFrom( + address from, + address to, + uint256 amount + ) external returns (bool); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/token/ERC20/extensions/IERC20Permit.sol b/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/token/ERC20/extensions/IERC20Permit.sol new file mode 100644 index 00000000..bb43e53b --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/token/ERC20/extensions/IERC20Permit.sol @@ -0,0 +1,60 @@ +// SPDX-License-Identifier: MIT +// OpenZeppelin Contracts v4.4.1 (token/ERC20/extensions/IERC20Permit.sol) + +pragma solidity ^0.8.0; + +/** + * @dev Interface of the ERC20 Permit extension allowing approvals to be made via signatures, as defined in + * https://eips.ethereum.org/EIPS/eip-2612[EIP-2612]. + * + * Adds the {permit} method, which can be used to change an account's ERC20 allowance (see {IERC20-allowance}) by + * presenting a message signed by the account. By not relying on {IERC20-approve}, the token holder account doesn't + * need to send a transaction, and thus is not required to hold Ether at all. + */ +interface IERC20Permit { + /** + * @dev Sets `value` as the allowance of `spender` over ``owner``'s tokens, + * given ``owner``'s signed approval. + * + * IMPORTANT: The same issues {IERC20-approve} has related to transaction + * ordering also apply here. + * + * Emits an {Approval} event. + * + * Requirements: + * + * - `spender` cannot be the zero address. + * - `deadline` must be a timestamp in the future. + * - `v`, `r` and `s` must be a valid `secp256k1` signature from `owner` + * over the EIP712-formatted function arguments. + * - the signature must use ``owner``'s current nonce (see {nonces}). + * + * For more information on the signature format, see the + * https://eips.ethereum.org/EIPS/eip-2612#specification[relevant EIP + * section]. + */ + function permit( + address owner, + address spender, + uint256 value, + uint256 deadline, + uint8 v, + bytes32 r, + bytes32 s + ) external; + + /** + * @dev Returns the current nonce for `owner`. This value must be + * included whenever a signature is generated for {permit}. + * + * Every successful call to {permit} increases ``owner``'s nonce by one. This + * prevents a signature from being used multiple times. + */ + function nonces(address owner) external view returns (uint256); + + /** + * @dev Returns the domain separator used in the encoding of the signature for {permit}, as defined by {EIP712}. + */ + // solhint-disable-next-line func-name-mixedcase + function DOMAIN_SEPARATOR() external view returns (bytes32); +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/token/ERC20/utils/SafeERC20.sol b/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/token/ERC20/utils/SafeERC20.sol new file mode 100644 index 00000000..4a07fff2 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/token/ERC20/utils/SafeERC20.sol @@ -0,0 +1,151 @@ +// SPDX-License-Identifier: MIT +// OpenZeppelin Contracts (last updated v4.8.0) (token/ERC20/utils/SafeERC20.sol) + +pragma solidity ^0.8.0; + +import "../IERC20.sol"; +import "../extensions/IERC20Permit.sol"; +import "../../../utils/Address.sol"; + +/** + * @title SafeERC20 + * @dev Wrappers around ERC20 operations that throw on failure (when the token + * contract returns false). Tokens that return no value (and instead revert or + * throw on failure) are also supported, non-reverting calls are assumed to be + * successful. + * To use this library you can add a `using SafeERC20 for IERC20;` statement to your contract, + * which allows you to call the safe operations as `token.safeTransfer(...)`, etc. + */ +library SafeERC20 { + using Address for address; + + function safeTransfer( + IERC20 token, + address to, + uint256 value + ) internal { + _callOptionalReturn( + token, + abi.encodeWithSelector(token.transfer.selector, to, value) + ); + } + + function safeTransferFrom( + IERC20 token, + address from, + address to, + uint256 value + ) internal { + _callOptionalReturn( + token, + abi.encodeWithSelector(token.transferFrom.selector, from, to, value) + ); + } + + /** + * @dev Deprecated. This function has issues similar to the ones found in + * {IERC20-approve}, and its usage is discouraged. + * + * Whenever possible, use {safeIncreaseAllowance} and + * {safeDecreaseAllowance} instead. + */ + function safeApprove( + IERC20 token, + address spender, + uint256 value + ) internal { + // safeApprove should only be called when setting an initial allowance, + // or when resetting it to zero. To increase and decrease it, use + // 'safeIncreaseAllowance' and 'safeDecreaseAllowance' + require( + (value == 0) || (token.allowance(address(this), spender) == 0), + "SafeERC20: approve from non-zero to non-zero allowance" + ); + _callOptionalReturn( + token, + abi.encodeWithSelector(token.approve.selector, spender, value) + ); + } + + function safeIncreaseAllowance( + IERC20 token, + address spender, + uint256 value + ) internal { + uint256 newAllowance = token.allowance(address(this), spender) + value; + _callOptionalReturn( + token, + abi.encodeWithSelector( + token.approve.selector, + spender, + newAllowance + ) + ); + } + + function safeDecreaseAllowance( + IERC20 token, + address spender, + uint256 value + ) internal { + unchecked { + uint256 oldAllowance = token.allowance(address(this), spender); + require( + oldAllowance >= value, + "SafeERC20: decreased allowance below zero" + ); + uint256 newAllowance = oldAllowance - value; + _callOptionalReturn( + token, + abi.encodeWithSelector( + token.approve.selector, + spender, + newAllowance + ) + ); + } + } + + function safePermit( + IERC20Permit token, + address owner, + address spender, + uint256 value, + uint256 deadline, + uint8 v, + bytes32 r, + bytes32 s + ) internal { + uint256 nonceBefore = token.nonces(owner); + token.permit(owner, spender, value, deadline, v, r, s); + uint256 nonceAfter = token.nonces(owner); + require( + nonceAfter == nonceBefore + 1, + "SafeERC20: permit did not succeed" + ); + } + + /** + * @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement + * on the return value: the return value is optional (but if data is returned, it must not be false). + * @param token The token targeted by the call. + * @param data The call data (encoded using abi.encode or one of its variants). + */ + function _callOptionalReturn(IERC20 token, bytes memory data) private { + // We need to perform a low level call here, to bypass Solidity's return data size checking mechanism, since + // we're implementing it ourselves. We use {Address-functionCall} to perform this call, which verifies that + // the target address contains contract code and also asserts for success in the low-level call. + + bytes memory returndata = address(token).functionCall( + data, + "SafeERC20: low-level call failed" + ); + if (returndata.length > 0) { + // Return data is optional + require( + abi.decode(returndata, (bool)), + "SafeERC20: ERC20 operation did not succeed" + ); + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/utils/Address.sol b/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/utils/Address.sol new file mode 100644 index 00000000..7a7d2d5d --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/openzeppelin/utils/Address.sol @@ -0,0 +1,308 @@ +// SPDX-License-Identifier: MIT +// OpenZeppelin Contracts (last updated v4.8.0) (utils/Address.sol) + +pragma solidity ^0.8.1; + +/** + * @dev Collection of functions related to the address type + */ +library Address { + /** + * @dev Returns true if `account` is a contract. + * + * [IMPORTANT] + * ==== + * It is unsafe to assume that an address for which this function returns + * false is an externally-owned account (EOA) and not a contract. + * + * Among others, `isContract` will return false for the following + * types of addresses: + * + * - an externally-owned account + * - a contract in construction + * - an address where a contract will be created + * - an address where a contract lived, but was destroyed + * ==== + * + * [IMPORTANT] + * ==== + * You shouldn't rely on `isContract` to protect against flash loan attacks! + * + * Preventing calls from contracts is highly discouraged. It breaks composability, breaks support for smart wallets + * like Gnosis Safe, and does not provide security since it can be circumvented by calling from a contract + * constructor. + * ==== + */ + function isContract(address account) internal view returns (bool) { + // This method relies on extcodesize/address.code.length, which returns 0 + // for contracts in construction, since the code is only stored at the end + // of the constructor execution. + + return account.code.length > 0; + } + + /** + * @dev Replacement for Solidity's `transfer`: sends `amount` wei to + * `recipient`, forwarding all available gas and reverting on errors. + * + * https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost + * of certain opcodes, possibly making contracts go over the 2300 gas limit + * imposed by `transfer`, making them unable to receive funds via + * `transfer`. {sendValue} removes this limitation. + * + * https://consensys.net/diligence/blog/2019/09/stop-using-soliditys-transfer-now/[Learn more]. + * + * IMPORTANT: because control is transferred to `recipient`, care must be + * taken to not create reentrancy vulnerabilities. Consider using + * {ReentrancyGuard} or the + * https://solidity.readthedocs.io/en/v0.5.11/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern]. + */ + function sendValue(address payable recipient, uint256 amount) internal { + require( + address(this).balance >= amount, + "Address: insufficient balance" + ); + + (bool success, ) = recipient.call{value: amount}(""); + require( + success, + "Address: unable to send value, recipient may have reverted" + ); + } + + /** + * @dev Performs a Solidity function call using a low level `call`. A + * plain `call` is an unsafe replacement for a function call: use this + * function instead. + * + * If `target` reverts with a revert reason, it is bubbled up by this + * function (like regular Solidity function calls). + * + * Returns the raw returned data. To convert to the expected return value, + * use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`]. + * + * Requirements: + * + * - `target` must be a contract. + * - calling `target` with `data` must not revert. + * + * _Available since v3.1._ + */ + function functionCall(address target, bytes memory data) + internal + returns (bytes memory) + { + return + functionCallWithValue( + target, + data, + 0, + "Address: low-level call failed" + ); + } + + /** + * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with + * `errorMessage` as a fallback revert reason when `target` reverts. + * + * _Available since v3.1._ + */ + function functionCall( + address target, + bytes memory data, + string memory errorMessage + ) internal returns (bytes memory) { + return functionCallWithValue(target, data, 0, errorMessage); + } + + /** + * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], + * but also transferring `value` wei to `target`. + * + * Requirements: + * + * - the calling contract must have an ETH balance of at least `value`. + * - the called Solidity function must be `payable`. + * + * _Available since v3.1._ + */ + function functionCallWithValue( + address target, + bytes memory data, + uint256 value + ) internal returns (bytes memory) { + return + functionCallWithValue( + target, + data, + value, + "Address: low-level call with value failed" + ); + } + + /** + * @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but + * with `errorMessage` as a fallback revert reason when `target` reverts. + * + * _Available since v3.1._ + */ + function functionCallWithValue( + address target, + bytes memory data, + uint256 value, + string memory errorMessage + ) internal returns (bytes memory) { + require( + address(this).balance >= value, + "Address: insufficient balance for call" + ); + (bool success, bytes memory returndata) = target.call{value: value}( + data + ); + return + verifyCallResultFromTarget( + target, + success, + returndata, + errorMessage + ); + } + + /** + * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], + * but performing a static call. + * + * _Available since v3.3._ + */ + function functionStaticCall(address target, bytes memory data) + internal + view + returns (bytes memory) + { + return + functionStaticCall( + target, + data, + "Address: low-level static call failed" + ); + } + + /** + * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`], + * but performing a static call. + * + * _Available since v3.3._ + */ + function functionStaticCall( + address target, + bytes memory data, + string memory errorMessage + ) internal view returns (bytes memory) { + (bool success, bytes memory returndata) = target.staticcall(data); + return + verifyCallResultFromTarget( + target, + success, + returndata, + errorMessage + ); + } + + /** + * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], + * but performing a delegate call. + * + * _Available since v3.4._ + */ + function functionDelegateCall(address target, bytes memory data) + internal + returns (bytes memory) + { + return + functionDelegateCall( + target, + data, + "Address: low-level delegate call failed" + ); + } + + /** + * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`], + * but performing a delegate call. + * + * _Available since v3.4._ + */ + function functionDelegateCall( + address target, + bytes memory data, + string memory errorMessage + ) internal returns (bytes memory) { + (bool success, bytes memory returndata) = target.delegatecall(data); + return + verifyCallResultFromTarget( + target, + success, + returndata, + errorMessage + ); + } + + /** + * @dev Tool to verify that a low level call to smart-contract was successful, and revert (either by bubbling + * the revert reason or using the provided one) in case of unsuccessful call or if target was not a contract. + * + * _Available since v4.8._ + */ + function verifyCallResultFromTarget( + address target, + bool success, + bytes memory returndata, + string memory errorMessage + ) internal view returns (bytes memory) { + if (success) { + if (returndata.length == 0) { + // only check isContract if the call was successful and the return data is empty + // otherwise we already know that it was a contract + require(isContract(target), "Address: call to non-contract"); + } + return returndata; + } else { + _revert(returndata, errorMessage); + } + } + + /** + * @dev Tool to verify that a low level call was successful, and revert if it wasn't, either by bubbling the + * revert reason or using the provided one. + * + * _Available since v4.3._ + */ + function verifyCallResult( + bool success, + bytes memory returndata, + string memory errorMessage + ) internal pure returns (bytes memory) { + if (success) { + return returndata; + } else { + _revert(returndata, errorMessage); + } + } + + function _revert(bytes memory returndata, string memory errorMessage) + private + pure + { + // Look for revert reason and bubble it up if present + if (returndata.length > 0) { + // The easiest way to bubble the revert reason is using memory via assembly + /// @solidity memory-safe-assembly + assembly { + let returndata_size := mload(returndata) + revert(add(32, returndata), returndata_size) + } + } else { + revert(errorMessage); + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/precompiles/EcAdd.yul b/.test-node-subtree/etc/system-contracts/contracts/precompiles/EcAdd.yul new file mode 100644 index 00000000..bfbac645 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/precompiles/EcAdd.yul @@ -0,0 +1,441 @@ +object "EcAdd" { + code { + return(0, 0) + } + object "EcAdd_deployed" { + code { + //////////////////////////////////////////////////////////////// + // CONSTANTS + //////////////////////////////////////////////////////////////// + + /// @notice Constant function for value three in Montgomery form. + /// @dev This value was precomputed using Python. + /// @return m_three The value three in Montgomery form. + function MONTGOMERY_THREE() -> m_three { + m_three := 19052624634359457937016868847204597229365286637454337178037183604060995791063 + } + + /// @notice Constant function for the alt_bn128 field order. + /// @dev See https://eips.ethereum.org/EIPS/eip-196 for further details. + /// @return ret The alt_bn128 field order. + function P() -> ret { + ret := 21888242871839275222246405745257275088696311157297823662689037894645226208583 + } + + /// @notice Constant function for the pre-computation of R^2 % N for the Montgomery REDC algorithm. + /// @dev R^2 is the Montgomery residue of the value 2^512. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value R^2 modulus the curve field order. + function R2_MOD_P() -> ret { + ret := 3096616502983703923843567936837374451735540968419076528771170197431451843209 + } + + /// @notice Constant function for the pre-computation of N' for the Montgomery REDC algorithm. + /// @dev N' is a value such that NN' = -1 mod R, with N being the curve field order. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value N'. + function N_PRIME() -> ret { + ret := 111032442853175714102588374283752698368366046808579839647964533820976443843465 + } + + ////////////////////////////////////////////////////////////////// + // HELPER FUNCTIONS + ////////////////////////////////////////////////////////////////// + + /// @dev Executes the `precompileCall` opcode. + function precompileCall(precompileParams, gasToBurn) -> ret { + // Compiler simulation for calling `precompileCall` opcode + ret := verbatim_2i_1o("precompile", precompileParams, gasToBurn) + } + + /// @notice Burns remaining gas until revert. + /// @dev This function is used to burn gas in the case of a failed precompile call. + function burnGas() { + // Precompiles that do not have a circuit counterpart + // will burn the provided gas by calling this function. + precompileCall(0, gas()) + } + + /// @notice Retrieves the highest half of the multiplication result. + /// @param multiplicand The value to multiply. + /// @param multiplier The multiplier. + /// @return ret The highest half of the multiplication result. + function getHighestHalfOfMultiplication(multiplicand, multiplier) -> ret { + ret := verbatim_2i_1o("mul_high", multiplicand, multiplier) + } + + /// @notice Computes the modular subtraction of two values. + /// @param minuend The value to subtract from. + /// @param subtrahend The value to subtract. + /// @param modulus The modulus. + /// @return difference The modular subtraction of the two values. + function submod(minuend, subtrahend, modulus) -> difference { + difference := addmod(minuend, sub(modulus, subtrahend), modulus) + } + + /// @notice Computes an addition and checks for overflow. + /// @param augend The value to add to. + /// @param addend The value to add. + /// @return sum The sum of the two values. + /// @return overflowed True if the addition overflowed, false otherwise. + function overflowingAdd(augend, addend) -> sum, overflowed { + sum := add(augend, addend) + overflowed := lt(sum, augend) + } + + // @notice Checks if a point is on the curve. + // @dev The curve in question is the alt_bn128 curve. + // @dev The Short Weierstrass equation of the curve is y^2 = x^3 + 3. + // @param x The x coordinate of the point in Montgomery form. + // @param y The y coordinate of the point in Montgomery form. + // @return ret True if the point is on the curve, false otherwise. + function pointIsInCurve(x, y) -> ret { + let ySquared := montgomeryMul(y, y) + let xSquared := montgomeryMul(x, x) + let xQubed := montgomeryMul(xSquared, x) + let xQubedPlusThree := montgomeryAdd(xQubed, MONTGOMERY_THREE()) + + ret := eq(ySquared, xQubedPlusThree) + } + + /// @notice Checks if a point is the point at infinity. + /// @dev The point at infinity is defined as the point (0, 0). + /// @dev See https://eips.ethereum.org/EIPS/eip-196 for further details. + /// @param x The x coordinate of the point. + /// @param y The y coordinate of the point. + /// @return ret True if the point is the point at infinity, false otherwise. + function isInfinity(x, y) -> ret { + ret := iszero(or(x, y)) + } + + /// @notice Checks if a coordinate is on the curve field order. + /// @dev A coordinate is on the curve field order if it is on the range [0, curveFieldOrder). + /// @dev This check is required in the precompile specification. See https://eips.ethereum.org/EIPS/eip-196 for further details. + /// @param coordinate The coordinate to check. + /// @return ret True if the coordinate is in the range, false otherwise. + function isOnFieldOrder(coordinate) -> ret { + ret := lt(coordinate, P()) + } + + /// @notice Computes the inverse in Montgomery Form of a number in Montgomery Form. + /// @dev Reference: https://github.com/lambdaclass/lambdaworks/blob/main/math/src/field/fields/montgomery_backed_prime_fields.rs#L169 + /// @dev Let `base` be a number in Montgomery Form, then base = a*R mod P() being `a` the base number (not in Montgomery Form) + /// @dev Let `inv` be the inverse of a number `a` in Montgomery Form, then inv = a^(-1)*R mod P() + /// @dev The original binary extended euclidean algorithms takes a number a and returns a^(-1) mod N + /// @dev In our case N is P(), and we'd like the input and output to be in Montgomery Form (a*R mod P() + /// @dev and a^(-1)*R mod P() respectively). + /// @dev If we just pass the input as a number in Montgomery Form the result would be a^(-1)*R^(-1) mod P(), + /// @dev but we want it to be a^(-1)*R mod P(). + /// @dev For that, we take advantage of the algorithm's linearity and multiply the result by R^2 mod P() + /// @dev to get R^2*a^(-1)*R^(-1) mod P() = a^(-1)*R mod P() as the desired result in Montgomery Form. + /// @dev `inv` takes the value of `b` or `c` being the result sometimes `b` and sometimes `c`. In paper + /// @dev multiplying `b` or `c` by R^2 mod P() results on starting their values as b = R2_MOD_P() and c = 0. + /// @param base A number `a` in Montgomery Form, then base = a*R mod P(). + /// @return inv The inverse of a number `a` in Montgomery Form, then inv = a^(-1)*R mod P(). + function binaryExtendedEuclideanAlgorithm(base) -> inv { + let modulus := P() + let u := base + let v := modulus + // Avoids unnecessary reduction step. + let b := R2_MOD_P() + let c := 0 + + for {} and(iszero(eq(u, 1)), iszero(eq(v, 1))) {} { + for {} iszero(and(u, 1)) {} { + u := shr(1, u) + let current := b + switch and(current, 1) + case 0 { + b := shr(1, b) + } + case 1 { + b := shr(1, add(b, modulus)) + } + } + + for {} iszero(and(v, 1)) {} { + v := shr(1, v) + let current := c + switch and(current, 1) + case 0 { + c := shr(1, c) + } + case 1 { + c := shr(1, add(c, modulus)) + } + } + + switch gt(v, u) + case 0 { + u := sub(u, v) + if lt(b, c) { + b := add(b, modulus) + } + b := sub(b, c) + } + case 1 { + v := sub(v, u) + if lt(c, b) { + c := add(c, modulus) + } + c := sub(c, b) + } + } + + switch eq(u, 1) + case 0 { + inv := c + } + case 1 { + inv := b + } + } + + /// @notice Implementation of the Montgomery reduction algorithm (a.k.a. REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm + /// @param lowestHalfOfT The lowest half of the value T. + /// @param higherHalfOfT The higher half of the value T. + /// @return S The result of the Montgomery reduction. + function REDC(lowestHalfOfT, higherHalfOfT) -> S { + let m := mul(lowestHalfOfT, N_PRIME()) + let hi := add(higherHalfOfT, getHighestHalfOfMultiplication(m, P())) + let lo, overflowed := overflowingAdd(lowestHalfOfT, mul(m, P())) + if overflowed { + hi := add(hi, 1) + } + S := hi + if iszero(lt(hi, P())) { + S := sub(hi, P()) + } + } + + /// @notice Encodes a field element into the Montgomery form using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further details on transforming a field element into the Montgomery form. + /// @param a The field element to encode. + /// @return ret The field element in Montgomery form. + function intoMontgomeryForm(a) -> ret { + let hi := getHighestHalfOfMultiplication(a, R2_MOD_P()) + let lo := mul(a, R2_MOD_P()) + ret := REDC(lo, hi) + } + + /// @notice Decodes a field element out of the Montgomery form using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further details on transforming a field element out of the Montgomery form. + /// @param m The field element in Montgomery form to decode. + /// @return ret The decoded field element. + function outOfMontgomeryForm(m) -> ret { + let hi := 0 + let lo := m + ret := REDC(lo, hi) + } + + /// @notice Computes the Montgomery addition. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param augend The augend in Montgomery form. + /// @param addend The addend in Montgomery form. + /// @return ret The result of the Montgomery addition. + function montgomeryAdd(augend, addend) -> ret { + ret := add(augend, addend) + if iszero(lt(ret, P())) { + ret := sub(ret, P()) + } + } + + /// @notice Computes the Montgomery subtraction. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param minuend The minuend in Montgomery form. + /// @param subtrahend The subtrahend in Montgomery form. + /// @return ret The result of the Montgomery subtraction. + function montgomerySub(minuend, subtrahend) -> ret { + ret := montgomeryAdd(minuend, sub(P(), subtrahend)) + } + + /// @notice Computes the Montgomery multiplication using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param multiplicand The multiplicand in Montgomery form. + /// @param multiplier The multiplier in Montgomery form. + /// @return ret The result of the Montgomery multiplication. + function montgomeryMul(multiplicand, multiplier) -> ret { + let higherHalfOfProduct := getHighestHalfOfMultiplication(multiplicand, multiplier) + let lowestHalfOfProduct := mul(multiplicand, multiplier) + ret := REDC(lowestHalfOfProduct, higherHalfOfProduct) + } + + /// @notice Computes the Montgomery modular inverse skipping the Montgomery reduction step. + /// @dev The Montgomery reduction step is skept because a modification in the binary extended Euclidean algorithm is used to compute the modular inverse. + /// @dev See the function `binaryExtendedEuclideanAlgorithm` for further details. + /// @param a The field element in Montgomery form to compute the modular inverse of. + /// @return invmod The result of the Montgomery modular inverse (in Montgomery form). + function montgomeryModularInverse(a) -> invmod { + invmod := binaryExtendedEuclideanAlgorithm(a) + } + + /// @notice Computes the Montgomery division. + /// @dev The Montgomery division is computed by multiplying the dividend with the modular inverse of the divisor. + /// @param dividend The dividend in Montgomery form. + /// @param divisor The divisor in Montgomery form. + /// @return quotient The result of the Montgomery division. + function montgomeryDiv(dividend, divisor) -> quotient { + quotient := montgomeryMul(dividend, montgomeryModularInverse(divisor)) + } + + //////////////////////////////////////////////////////////////// + // FALLBACK + //////////////////////////////////////////////////////////////// + + // Retrieve the coordinates from the calldata + let x1 := calldataload(0) + let y1 := calldataload(32) + let x2 := calldataload(64) + let y2 := calldataload(96) + + let p1IsInfinity := isInfinity(x1, y1) + let p2IsInfinity := isInfinity(x2, y2) + + if and(p1IsInfinity, p2IsInfinity) { + // Infinity + Infinity = Infinity + mstore(0, 0) + mstore(32, 0) + return(0, 64) + } + if and(p1IsInfinity, iszero(p2IsInfinity)) { + // Infinity + P = P + + // Ensure that the coordinates are between 0 and the field order. + if or(iszero(isOnFieldOrder(x2)), iszero(isOnFieldOrder(y2))) { + burnGas() + } + + let m_x2 := intoMontgomeryForm(x2) + let m_y2 := intoMontgomeryForm(y2) + + // Ensure that the point is in the curve (Y^2 = X^3 + 3). + if iszero(pointIsInCurve(m_x2, m_y2)) { + burnGas() + } + + // We just need to go into the Montgomery form to perform the + // computations in pointIsInCurve, but we do not need to come back. + + mstore(0, x2) + mstore(32, y2) + return(0, 64) + } + if and(iszero(p1IsInfinity), p2IsInfinity) { + // P + Infinity = P + + // Ensure that the coordinates are between 0 and the field order. + if or(iszero(isOnFieldOrder(x1)), iszero(isOnFieldOrder(y1))) { + burnGas() + } + + let m_x1 := intoMontgomeryForm(x1) + let m_y1 := intoMontgomeryForm(y1) + + // Ensure that the point is in the curve (Y^2 = X^3 + 3). + if iszero(pointIsInCurve(m_x1, m_y1)) { + burnGas() + } + + // We just need to go into the Montgomery form to perform the + // computations in pointIsInCurve, but we do not need to come back. + + mstore(0, x1) + mstore(32, y1) + return(0, 64) + } + + // Ensure that the coordinates are between 0 and the field order. + if or(iszero(isOnFieldOrder(x1)), iszero(isOnFieldOrder(y1))) { + burnGas() + } + + // Ensure that the coordinates are between 0 and the field order. + if or(iszero(isOnFieldOrder(x2)), iszero(isOnFieldOrder(y2))) { + burnGas() + } + + // There's no need for transforming into Montgomery form + // for this case. + if and(eq(x1, x2), eq(submod(0, y1, P()), y2)) { + // P + (-P) = Infinity + + let m_x1 := intoMontgomeryForm(x1) + let m_y1 := intoMontgomeryForm(y1) + let m_x2 := intoMontgomeryForm(x2) + let m_y2 := intoMontgomeryForm(y2) + + // Ensure that the points are in the curve (Y^2 = X^3 + 3). + if or(iszero(pointIsInCurve(m_x1, m_y1)), iszero(pointIsInCurve(m_x2, m_y2))) { + burnGas() + } + + // We just need to go into the Montgomery form to perform the + // computations in pointIsInCurve, but we do not need to come back. + + mstore(0, 0) + mstore(32, 0) + return(0, 64) + } + + if and(eq(x1, x2), and(iszero(eq(y1, y2)), iszero(eq(y1, submod(0, y2, P()))))) { + burnGas() + } + + if and(eq(x1, x2), eq(y1, y2)) { + // P + P = 2P + + let x := intoMontgomeryForm(x1) + let y := intoMontgomeryForm(y1) + + // Ensure that the points are in the curve (Y^2 = X^3 + 3). + if iszero(pointIsInCurve(x, y)) { + burnGas() + } + + // (3 * x1^2 + a) / (2 * y1) + let x1_squared := montgomeryMul(x, x) + let slope := montgomeryDiv(addmod(x1_squared, addmod(x1_squared, x1_squared, P()), P()), addmod(y, y, P())) + // x3 = slope^2 - 2 * x1 + let x3 := submod(montgomeryMul(slope, slope), addmod(x, x, P()), P()) + // y3 = slope * (x1 - x3) - y1 + let y3 := submod(montgomeryMul(slope, submod(x, x3, P())), y, P()) + + x3 := outOfMontgomeryForm(x3) + y3 := outOfMontgomeryForm(y3) + + mstore(0, x3) + mstore(32, y3) + return(0, 64) + } + + // P1 + P2 = P3 + + x1 := intoMontgomeryForm(x1) + y1 := intoMontgomeryForm(y1) + x2 := intoMontgomeryForm(x2) + y2 := intoMontgomeryForm(y2) + + // Ensure that the points are in the curve (Y^2 = X^3 + 3). + if or(iszero(pointIsInCurve(x1, y1)), iszero(pointIsInCurve(x2, y2))) { + burnGas() + } + + // (y2 - y1) / (x2 - x1) + let slope := montgomeryDiv(submod(y2, y1, P()), submod(x2, x1, P())) + // x3 = slope^2 - x1 - x2 + let x3 := submod(montgomeryMul(slope, slope), addmod(x1, x2, P()), P()) + // y3 = slope * (x1 - x3) - y1 + let y3 := submod(montgomeryMul(slope, submod(x1, x3, P())), y1, P()) + + x3 := outOfMontgomeryForm(x3) + y3 := outOfMontgomeryForm(y3) + + mstore(0, x3) + mstore(32, y3) + return(0, 64) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/precompiles/EcMul.yul b/.test-node-subtree/etc/system-contracts/contracts/precompiles/EcMul.yul new file mode 100644 index 00000000..83c45ff0 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/precompiles/EcMul.yul @@ -0,0 +1,495 @@ +object "EcMul" { + code { + return(0, 0) + } + object "EcMul_deployed" { + code { + //////////////////////////////////////////////////////////////// + // CONSTANTS + //////////////////////////////////////////////////////////////// + + /// @notice Constant function for value one in Montgomery form. + /// @dev This value was precomputed using Python. + /// @return m_one The value one in Montgomery form. + function MONTGOMERY_ONE() -> m_one { + m_one := 6350874878119819312338956282401532409788428879151445726012394534686998597021 + } + + /// @notice Constant function for value three in Montgomery form. + /// @dev This value was precomputed using Python. + /// @return m_three The value three in Montgomery form. + function MONTGOMERY_THREE() -> m_three { + m_three := 19052624634359457937016868847204597229365286637454337178037183604060995791063 + } + + /// @notice Constant function for value 3*b (i.e. 9) in Montgomery form. + /// @dev This value was precomputed using Python. + /// @return m_b3 The value 9 in Montgomery form. + function MONTGOMERY_B3() -> m_b3 { + m_b3 := 13381388159399823366557795051099241510703237597767364208733475022892534956023 + } + + /// @notice Constant function for the alt_bn128 field order. + /// @dev See https://eips.ethereum.org/EIPS/eip-196 for further details. + /// @return ret The alt_bn128 field order. + function P() -> ret { + ret := 21888242871839275222246405745257275088696311157297823662689037894645226208583 + } + + /// @notice Constant function for the pre-computation of R^2 % N for the Montgomery REDC algorithm. + /// @dev R^2 is the Montgomery residue of the value 2^512. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value R^2 modulus the curve field order. + function R2_MOD_P() -> ret { + ret := 3096616502983703923843567936837374451735540968419076528771170197431451843209 + } + + /// @notice Constant function for the pre-computation of N' for the Montgomery REDC algorithm. + /// @dev N' is a value such that NN' = -1 mod R, with N being the curve field order. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value N'. + function N_PRIME() -> ret { + ret := 111032442853175714102588374283752698368366046808579839647964533820976443843465 + } + + // //////////////////////////////////////////////////////////////// + // HELPER FUNCTIONS + // //////////////////////////////////////////////////////////////// + + /// @dev Executes the `precompileCall` opcode. + function precompileCall(precompileParams, gasToBurn) -> ret { + // Compiler simulation for calling `precompileCall` opcode + ret := verbatim_2i_1o("precompile", precompileParams, gasToBurn) + } + + /// @notice Burns remaining gas until revert. + /// @dev This function is used to burn gas in the case of a failed precompile call. + function burnGas() { + // Precompiles that do not have a circuit counterpart + // will burn the provided gas by calling this function. + precompileCall(0, gas()) + } + + /// @notice Retrieves the highest half of the multiplication result. + /// @param multiplicand The value to multiply. + /// @param multiplier The multiplier. + /// @return ret The highest half of the multiplication result. + function getHighestHalfOfMultiplication(multiplicand, multiplier) -> ret { + ret := verbatim_2i_1o("mul_high", multiplicand, multiplier) + } + + /// @notice Computes an addition and checks for overflow. + /// @param augend The value to add to. + /// @param addend The value to add. + /// @return sum The sum of the two values. + /// @return overflowed True if the addition overflowed, false otherwise. + function overflowingAdd(augend, addend) -> sum, overflowed { + sum := add(augend, addend) + overflowed := lt(sum, augend) + } + + /// @notice Checks if the LSB of a number is 1. + /// @param x The number to check. + /// @return ret True if the LSB is 1, false otherwise. + function lsbIsOne(x) -> ret { + ret := and(x, 1) + } + + /// @notice Computes the inverse in Montgomery Form of a number in Montgomery Form. + /// @dev Reference: https://github.com/lambdaclass/lambdaworks/blob/main/math/src/field/fields/montgomery_backed_prime_fields.rs#L169 + /// @dev Let `base` be a number in Montgomery Form, then base = a*R mod P() being `a` the base number (not in Montgomery Form) + /// @dev Let `inv` be the inverse of a number `a` in Montgomery Form, then inv = a^(-1)*R mod P() + /// @dev The original binary extended euclidean algorithms takes a number a and returns a^(-1) mod N + /// @dev In our case N is P(), and we'd like the input and output to be in Montgomery Form (a*R mod P() + /// @dev and a^(-1)*R mod P() respectively). + /// @dev If we just pass the input as a number in Montgomery Form the result would be a^(-1)*R^(-1) mod P(), + /// @dev but we want it to be a^(-1)*R mod P(). + /// @dev For that, we take advantage of the algorithm's linearity and multiply the result by R^2 mod P() + /// @dev to get R^2*a^(-1)*R^(-1) mod P() = a^(-1)*R mod P() as the desired result in Montgomery Form. + /// @dev `inv` takes the value of `b` or `c` being the result sometimes `b` and sometimes `c`. In paper + /// @dev multiplying `b` or `c` by R^2 mod P() results on starting their values as b = R2_MOD_P() and c = 0. + /// @param base A number `a` in Montgomery Form, then base = a*R mod P(). + /// @return inv The inverse of a number `a` in Montgomery Form, then inv = a^(-1)*R mod P(). + function binaryExtendedEuclideanAlgorithm(base) -> inv { + let modulus := P() + let u := base + let v := modulus + // Avoids unnecessary reduction step. + let b := R2_MOD_P() + let c := 0 + + for {} and(iszero(eq(u, 1)), iszero(eq(v, 1))) {} { + for {} iszero(and(u, 1)) {} { + u := shr(1, u) + let current := b + switch and(current, 1) + case 0 { + b := shr(1, b) + } + case 1 { + b := shr(1, add(b, modulus)) + } + } + + for {} iszero(and(v, 1)) {} { + v := shr(1, v) + let current := c + switch and(current, 1) + case 0 { + c := shr(1, c) + } + case 1 { + c := shr(1, add(c, modulus)) + } + } + + switch gt(v, u) + case 0 { + u := sub(u, v) + if lt(b, c) { + b := add(b, modulus) + } + b := sub(b, c) + } + case 1 { + v := sub(v, u) + if lt(c, b) { + c := add(c, modulus) + } + c := sub(c, b) + } + } + + switch eq(u, 1) + case 0 { + inv := c + } + case 1 { + inv := b + } + } + + /// @notice Implementation of the Montgomery reduction algorithm (a.k.a. REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_The_REDC_algorithm + /// @param lowestHalfOfT The lowest half of the value T. + /// @param higherHalfOfT The higher half of the value T. + /// @return S The result of the Montgomery reduction. + function REDC(lowestHalfOfT, higherHalfOfT) -> S { + let m := mul(lowestHalfOfT, N_PRIME()) + let hi := add(higherHalfOfT, getHighestHalfOfMultiplication(m, P())) + let lo, overflowed := overflowingAdd(lowestHalfOfT, mul(m, P())) + if overflowed { + hi := add(hi, 1) + } + S := hi + if iszero(lt(hi, P())) { + S := sub(hi, P()) + } + } + + /// @notice Encodes a field element into the Montgomery form using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_The_REDC_algorithm for further details on transforming a field element into the Montgomery form. + /// @param a The field element to encode. + /// @return ret The field element in Montgomery form. + function intoMontgomeryForm(a) -> ret { + let hi := getHighestHalfOfMultiplication(a, R2_MOD_P()) + let lo := mul(a, R2_MOD_P()) + ret := REDC(lo, hi) + } + + /// @notice Decodes a field element out of the Montgomery form using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_The_REDC_algorithm for further details on transforming a field element out of the Montgomery form. + /// @param m The field element in Montgomery form to decode. + /// @return ret The decoded field element. + function outOfMontgomeryForm(m) -> ret { + let hi := 0 + let lo := m + ret := REDC(lo, hi) + } + + /// @notice Computes the Montgomery addition. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param augend The augend in Montgomery form. + /// @param addend The addend in Montgomery form. + /// @return ret The result of the Montgomery addition. + function montgomeryAdd(augend, addend) -> ret { + ret := add(augend, addend) + if iszero(lt(ret, P())) { + ret := sub(ret, P()) + } + } + + /// @notice Computes the Montgomery subtraction. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param minuend The minuend in Montgomery form. + /// @param subtrahend The subtrahend in Montgomery form. + /// @return ret The result of the Montgomery subtraction. + function montgomerySub(minuend, subtrahend) -> ret { + ret := montgomeryAdd(minuend, sub(P(), subtrahend)) + } + + /// @notice Computes the Montgomery multiplication using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param multiplicand The multiplicand in Montgomery form. + /// @param multiplier The multiplier in Montgomery form. + /// @return ret The result of the Montgomery multiplication. + function montgomeryMul(multiplicand, multiplier) -> ret { + let hi := getHighestHalfOfMultiplication(multiplicand, multiplier) + let lo := mul(multiplicand, multiplier) + ret := REDC(lo, hi) + } + + /// @notice Computes the Montgomery modular inverse skipping the Montgomery reduction step. + /// @dev The Montgomery reduction step is skept because a modification in the binary extended Euclidean algorithm is used to compute the modular inverse. + /// @dev See the function `binaryExtendedEuclideanAlgorithm` for further details. + /// @param a The field element in Montgomery form to compute the modular inverse of. + /// @return invmod The result of the Montgomery modular inverse (in Montgomery form). + function montgomeryModularInverse(a) -> invmod { + invmod := binaryExtendedEuclideanAlgorithm(a) + } + + /// @notice Checks if a coordinate is on the curve field order. + /// @dev A coordinate is on the curve field order if it is on the range [0, curveFieldOrder). + /// @param coordinate The coordinate to check. + /// @return ret True if the coordinate is in the range, false otherwise. + function coordinateIsOnFieldOrder(coordinate) -> ret { + ret := lt(coordinate, P()) + } + + /// @notice Checks if affine coordinates are on the curve field order. + /// @dev Affine coordinates are on the curve field order if both coordinates are on the range [0, curveFieldOrder). + /// @param x The x coordinate to check. + /// @param y The y coordinate to check. + /// @return ret True if the coordinates are in the range, false otherwise. + function affinePointCoordinatesAreOnFieldOrder(x, y) -> ret { + ret := and(coordinateIsOnFieldOrder(x), coordinateIsOnFieldOrder(y)) + } + + /// @notice Checks if projective coordinates are on the curve field order. + /// @dev Projective coordinates are on the curve field order if the coordinates are on the range [0, curveFieldOrder) and the z coordinate is not zero. + /// @param x The x coordinate to check. + /// @param y The y coordinate to check. + /// @param z The z coordinate to check. + /// @return ret True if the coordinates are in the range, false otherwise. + function projectivePointCoordinatesAreOnFieldOrder(x, y, z) -> ret { + let _x, _y := projectiveIntoAffine(x, y, z) + ret := and(z, affinePointCoordinatesAreOnFieldOrder(_x, _y)) + } + + // @notice Checks if a point in affine coordinates in Montgomery form is on the curve. + // @dev The curve in question is the alt_bn128 curve. + // @dev The Short Weierstrass equation of the curve is y^2 = x^3 + 3. + // @param x The x coordinate of the point in Montgomery form. + // @param y The y coordinate of the point in Montgomery form. + // @return ret True if the point is on the curve, false otherwise. + function affinePointIsOnCurve(x, y) -> ret { + let ySquared := montgomeryMul(y, y) + let xSquared := montgomeryMul(x, x) + let xQubed := montgomeryMul(xSquared, x) + let xQubedPlusThree := montgomeryAdd(xQubed, MONTGOMERY_THREE()) + + ret := eq(ySquared, xQubedPlusThree) + } + + /// @notice Checks if a point in affine coordinates is the point at infinity. + /// @dev The point at infinity is defined as the point (0, 0). + /// @dev See https://eips.ethereum.org/EIPS/eip-196 for further details. + /// @param x The x coordinate of the point in Montgomery form. + /// @param y The y coordinate of the point in Montgomery form. + /// @return ret True if the point is the point at infinity, false otherwise. + function affinePointIsInfinity(x, y) -> ret { + ret := and(iszero(x), iszero(y)) + } + + /// @notice Checks if a point in projective coordinates in Montgomery form is the point at infinity. + /// @dev The point at infinity is defined as the point (0, 0, 0). + /// @param x The x coordinate of the point in Montgomery form. + /// @param y The y coordinate of the point in Montgomery form. + /// @param z The z coordinate of the point in Montgomery form. + /// @return ret True if the point is the point at infinity, false otherwise. + function projectivePointIsInfinity(x, y, z) -> ret { + ret := iszero(z) + } + + /// @notice Converts a point in affine coordinates to projective coordinates in Montgomery form. + /// @dev The point at infinity is defined as the point (0, 0, 0). + /// @dev For performance reasons, the point is assumed to be previously checked to be on the + /// @dev curve and not the point at infinity. + /// @param xp The x coordinate of the point P in affine coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in affine coordinates in Montgomery form. + /// @return xr The x coordinate of the point P in projective coordinates in Montgomery form. + /// @return yr The y coordinate of the point P in projective coordinates in Montgomery form. + /// @return zr The z coordinate of the point P in projective coordinates in Montgomery form. + function projectiveFromAffine(xp, yp) -> xr, yr, zr { + xr := xp + yr := yp + zr := MONTGOMERY_ONE() + } + + /// @notice Converts a point in projective coordinates to affine coordinates in Montgomery form. + /// @dev See https://www.nayuki.io/page/elliptic-curve-point-addition-in-projective-coordinates for further details. + /// @dev Reverts if the point is not on the curve. + /// @param xp The x coordinate of the point P in projective coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in projective coordinates in Montgomery form. + /// @param zp The z coordinate of the point P in projective coordinates in Montgomery form. + /// @return xr The x coordinate of the point P in affine coordinates in Montgomery form. + /// @return yr The y coordinate of the point P in affine coordinates in Montgomery form. + function projectiveIntoAffine(xp, yp, zp) -> xr, yr { + if zp { + let zp_inv := montgomeryModularInverse(zp) + xr := montgomeryMul(xp, zp_inv) + yr := montgomeryMul(yp, zp_inv) + } + } + + /// @notice Doubles a point in projective coordinates in Montgomery form. + /// @dev See Algorithm 9 in https://eprint.iacr.org/2015/1060.pdf for further details. + /// @dev The point is assumed to be on the curve. + /// @dev It works correctly for the point at infinity. + /// @param xp The x coordinate of the point P in projective coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in projective coordinates in Montgomery form. + /// @param zp The z coordinate of the point P in projective coordinates in Montgomery form. + /// @return xr The x coordinate of the point 2P in projective coordinates in Montgomery form. + /// @return yr The y coordinate of the point 2P in projective coordinates in Montgomery form. + /// @return zr The z coordinate of the point 2P in projective coordinates in Montgomery form. + function projectiveDouble(xp, yp, zp) -> xr, yr, zr { + let t0 := montgomeryMul(yp, yp) + zr := montgomeryAdd(t0, t0) + zr := montgomeryAdd(zr, zr) + zr := montgomeryAdd(zr, zr) + let t1 := montgomeryMul(yp, zp) + let t2 := montgomeryMul(zp, zp) + t2 := montgomeryMul(MONTGOMERY_B3(), t2) + xr := montgomeryMul(t2, zr) + yr := montgomeryAdd(t0, t2) + zr := montgomeryMul(t1, zr) + t1 := montgomeryAdd(t2, t2) + t2 := montgomeryAdd(t1, t2) + t0 := montgomerySub(t0, t2) + yr := montgomeryMul(t0, yr) + yr := montgomeryAdd(xr, yr) + t1 := montgomeryMul(xp, yp) + xr := montgomeryMul(t0, t1) + xr := montgomeryAdd(xr, xr) + } + + //////////////////////////////////////////////////////////////// + // FALLBACK + //////////////////////////////////////////////////////////////// + + // Retrieve the coordinates from the calldata + let x := calldataload(0) + let y := calldataload(32) + if iszero(affinePointCoordinatesAreOnFieldOrder(x, y)) { + burnGas() + } + let scalar := calldataload(64) + + if affinePointIsInfinity(x, y) { + // Infinity * scalar = Infinity + return(0x00, 0x40) + } + + let m_x := intoMontgomeryForm(x) + let m_y := intoMontgomeryForm(y) + + // Ensure that the point is in the curve (Y^2 = X^3 + 3). + if iszero(affinePointIsOnCurve(m_x, m_y)) { + burnGas() + } + + if eq(scalar, 0) { + // P * 0 = Infinity + return(0x00, 0x40) + } + if eq(scalar, 1) { + // P * 1 = P + mstore(0x00, x) + mstore(0x20, y) + return(0x00, 0x40) + } + + let xp, yp, zp := projectiveFromAffine(m_x, m_y) + + if eq(scalar, 2) { + let xr, yr, zr := projectiveDouble(xp, yp, zp) + + xr, yr := projectiveIntoAffine(xr, yr, zr) + xr := outOfMontgomeryForm(xr) + yr := outOfMontgomeryForm(yr) + + mstore(0x00, xr) + mstore(0x20, yr) + return(0x00, 0x40) + } + + let xq := xp + let yq := yp + let zq := zp + let xr := 0 + let yr := MONTGOMERY_ONE() + let zr := 0 + for {} scalar {} { + if lsbIsOne(scalar) { + let rIsInfinity := projectivePointIsInfinity(xr, yr, zr) + + if rIsInfinity { + // Infinity + P = P + xr := xq + yr := yq + zr := zq + + xq, yq, zq := projectiveDouble(xq, yq, zq) + // Check next bit + scalar := shr(1, scalar) + continue + } + + let t0 := montgomeryMul(yq, zr) + let t1 := montgomeryMul(yr, zq) + let t := montgomerySub(t0, t1) + let u0 := montgomeryMul(xq, zr) + let u1 := montgomeryMul(xr, zq) + let u := montgomerySub(u0, u1) + + // t = (yq*zr - yr*zq); u = (xq*zr - xr*zq) + if iszero(or(t, u)) { + // P + P = 2P + xr, yr, zr := projectiveDouble(xr, yr, zr) + + xq := xr + yq := yr + zq := zr + // Check next bit + scalar := shr(1, scalar) + continue + } + + // P1 + P2 = P3 + let u2 := montgomeryMul(u, u) + let u3 := montgomeryMul(u2, u) + let v := montgomeryMul(zq, zr) + let w := montgomerySub(montgomeryMul(montgomeryMul(t, t), v), montgomeryMul(u2, montgomeryAdd(u0, u1))) + + xr := montgomeryMul(u, w) + yr := montgomerySub(montgomeryMul(t, montgomerySub(montgomeryMul(u0, u2), w)), montgomeryMul(t0, u3)) + zr := montgomeryMul(u3, v) + } + + xq, yq, zq := projectiveDouble(xq, yq, zq) + // Check next bit + scalar := shr(1, scalar) + } + + xr, yr := projectiveIntoAffine(xr, yr, zr) + xr := outOfMontgomeryForm(xr) + yr := outOfMontgomeryForm(yr) + + mstore(0, xr) + mstore(32, yr) + return(0, 64) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/precompiles/EcPairing.yul b/.test-node-subtree/etc/system-contracts/contracts/precompiles/EcPairing.yul new file mode 100644 index 00000000..0d5cadb7 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/precompiles/EcPairing.yul @@ -0,0 +1,1669 @@ +object "EcPairing" { + code { } + object "EcPairing_deployed" { + code { + // CONSTANTS + + /// @notice Constant function for value one in Montgomery form. + /// @dev This value was precomputed using Python. + /// @return m_one The value one in Montgomery form. + function MONTGOMERY_ONE() -> m_one { + m_one := 6350874878119819312338956282401532409788428879151445726012394534686998597021 + } + + /// @notice Constant function for value three in Montgomery form. + /// @dev This value was precomputed using Python. + /// @return m_three The value three in Montgomery form. + function MONTGOMERY_THREE() -> m_three { + m_three := 19052624634359457937016868847204597229365286637454337178037183604060995791063 + } + + /// @notice Constant function for the inverse of two on the alt_bn128 group in Montgomery form. + /// @dev This value was precomputed using Python. + /// @return two_inv The value of the inverse of two on the alt_bn128 group in Montgomery form. + function MONTGOMERY_TWO_INV() -> two_inv { + two_inv := 14119558874979547267292681013829403749242370018224634694350716214666112402802 + } + /// @notice constant function for the coeffitients of the sextic twist of the BN256 curve. + /// @dev E': y' ** 2 = x' ** 3 + 3 / (3 + u) + /// @dev the curve E' is defined over Fp2 elements. + /// @dev See https://hackmd.io/@jpw/bn254#Twists for further details. + /// @return coefficients of the sextic twist of the BN256 curve + function MONTGOMERY_TWISTED_CURVE_COEFFS() -> z0, z1 { + z0 := 16772280239760917788496391897731603718812008455956943122563801666366297604776 + z1 := 568440292453150825972223760836185707764922522371208948902804025364325400423 + } + + /// @notice Constant function for the alt_bn128 group order. + /// @dev See https://eips.ethereum.org/EIPS/eip-196 for further details. + /// @return ret The alt_bn128 group order. + function P() -> ret { + ret := 21888242871839275222246405745257275088696311157297823662689037894645226208583 + } + + /// @notice Constant function for the twisted curve subgroup order. + /// @dev See https://hackmd.io/@jpw/bn254#Parameter-for-BN254 for further details. + /// @return ret The twisted curve subgroup orde. + function TWISTED_SUBGROUP_ORDER() -> ret { + ret := 21888242871839275222246405745257275088548364400416034343698204186575808495617 + } + + /// @notice Constant function for the pre-computation of R^2 % N for the Montgomery REDC algorithm. + /// @dev R^2 is the Montgomery residue of the value 2^512. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value R^2 modulus the curve group order. + function R2_MOD_P() -> ret { + ret := 3096616502983703923843567936837374451735540968419076528771170197431451843209 + } + + /// @notice Constant function for the pre-computation of N' for the Montgomery REDC algorithm. + /// @dev N' is a value such that NN' = -1 mod R, with N being the curve group order. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value N'. + function N_PRIME() -> ret { + ret := 111032442853175714102588374283752698368366046808579839647964533820976443843465 + } + + /// @notice Constant function for decimal representation of the NAF for the Millers Loop. + /// @dev Millers loop uses to iterate the NAF representation of the value t = 6x^2 + 1. Where x = 4965661367192848881 is a parameter of the BN 256 curve. + /// @dev For details of the x parameter: https://hackmd.io/@jpw/bn254#Barreto-Naehrig-curves. + /// @dev A NAF representation uses values: -1, 0 and 1. https://en.wikipedia.org/wiki/Non-adjacent_form. + /// @dev For iterating between this values we represent the 0 as 001, the 1 as 010 and the -1 as 100. + /// @dev Then we concatenate all and represent the result as a decimal. E.g. [0,-1,0,1] -> 001 100 001 010 -> 778 + /// @dev In each step of the iteration we just need to compute the operation AND between the number and 1, 2 and 4 to check the original value. + /// @dev Finally we shift 3 bits to the right to get the next value. + /// @dev For this implementation, the first two iterations of the Miller loop are skipped, so the last two digits of the NAF representation of t are not used. + /// @dev This value was precomputed using Python. + /// @return ret The value of the decimal representation of the NAF. + function NAF_REPRESENTATIVE() -> ret { + ret := 112285798093791963372401816628038344551273221779706221137 + } + + /// @notice Constant function for the zero element in Fp6 representation. + /// @return z00, z01, z10, z11, z20, z21 The values of zero in Fp6. + function FP6_ZERO() -> z00, z01, z10, z11, z20, z21 { + z00 := 0 + z01 := 0 + z10 := 0 + z11 := 0 + z20 := 0 + z21 := 0 + } + + /// @notice Constant function for the zero element in the twisted cuve on affine representation. + /// @return z00, z01, z10, z11, z20, z21 The values of infinity point on affine representation. + function G2_INFINITY() -> z00, z01, z02, z10, z11, z12 { + z00 := 0 + z01 := 0 + z02 := 0 + z10 := 0 + z11 := 0 + z12 := 0 + } + + /// @notice Constant function for element one in Fp12 representation. + /// @return the values of one in Fp12. + function FP12_ONE() -> z000, z001, z010, z011, z100, z101, z110, z111, z200, z201, z210, z211 { + z000 := MONTGOMERY_ONE() + z001 := 0 + z010 := 0 + z011 := 0 + z100 := 0 + z101 := 0 + z110 := 0 + z111 := 0 + z200 := 0 + z201 := 0 + z210 := 0 + z211 := 0 + } + + /// @notice Constant function for the lenght of the input of a single pair of points to compute the pairing. + /// @return ret The lenght of a pair of points input. + function PAIR_LENGTH() -> ret { + ret := 0xc0 + } + + // HELPER FUNCTIONS + + /// @dev Executes the `precompileCall` opcode. + function precompileCall(precompileParams, gasToBurn) -> ret { + // Compiler simulation for calling `precompileCall` opcode + ret := verbatim_2i_1o("precompile", precompileParams, gasToBurn) + } + + /// @notice Burns remaining gas until revert. + /// @dev This function is used to burn gas in the case of a failed precompile call. + function burnGas() { + // Precompiles that do not have a circuit counterpart + // will burn the provided gas by calling this function. + precompileCall(0, gas()) + } + + /// @notice Calculate the bit length of a number. + /// @param x The number to calculate the bit length of. + /// @return ret The bit length of the number. + function bitLen(x) -> ret { + ret := 0 + for {} x {} { + ret := add(ret, 1) + x := shr(1, x) + } + } + + /// @notice Checks if the bit of a number at a given index is 1. + /// @dev The index is counted from the right, starting at 0. + /// @param index The index of the bit to check. + /// @param n The number to check the bit of. + /// @return ret The value of the bit at the given index. + function checkBit(index, n) -> ret { + ret := and(shr(index, n), 1) + } + + // MONTGOMERY + + /// @notice Computes the inverse in Montgomery Form of a number in Montgomery Form. + /// @dev Reference: https://github.com/lambdaclass/lambdaworks/blob/main/math/src/field/fields/montgomery_backed_prime_fields.rs#L169 + /// @dev Let `base` be a number in Montgomery Form, then base = a*R mod P() being `a` the base number (not in Montgomery Form) + /// @dev Let `inv` be the inverse of a number `a` in Montgomery Form, then inv = a^(-1)*R mod P() + /// @dev The original binary extended euclidean algorithms takes a number a and returns a^(-1) mod N + /// @dev In our case N is P(), and we'd like the input and output to be in Montgomery Form (a*R mod P() + /// @dev and a^(-1)*R mod P() respectively). + /// @dev If we just pass the input as a number in Montgomery Form the result would be a^(-1)*R^(-1) mod P(), + /// @dev but we want it to be a^(-1)*R mod P(). + /// @dev For that, we take advantage of the algorithm's linearity and multiply the result by R^2 mod P() + /// @dev to get R^2*a^(-1)*R^(-1) mod P() = a^(-1)*R mod P() as the desired result in Montgomery Form. + /// @dev `inv` takes the value of `b` or `c` being the result sometimes `b` and sometimes `c`. In paper + /// @dev multiplying `b` or `c` by R^2 mod P() results on starting their values as b = R2_MOD_P() and c = 0. + /// @param base A number `a` in Montgomery Form, then base = a*R mod P(). + /// @return inv The inverse of a number `a` in Montgomery Form, then inv = a^(-1)*R mod P(). + function binaryExtendedEuclideanAlgorithm(base) -> inv { + let modulus := P() + let u := base + let v := modulus + // Avoids unnecessary reduction step. + let b := R2_MOD_P() + let c := 0 + + for {} and(iszero(eq(u, 1)), iszero(eq(v, 1))) {} { + for {} iszero(and(u, 1)) {} { + u := shr(1, u) + let current := b + switch and(current, 1) + case 0 { + b := shr(1, b) + } + case 1 { + b := shr(1, add(b, modulus)) + } + } + + for {} iszero(and(v, 1)) {} { + v := shr(1, v) + let current := c + switch and(current, 1) + case 0 { + c := shr(1, c) + } + case 1 { + c := shr(1, add(c, modulus)) + } + } + + switch gt(v, u) + case 0 { + u := sub(u, v) + if lt(b, c) { + b := add(b, modulus) + } + b := sub(b, c) + } + case 1 { + v := sub(v, u) + if lt(c, b) { + c := add(c, modulus) + } + c := sub(c, b) + } + } + + switch eq(u, 1) + case 0 { + inv := c + } + case 1 { + inv := b + } + } + + /// @notice Computes an addition and checks for overflow. + /// @param augend The value to add to. + /// @param addend The value to add. + /// @return sum The sum of the two values. + /// @return overflowed True if the addition overflowed, false otherwise. + function overflowingAdd(augend, addend) -> sum, overflowed { + sum := add(augend, addend) + overflowed := lt(sum, augend) + } + + /// @notice Retrieves the highest half of the multiplication result. + /// @param multiplicand The value to multiply. + /// @param multiplier The multiplier. + /// @return ret The highest half of the multiplication result. + function getHighestHalfOfMultiplication(multiplicand, multiplier) -> ret { + ret := verbatim_2i_1o("mul_high", multiplicand, multiplier) + } + + /// @notice Implementation of the Montgomery reduction algorithm (a.k.a. REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm + /// @param lowestHalfOfT The lowest half of the value T. + /// @param higherHalfOfT The higher half of the value T. + /// @return S The result of the Montgomery reduction. + function REDC(lowest_half_of_T, higher_half_of_T) -> S { + let q := mul(lowest_half_of_T, N_PRIME()) + let a_high := add(higher_half_of_T, getHighestHalfOfMultiplication(q, P())) + let a_low, overflowed := overflowingAdd(lowest_half_of_T, mul(q, P())) + if overflowed { + a_high := add(a_high, 1) + } + S := a_high + if iszero(lt(a_high, P())) { + S := sub(a_high, P()) + } + } + + /// @notice Encodes a field element into the Montgomery form using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further details on transforming a field element into the Montgomery form. + /// @param a The field element to encode. + /// @return ret The field element in Montgomery form. + function intoMontgomeryForm(a) -> ret { + let hi := getHighestHalfOfMultiplication(a, R2_MOD_P()) + let lo := mul(a, R2_MOD_P()) + ret := REDC(lo, hi) + } + + /// @notice Decodes a field element out of the Montgomery form using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further details on transforming a field element out of the Montgomery form. + /// @param m The field element in Montgomery form to decode. + /// @return ret The decoded field element. + function outOfMontgomeryForm(m) -> ret { + let higher_half_of_m := 0 + let lowest_half_of_m := m + ret := REDC(lowest_half_of_m, higher_half_of_m) + } + + /// @notice Computes the Montgomery addition. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param augend The augend in Montgomery form. + /// @param addend The addend in Montgomery form. + /// @return ret The result of the Montgomery addition. + function montgomeryAdd(augend, addend) -> ret { + ret := add(augend, addend) + if iszero(lt(ret, P())) { + ret := sub(ret, P()) + } + } + + /// @notice Computes the Montgomery subtraction. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param minuend The minuend in Montgomery form. + /// @param subtrahend The subtrahend in Montgomery form. + /// @return ret The result of the Montgomery addition. + function montgomerySub(minuend, subtrahend) -> ret { + ret := montgomeryAdd(minuend, sub(P(), subtrahend)) + } + + /// @notice Computes the Montgomery multiplication using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param multiplicand The multiplicand in Montgomery form. + /// @param multiplier The multiplier in Montgomery form. + /// @return ret The result of the Montgomery multiplication. + function montgomeryMul(multiplicand, multiplier) -> ret { + let higher_half_of_product := getHighestHalfOfMultiplication(multiplicand, multiplier) + let lowest_half_of_product := mul(multiplicand, multiplier) + ret := REDC(lowest_half_of_product, higher_half_of_product) + } + + /// @notice Computes the Montgomery modular inverse skipping the Montgomery reduction step. + /// @dev The Montgomery reduction step is skept because a modification in the binary extended Euclidean algorithm is used to compute the modular inverse. + /// @dev See the function `binaryExtendedEuclideanAlgorithm` for further details. + /// @param a The field element in Montgomery form to compute the modular inverse of. + /// @return invmod The result of the Montgomery modular inverse (in Montgomery form). + function montgomeryModularInverse(a) -> invmod { + invmod := binaryExtendedEuclideanAlgorithm(a) + } + + // CURVE ARITHMETICS + + /// @notice Checks if a coordinate is on the curve group order. + /// @dev A coordinate is on the curve group order if it is on the range [0, curveFieldOrder). + /// @param coordinate The coordinate to check. + /// @return ret True if the coordinate is in the range, false otherwise. + function coordinateIsOnFieldOrder(coordinate) -> ret { + ret := lt(coordinate, P()) + } + + // G1 + + /// @notice Checks if a point of the G1 curve is infinity. + /// @dev In affine coordinates the infinity is represented by the point (0,0). + /// @param x The x coordinate to check. + /// @param y The y coordinate to check. + /// @return ret True if the point is infinity, false otherwise. + function g1AffinePointIsInfinity(x, y) -> ret { + ret := iszero(or(x, y)) + } + + /// @notice Checks if a point in affine coordinates in Montgomery form is on the curve. + /// @dev The curve in question is the alt_bn128 curve. + /// @dev The Short Weierstrass equation of the curve is y^2 = x^3 + 3. + /// @param x The x coordinate of the point in Montgomery form. + /// @param y The y coordinate of the point in Montgomery form. + /// @return ret True if the point is on the curve, false otherwise. + function g1AffinePointIsOnCurve(x, y) -> ret { + let ySquared := montgomeryMul(y, y) + let xSquared := montgomeryMul(x, x) + let xQubed := montgomeryMul(xSquared, x) + let xQubedPlusThree := montgomeryAdd(xQubed, MONTGOMERY_THREE()) + + ret := eq(ySquared, xQubedPlusThree) + } + + // G2 + + /// @notice Converts a G2 point in affine coordinates to projective coordinates. + /// @dev Both input and output coordinates are encoded in Montgomery form. + /// @dev If x and y differ from 0, just add z = (1,0). + /// @dev If x and y are equal to 0, then P is the infinity point, and z = (0,0). + /// @param xp0, xp1 The x coordinate to trasnform. + /// @param yp0, yp1 The y coordinate to transform. + /// @return xr0, xr1, yr0, yr1, zr0, zr1 The projectives coordinates of the given G2 point. + function g2ProjectiveFromAffine(xp0, xp1, yp0, yp1) -> xr0, xr1, yr0, yr1, zr0, zr1 { + xr0 := xp0 + xr1 := xp1 + yr0 := yp0 + yr1 := yp1 + zr0 := MONTGOMERY_ONE() + zr1 := 0 + if and(eq(xp0, 0), eq(xp1, 0)) { + if and(eq(yp0, 0), eq(yp1, 0)) { + xr0 := MONTGOMERY_ONE() + // xr1 is already 0 + yr0 := MONTGOMERY_ONE() + // yr1 is already 0 + zr0 := 0 + // zr1 is already 0 + } + } + } + + /// @notice Checks if a G2 point in affine coordinates is the point at infinity. + /// @dev The coordinates are encoded in Montgomery form. + /// @dev in Affine coordinates the point represents the infinity if both coordinates are 0. + /// @param x0, x1 The x coordinate to check. + /// @param y0, y1 The y coordinate to check. + /// @return ret True if the point is the point at infinity, false otherwise. + function g2AffinePointIsInfinity(x0, x1, y0, y1) -> ret { + ret := iszero(or(or(x0, x1), or(y0, y1))) + } + + /// @notice Checks if a G2 point in affine coordinates belongs to the twisted curve. + /// @dev The coordinates are encoded in Montgomery form. + /// @dev in Affine coordinates the point belongs to the curve if it satisfies the equation: y^3 = x^2 + 3/(9+u). + /// @dev See https://hackmd.io/@jpw/bn254#Twists for further details. + /// @param x0, x1 The x coordinate to check. + /// @param y0, y1 The y coordinate to check. + /// @return ret True if the point is in the curve, false otherwise. + function g2AffinePointIsOnCurve(x0, x1, y0, y1) -> ret { + let a0, a1 := MONTGOMERY_TWISTED_CURVE_COEFFS() + let b0, b1 := fp2Mul(x0, x1, x0, x1) + b0, b1 := fp2Mul(b0, b1, x0, x1) + b0, b1 := fp2Add(b0, b1, a0, a1) + let c0, c1 := fp2Mul(y0, y1, y0, y1) + ret := and(eq(b0, c0), eq(b1, c1)) + } + + /// @notice Checks if a G2 point in projective coordinates is the point at infinity. + /// @dev The coordinates are encoded in Montgomery form. + /// @dev A projective point is at infinity if the z coordinate is (0, 0). + /// @param x0, x1 The x coordinate of the point. + /// @param y0, y1 The y coordinate of the point. + /// @param z0, z1 The z coordinate of the point. + /// @return ret True if the point is the point at infinity, false otherwise. + function g2ProjectivePointIsInfinity(x0, x1, y0, y1, z0, z1) -> ret { + ret := iszero(or(z0, z1)) + } + + /// @notice Negates a G2 point in affine coordinates. + /// @dev The coordinates are encoded in Montgomery form. + /// @dev The negation of a point (x, y) is (x, -y). + /// @param x0, x1 The x coordinate of the point. + /// @param y0, y1 The y coordinate of the point. + /// @return nx0, nx1, ny0, ny1 The coordinates of the negated point. + function g2AffineNeg(x0, x1, y0, y1) -> nx0, nx1, ny0, ny1 { + nx0 := x0 + nx1 := x1 + ny0, ny1 := fp2Neg(y0, y1) + } + + /// @notice Check if a G2 point in jacobian coordinates is in the subgroup of the twisted curve. + /// @dev The coordinates are encoded in Montgomery form. + /// @param xp0, xp1 The x coordinate of the point. + /// @param yp0, yp1 The y coordinate of the point. + /// @param zp0, zp1 The z coordinate of the point. + /// @return ret True if the point is in the subgroup, false otherwise. + function g2IsInSubGroup(xp0, xp1, yp0, yp1, zp0, zp1) -> ret { + let xr0, xr1, yr0, yr1, zr0, zr1 := g2ScalarMul(xp0, xp1, yp0, yp1, zp0, zp1, TWISTED_SUBGROUP_ORDER()) + ret := and(iszero(zr0), iszero(zr1)) + } + + /// @notice Double a g2 point represented in jacobian coordinates. + /// @dev The coordinates must be encoded in Montgomery form. + /// @param xp0, xp1 The x coordinate of the point. + /// @param yp0, yp1 The y coordinate of the point. + /// @param zp0, zp1 The z coordinate of the point. + /// @return xr0, xr1, yr0, yr1, zr0, zr1 The coordinates of the doubled point. + function g2JacobianDouble(xp0, xp1, yp0, yp1, zp0, zp1) -> xr0, xr1, yr0, yr1, zr0, zr1 { + let a00, a01 := fp2Mul(xp0, xp1, xp0, xp1) // A = X1^2 + let b00, b01 := fp2Mul(yp0, yp1, yp0, yp1) // B = Y1^2 + let c00, c01 := fp2Mul(b00, b01, b00, b01) // C = B^2 + let t00, t01 := fp2Add(xp0, xp1, b00, b01) // t0 = X1+B + let t10, t11 := fp2Mul(t00, t01, t00, t01) // t1 = t0^2 + let t20, t21 := fp2Sub(t10, t11, a00, a01) // t2 = t1-A + let t30, t31 := fp2Sub(t20, t21, c00, c01) // t3 = t2-C + let d00, d01 := fp2Add(t30, t31, t30, t31) // D = 2*t3 + let e00, e01 := fp2Add(a00, a01, a00, a01) // E = 3*A + e00, e01 := fp2Add(e00, e01, a00, a01) + let f00, f01 := fp2Mul(e00, e01, e00, e01) // F = E^2 + let t40, t41 := fp2Add(d00, d01, d00, d01) // t4 = 2*D + xr0, xr1 := fp2Sub(f00, f01, t40, t41) // X3 = F-t4 + let t50, t51 := fp2Sub(d00, d01, xr0, xr1) // t5 = D-X3 + let t60, t61 := fp2Add(c00, c01, c00, c01) // t6 = 8*C + t60, t61 := fp2Add(t60, t61, t60, t61) + t60, t61 := fp2Add(t60, t61, t60, t61) + let t70, t71 := fp2Mul(e00, e01, t50, t51) // t7 = E*t5 + yr0, yr1 := fp2Sub(t70, t71, t60, t61) // Y3 = t7-t6 + let t80, t81 := fp2Mul(yp0, yp1, zp0, zp1) // t8 = Y1*Z1 + zr0, zr1 := fp2Add(t80, t81, t80, t81) // Z3 = 2*t8 + } + + /// @notice Add two g2 points represented in jacobian coordinates. + /// @dev The coordinates must be encoded in Montgomery form. + /// @param xq0, xq1 The x coordinate of the first point. + /// @param yq0, yq1 The y coordinate of the first point. + /// @param zq0, zq1 The z coordinate of the first point. + /// @param xr0, xr1 The x coordinate of the second point. + /// @param yr0, yr1 The y coordinate of the second point. + /// @param zr0, zr1 The z coordinate of the second point. + /// @return c00, c01, c10, c11, c20, c21 The coordinates of the added points. + function g2JacobianAdd(xq0, xq1, yq0, yq1, zq0, zq1, xr0, xr1, yr0, yr1, zr0, zr1) -> c00, c01, c10, c11, c20, c21 { + // Check for infinity in projective coordinates is the same as jacobian + let qIsInfinity := g2ProjectivePointIsInfinity(xq0, xq1, yq0, yq1, zq0, zq1) + let rIsInfinity := g2ProjectivePointIsInfinity(xr0, xr1, yr0, yr1, zr0, zr1) + if and(rIsInfinity, qIsInfinity) { + // Infinity + Infinity = Infinity + leave + } + if rIsInfinity { + // Infinity + P = P + c00 := xq0 + c01 := xq1 + c10 := yq0 + c11 := yq1 + c20 := zq0 + c21 := zq1 + leave + } + if qIsInfinity { + // P + Infinity = P + c00 := xr0 + c01 := xr1 + c10 := yr0 + c11 := yr1 + c20 := zr0 + c21 := zr1 + leave + } + + // Z1Z1 = Z1^2 + let zqzq0, zqzq1 := fp2Mul(zq0, zq1, zq0, zq1) + // Z2Z2 = Z2^2 + let zrzr0, zrzr1 := fp2Mul(zr0, zr1, zr0, zr1) + // U1 = X1*Z2Z2 + let u0, u1 := fp2Mul(xq0, xq1, zrzr0, zrzr1) + // U2 = X2*Z1Z1 + let u2, u3 := fp2Mul(xr0, xr1, zqzq0, zqzq1) + // t0 = Z2*Z2Z2 + let t0, t1 := fp2Mul(zr0, zr1, zrzr0, zrzr1) + // S1 = Y1*t0 + let s0, s1 := fp2Mul(yq0, yq1, t0, t1) + // t1 = Z1*Z1Z1 + let t2, t3 := fp2Mul(zq0, zq1, zqzq0, zqzq1) + // S2 = Y2*t1 + let s2, s3 := fp2Mul(yr0, yr1, t2, t3) + // H = U2-U1 + let h0, h1 := fp2Sub(u2, u3, u0, u1) + // t2 = 2*H + let t4, t5 := fp2Add(h0, h1, h0, h1) + // I = t2^2 + let i0, i1 := fp2Mul(t4, t5, t4, t5) + // J = H*I + let j0, j1 := fp2Mul(h0, h1, i0, i1) + // t3 = S2-S1 + let t6, t7 := fp2Sub(s2, s3, s0, s1) + // r = 2*t3 + let r0, r1 := fp2Add(t6, t7, t6, t7) + // V = U1*I + let v0, v1 := fp2Mul(u0, u1, i0, i1) + // t4 = r^2 + let t8, t9 := fp2Mul(r0, r1, r0, r1) + // t5 = 2*V + let t10, t11 := fp2Add(v0, v1, v0, v1) + // t6 = t4-J + let t12, t13 := fp2Sub(t8, t9, j0, j1) + // X3 = t6-t5 + c00, c01 := fp2Sub(t12, t13, t10, t11) + // t7 = V-X3 + let t14, t15 := fp2Sub(v0, v1, c00, c01) + // t8 = S1*J + let t16, t17 := fp2Mul(s0, s1, j0, j1) + // t9 = 2*t8 + let t18, t19 := fp2Add(t16, t17, t16, t17) + // t10 = r*t7 + let t20, t21 := fp2Mul(r0, r1, t14, t15) + // Y3 = t10-t9 + c10, c11 := fp2Sub(t20, t21, t18, t19) + // t11 = Z1+Z2 + let t22, t23 := fp2Add(zq0, zq1, zr0, zr1) + // t12 = t11^2 + let t24, t25 := fp2Mul(t22, t23, t22, t23) + // t13 = t12-Z1Z1 + let t26, t27 := fp2Sub(t24, t25, zqzq0, zqzq1) + // t14 = t13-Z2Z2 + let t28, t29 := fp2Sub(t26, t27, zrzr0, zrzr1) + // Z3 = t14*H + c20, c21 := fp2Mul(t28, t29, h0, h1) + } + + /// @notice Multiplies a G2 point represented in jacobian coordinates by a scalar. + /// @dev The coordinates must be encoded in Montgomery form. + /// @dev The scalar must not be encoded in Montgomery form. + /// @param xp0, xp1 The x coordinate of the point. + /// @param yp0, yp1 The y coordinate of the point. + /// @param zp0, zp1 The z coordinate of the point. + /// @param scalar The scalar to multiply the point by. + /// @return xr0, xr1, yr0, yr1, zr0, zr1 The coordinates of the multiplied point. + function g2ScalarMul(xp0, xp1, yp0, yp1, zp0, zp1, scalar) -> xr0, xr1, yr0, yr1, zr0, zr1 { + let scalarBitIndex := bitLen(scalar) + switch scalar + case 0x02 { + xr0, xr1, yr0, yr1, zr0, zr1 := g2JacobianDouble(xp0, xp1, yp0, yp1, zp0, yp1) + } + default { + xr0 := 0 + xr1 := 0 + yr0 := MONTGOMERY_ONE() + yr1 := 0 + zr0 := 0 + zr1 := 0 + for {} scalarBitIndex {} { + scalarBitIndex := sub(scalarBitIndex, 1) + xr0, xr1, yr0, yr1, zr0, zr1 := g2JacobianDouble(xr0, xr1, yr0, yr1, zr0, zr1) + let bitindex := checkBit(scalarBitIndex, scalar) + if bitindex { + xr0, xr1, yr0, yr1, zr0, zr1 := g2JacobianAdd(xp0, xp1, yp0, yp1, zp0, zp1, xr0, xr1, yr0, yr1, zr0, zr1) + } + + } + } + } + + // FP2 ARITHMETHICS + + /// @notice Computes the sum of two Fp2 elements. + /// @dev Algorithm 5 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01 The coefficients of the A element to sum. + /// @param b00, b01 The coefficients of the B element to sum. + /// @return c00, c01 The coefficients of the element C = A + B. + function fp2Add(a00, a01, b00, b01) -> c00, c01 { + c00 := montgomeryAdd(a00, b00) + c01 := montgomeryAdd(a01, b01) + } + + /// @notice Computes the subtraction of two Fp2 elements. + /// @dev Algorithm 6 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01 The coefficients of the minuend A. + /// @param b00, b01 The coefficients of the subtrahend B. + /// @return c00, c01 The coefficients of the element C = A - B. + function fp2Sub(a00, a01, b00, b01) -> c00, c01 { + c00 := montgomerySub(a00, b00) + c01 := montgomerySub(a01, b01) + } + + /// @notice Computes the multiplication between a Fp2 element a Fp element. + /// @dev Algorithm 7 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01 The coefficients of the Fp2 element A. + /// @param scalar The value of the Fp element k. + /// @return c00, c01 The coefficients of the element C = k * A. + function fp2ScalarMul(a00, a01, scalar) -> c00, c01 { + c00 := montgomeryMul(a00, scalar) + c01 := montgomeryMul(a01, scalar) + } + + /// @notice Computes the multiplication between two Fp2 elements. + /// @dev Algorithm 7 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01 The coefficients of the Fp2 element A. + /// @param a00, a01 The coefficients of the Fp2 element B. + /// @return c00, c01 The coefficients of the element C = A * B. + function fp2Mul(a00, a01, b00, b01) -> c00, c01 { + c00 := montgomerySub(montgomeryMul(a00, b00), montgomeryMul(a01, b01)) + c01 := montgomeryAdd(montgomeryMul(a00, b01), montgomeryMul(a01, b00)) + } + + /// @notice Computes the negative of a Fp2 elements. + /// @param a00, a01 The coefficients of the Fp2 element A. + /// @return c00, c01 The coefficients of the element C = -A. + function fp2Neg(a00, a01) -> c00, c01 { + c00, c01 := fp2Sub(0, 0, a00, a01) + } + + /// @notice Computes the inverse of a Fp2 element. + /// @dev Algorithm 8 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01 The coefficients of the Fp2 element A. + /// @return c00, c01 The coefficients of the element C = A^(-1). + function fp2Inv(a00, a01) -> c00, c01 { + let t0 := montgomeryMul(a00, a00) + let t1 := montgomeryMul(a01, a01) + t0 := montgomeryAdd(t0, t1) + t1 := montgomeryModularInverse(t0) + + c00 := montgomeryMul(a00, t1) + c01 := montgomerySub(0, montgomeryMul(a01, t1)) + } + + /// @notice Computes the multiplication of a Fp2 element with xi. + /// @dev Where xi = u in Fp + /// @dev See https://hackmd.io/@jpw/bn254#Field-extension-towers for further details. + /// @param a00, a01 The coefficients of the Fp2 element A. + /// @return c00, c01 The coefficients of the element C = A * xi. + function mulByXi(a00, a01) -> c00, c01 { + let t0, t1 := fp2ScalarMul(a00, a01, intoMontgomeryForm(8)) + c00 := montgomerySub(montgomeryAdd(t0, a00), a01) + c01 := montgomeryAdd(montgomeryAdd(t1, a00), a01) + } + + /// @notice Computes the conjugation of a Fp2 element. + /// @param a00, a01 The coefficients of the Fp2 element A. + /// @return c00, c01 The coefficients of the element C = A'. + function fp2Conjugate(a00, a01) -> c00, c01 { + c00 := a00 + c01 := montgomerySub(0, a01) + } + + // FP6 ARITHMETHICS + + /// @notice Computes the sum of two Fp6 elements. + /// @dev Algorithm 10 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01, a10, a11, a20, a21 The coefficients of the A element to sum. + /// @param b00, b01, b10, b11, b20, b21 The coefficients of the B element to sum. + /// @return c00, c01, c10, c11, c20, c21 The coefficients of the element C = A + B. + function fp6Add(a00, a01, a10, a11, a20, a21, b00, b01, b10, b11, b20, b21) -> c00, c01, c10, c11, c20, c21 { + c00, c01 := fp2Add(a00, a01, b00, b01) + c10, c11 := fp2Add(a10, a11, b10, b11) + c20, c21 := fp2Add(a20, a21, b20, b21) + } + + /// @notice Computes the subtraction of two Fp6 elements. + /// @dev Algorithm 11 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01, a10, a11, a20, a21 The coefficients of the minuend A. + /// @param b00, b01, b10, b11, b20, b21 The coefficients of the subtrahend B. + /// @return c00, c01, c10, c11, c20, c21 The coefficients of the element C = A - B. + function fp6Sub(a00, a01, a10, a11, a20, a21, b00, b01, b10, b11, b20, b21) -> c00, c01, c10, c11, c20, c21 { + c00, c01 := fp2Sub(a00, a01, b00, b01) + c10, c11 := fp2Sub(a10, a11, b10, b11) + c20, c21 := fp2Sub(a20, a21, b20, b21) + } + + /// @notice Computes the multiplication of a Fp6 element with g. + /// @dev Algorithm 12 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01, a10, a11, a20, a21 The coefficients of the Fp6 element A. + /// @return c00, c01, c10, c11, c20, c21 The coefficients of the element C = A * g. + function mulByGamma(a00, a01, a10, a11, a20, a21) -> c00, c01, c10, c11, c20, c21 { + c00, c01 := mulByXi(a20, a21) + c10 := a00 + c11 := a01 + c20 := a10 + c21 := a11 + } + + /// @notice Computes the multiplication between two Fp6 elements. + /// @dev Algorithm 13 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01, a10, a11, a20, a21 The coefficients of the Fp6 element A. + /// @param b00, b01, b10, b11, b20, b21 The coefficients of the Fp6 element B. + /// @return c00, c01, c10, c11, c20, c21 The coefficients of the element C = A * B. + function fp6Mul(a00, a01, a10, a11, a20, a21, b00, b01, b10, b11, b20, b21) -> c00, c01, c10, c11, c20, c21 { + let t00, t01 := fp2Mul(a00, a01, b00, b01) + let t10, t11 := fp2Mul(a10, a11, b10, b11) + let t20, t21 := fp2Mul(a20, a21, b20, b21) + + let tmp0, temp1 := fp2Add(a10, a11, a20, a21) + let tmp2, tmp3 := fp2Add(b10, b11, b20, b21) + let tmp4, tmp5 := fp2Mul(tmp0, temp1, tmp2, tmp3) + let tmp6, tmp7 := fp2Sub(tmp4, tmp5, t10, t11) + let tmp8, tmp9 := fp2Sub(tmp6, tmp7, t20, t21) + let tmp10, tmp11 := mulByXi(tmp8, tmp9) + c00, c01 := fp2Add(tmp10, tmp11, t00, t01) + + tmp0, temp1 := fp2Add(a00, a01, a10, a11) + tmp2, tmp3 := fp2Add(b00, b01, b10, b11) + tmp4, tmp5 := fp2Mul(tmp0, temp1, tmp2, tmp3) + tmp6, tmp7 := fp2Sub(tmp4, tmp5, t00, t01) + tmp8, tmp9 := fp2Sub(tmp6, tmp7, t10, t11) + tmp10, tmp11 := mulByXi(t20, t21) + c10, c11 := fp2Add(tmp8, tmp9, tmp10, tmp11) + + tmp0, temp1 := fp2Add(a00, a01, a20, a21) + tmp2, tmp3 := fp2Add(b00, b01, b20, b21) + tmp4, tmp5 := fp2Mul(tmp0, temp1, tmp2, tmp3) + tmp6, tmp7 := fp2Sub(tmp4, tmp5, t00, t01) + tmp8, tmp9 := fp2Sub(tmp6, tmp7, t20, t21) + c20, c21 := fp2Add(tmp8, tmp9, t10, t11) + } + + /// @notice Computes the negative of a Fp6 element. + /// @param a00, a01, a10, a11, a20, a21 The coefficients of the Fp2 element A. + /// @return c00, c01, c10, c11, c20, c21 The coefficients of the element C = -A. + function fp6Neg(a00, a01, a10, a11, a20, a21) -> c00, c01, c10, c11, c20, c21 { + c00, c01 := fp2Neg(a00, a01) + c10, c11 := fp2Neg(a10, a11) + c20, c21 := fp2Neg(a20, a21) + } + + /// @notice Computes the square of a Fp6 element. + /// @dev Algorithm 16 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01, a10, a11, a20, a21 The coefficients of the Fp6 element A. + /// @return c00, c01, c10, c11, c20, c21 The coefficients of the element C = A^2. + function fp6Square(a00, a01, a10, a11, a20, a21) -> c00, c01, c10, c11, c20, c21 { + let tmp0, tmp1 := fp2Mul(a00, a01, a10, a11) + tmp0, tmp1 := fp2Add(tmp0, tmp1, tmp0, tmp1) + + let tmp2, tmp3 := fp2Mul(a20, a21, a20, a21) + let tmp4, tmp5 := mulByXi(tmp2, tmp3) + c10, c11 := fp2Add(tmp4, tmp5, tmp0, tmp1) + + c20, c21 := fp2Sub(tmp0, tmp1, tmp2, tmp3) + + let tmp6, tmp7 := fp2Mul(a00, a01, a00, a01) + let tmp8, tmp9 := fp2Sub(a00, a01, a10, a11) + tmp0, tmp1 := fp2Add(tmp8, tmp9, a20, a21) + + let tmp10, tmp11 := fp2Mul(a10, a11, a20, a21) + tmp2, tmp3 := fp2Add(tmp10, tmp11, tmp10, tmp11) + tmp0, tmp1 := fp2Mul(tmp0, tmp1, tmp0, tmp1) + + let tmp12, tmp13 := mulByXi(tmp2, tmp3) + c00, c01 := fp2Add(tmp12, tmp13, tmp6, tmp7) + + let tmp14, tmp15 := fp2Add(c20, c21, tmp0, tmp1) + tmp14, tmp15 := fp2Add(tmp14, tmp15, tmp2, tmp3) + c20, c21 := fp2Sub(tmp14, tmp15, tmp6, tmp7) + + } + + /// @notice Computes the inverse of a Fp6 element. + /// @dev Algorithm 17 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a00, a01, a10, a11, a20, a21 The coefficients of the Fp6 element A. + /// @return c00, c01, c10, c11, c20, c21 The coefficients of the element C = A^(-1). + function fp6Inv(a00, a01, a10, a11, a20, a21) -> c00, c01, c10, c11, c20, c21 { + let t00, t01 := fp2Mul(a00, a01, a00, a01) + let t10, t11 := fp2Mul(a10, a11, a10, a11) + let t20, t21 := fp2Mul(a20, a21, a20, a21) + let t30, t31 := fp2Mul(a00, a01, a10, a11) + let t40, t41 := fp2Mul(a00, a01, a20, a21) + let t50, t51 := fp2Mul(a20, a21, a10, a11) + let t50Xi, t51Xi := mulByXi(t50, t51) + c00, c01 := fp2Sub(t00, t01, t50Xi, t51Xi) + let t20Xi, t21Xi := mulByXi(t20, t21) + c10, c11 := fp2Sub(t20Xi, t21Xi, t30, t31) + c20, c21 := fp2Sub(t10, t11, t40, t41) + let t60, t61 := fp2Mul(a00, a01, c00, c01) + let a20Xi, a21Xi := mulByXi(a20, a21) + let a20XiC10, a21XiC11 := fp2Mul(a20Xi, a21Xi, c10, c11) + t60, t61 := fp2Add(t60, t61, a20XiC10, a21XiC11) + let a10Xi, a11Xi := mulByXi(a10, a11) + let a10XiC20, a11XiC21 := fp2Mul(a10Xi, a11Xi, c20, c21) + t60, t61 := fp2Add(t60, t61, a10XiC20, a11XiC21) + t60, t61 := fp2Inv(t60, t61) + c00, c01 := fp2Mul(c00, c01, t60, t61) + c10, c11 := fp2Mul(c10, c11, t60, t61) + c20, c21 := fp2Mul(c20, c21, t60, t61) + } + + // FP12 ARITHMETHICS + + /// @notice Computes the sum of two Fp12 elements. + /// @dev Algorithm 18 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the A element to sum. + /// @param b000, b001, b010, b011, b020, b021, b100, b101, b110, b111, b120, b121 The coefficients of the B element to sum. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A + B. + function fp12Add(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121, b000, b001, b010, b011, b020, b021, b100, b101, b110, b111, b120, b121) -> c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 { + c000, c001, c010, c011, c020, c021 := fp6Add(a000, a001, a010, a011, a020, a021, b000, b001, b010, b011, b020, b021) + c100, c101, c110, c111, c120, c121 := fp6Add(a100, a101, a110, a111, a120, a121, b100, b101, b110, b111, b120, b121) + } + + /// @notice Computes the subtraction of two Fp12 elements. + /// @dev Algorithm 19 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the minuend A. + /// @param b000, b001, b010, b011, b020, b021, b100, b101, b110, b111, b120, b121 The coefficients of the subtrahend B. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A - B. + function fp12Sub(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121, b000, b001, b010, b011, b020, b021, b100, b101, b110, b111, b120, b121) -> c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 { + c000, c001, c010, c011, c020, c021 := fp6Sub(a000, a001, a010, a011, a020, a021, b000, b001, b010, b011, b020, b021) + c100, c101, c110, c111, c120, c121 := fp6Sub(a100, a101, a110, a111, a120, a121, b100, b101, b110, b111, b120, b121) + } + + /// @notice Computes the multiplication between two Fp12 elements. + /// @dev Algorithm 20 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @param b000, b001, b010, b011, b020, b021, b100, b101, b110, b111, b120, b121 The coefficients of the Fp12 element B. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A * B. + function fp12Mul(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121, b000, b001, b010, b011, b020, b021, b100, b101, b110, b111, b120, b121) -> c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 { + let t000, t001, t010, t011, t020, t021 := fp6Mul(a000, a001, a010, a011, a020, a021, b000, b001, b010, b011, b020, b021) + let t100, t101, t110, t111, t120, t121 := fp6Mul(a100, a101, a110, a111, a120, a121, b100, b101, b110, b111, b120, b121) + let t200, t201, t210, t211, t220, t221 := mulByGamma(t100, t101, t110, t111, t120, t121) + c000, c001, c010, c011, c020, c021 := fp6Add(t000, t001, t010, t011, t020, t021, t200, t201, t210, t211, t220, t221) + let t300, t301, t310, t311, t320, t321 := fp6Add(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) + let t400, t401, t410, t411, t420, t421 := fp6Add(b000, b001, b010, b011, b020, b021, b100, b101, b110, b111, b120, b121) + c100, c101, c110, c111, c120, c121 := fp6Mul(t300, t301, t310, t311, t320, t321, t400, t401, t410, t411, t420, t421) + c100, c101, c110, c111, c120, c121 := fp6Sub(c100, c101, c110, c111, c120, c121, t000, t001, t010, t011, t020, t021) + c100, c101, c110, c111, c120, c121 := fp6Sub(c100, c101, c110, c111, c120, c121, t100, t101, t110, t111, t120, t121) + } + + /// @notice Computes the square of a Fp12 element. + /// @dev Algorithm 22 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A^2. + function fp12Square(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) -> c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 { + let t100, t101, t110, t111, t120, t121 := fp6Sub(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) + let t200, t201, t210, t211, t220, t221 := mulByGamma(a100, a101, a110, a111, a120, a121) + let t300, t301, t310, t311, t320, t321 := fp6Sub(a000, a001, a010, a011, a020, a021, t200, t201, t210, t211, t220, t221) + let t400, t401, t410, t411, t420, t421 := fp6Mul(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) + let t500, t501, t510, t511, t520, t521 := fp6Mul(t100, t101, t110, t111, t120, t121, t300, t301, t310, t311, t320, t321) + let t600, t601, t610, t611, t620, t621 := fp6Add(t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521) + c100, c101, c110, c111, c120, c121 := fp6Add(t400, t401, t410, t411, t420, t421, t400, t401, t410, t411, t420, t421) + let t700, t701, t710, t711, t720, t721 := mulByGamma(t400, t401, t410, t411, t420, t421) + c000, c001, c010, c011, c020, c021 := fp6Add(t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721) + } + + /// @notice Computes the inverse of a Fp12 element. + /// @dev Algorithm 23 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A^(-1). + function fp12Inv(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) -> c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 { + let t000, t001, t010, t011, t020, t021 := fp6Square(a000, a001, a010, a011, a020, a021) + let t100, t101, t110, t111, t120, t121 := fp6Square(a100, a101, a110, a111, a120, a121) + let t200, t201, t210, t211, t220, t221 := mulByGamma(t100, t101, t110, t111, t120, t121) + t000, t001, t010, t011, t020, t021 := fp6Sub(t000, t001, t010, t011, t020, t021, t200, t201, t210, t211, t220, t221) + t100, t101, t110, t111, t120, t121 := fp6Inv(t000, t001, t010, t011, t020, t021) + c000, c001, c010, c011, c020, c021 := fp6Mul(a000, a001, a010, a011, a020, a021, t100, t101, t110, t111, t120, t121) + let z00, z01, z10, z11, z20, z21 := FP6_ZERO() + c100, c101, c110, c111, c120, c121 := fp6Mul(a100, a101, a110, a111, a120, a121,t100, t101, t110, t111, t120, t121) + c100, c101, c110, c111, c120, c121 := fp6Sub(z00, z01, z10, z11, z20, z21, c100, c101, c110, c111, c120, c121) + } + + /// @notice Computes the exponentiation of a Fp12 element in the cyclotomic subgroup to t = 6x^2 + 1. + /// @dev We make use of an addition chain to optimize the operation. + /// @dev See https://eprint.iacr.org/2015/192.pdf for further details. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A^t. + function fp12Expt(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) -> c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 { + let t000, t001, t010, t011, t020, t021, t100, t101, t110, t111, t120, t121 := fp12CyclotomicSquare(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) + let t200, t201, t210, t211, t220, t221, t300, t301, t310, t311, t320, t321 := fp12CyclotomicSquare(t000, t001, t010, t011, t020, t021, t100, t101, t110, t111, t120, t121) + c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 := fp12CyclotomicSquare(t200, t201, t210, t211, t220, t221, t300, t301, t310, t311, t320, t321) + let t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521 := fp12CyclotomicSquare(c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121) + + let t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721 := fp12Mul(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121, t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521) + t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521 := fp12Mul(t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721, t000, t001, t010, t011, t020, t021, t100, t101, t110, t111, t120, t121) + let t800, t801, t810, t811, t820, t821, t900, t901, t910, t911, t920, t921 := fp12Mul(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121, t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521) + let t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121 := fp12Mul(c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121, t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721) + let t1200, t1201, t1210, t1211, t1220, t1221, t1300, t1301, t1310, t1311, t1320, t1321 := fp12CyclotomicSquare(t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721) + t800, t801, t810, t811, t820, t821, t900, t901, t910, t911, t920, t921 := fp12Mul(t800, t801, t810, t811, t820, t821, t900, t901, t910, t911, t920, t921, t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521) + t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521 := fp12Mul(t800, t801, t810, t811, t820, t821, t900, t901, t910, t911, t920, t921, t000, t001, t010, t011, t020, t021, t100, t101, t110, t111, t120, t121) + t1200, t1201, t1210, t1211, t1220, t1221, t1300, t1301, t1310, t1311, t1320, t1321 := nSquare(t1200, t1201, t1210, t1211, t1220, t1221, t1300, t1301, t1310, t1311, t1320, t1321, 6) + t200, t201, t210, t211, t220, t221, t300, t301, t310, t311, t320, t321 := fp12Mul(t1200, t1201, t1210, t1211, t1220, t1221, t1300, t1301, t1310, t1311, t1320, t1321, t200, t201, t210, t211, t220, t221, t300, t301, t310, t311, t320, t321) + t200, t201, t210, t211, t220, t221, t300, t301, t310, t311, t320, t321 := fp12Mul(t200, t201, t210, t211, t220, t221, t300, t301, t310, t311, t320, t321, t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121) + t200, t201, t210, t211, t220, t221, t300, t301, t310, t311, t320, t321 := nSquare(t200, t201, t210, t211, t220, t221, t300, t301, t310, t311, t320, t321, 7) + t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121 := fp12Mul(t200, t201, t210, t211, t220, t221, t300, t301, t310, t311, t320, t321, t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121) + t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121 := nSquare(t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121, 8) + t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121 := fp12Mul(t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121, t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521) + t000, t001, t010, t011, t020, t021, t100, t101, t110, t111, t120, t121 := fp12Mul(t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121, t000, t001, t010, t011, t020, t021, t100, t101, t110, t111, t120, t121) + t000, t001, t010, t011, t020, t021, t100, t101, t110, t111, t120, t121 := nSquare(t000, t001, t010, t011, t020, t021, t100, t101, t110, t111, t120, t121, 6) + t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721 := fp12Mul(t000, t001, t010, t011, t020, t021, t100, t101, t110, t111, t120, t121, t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721) + t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721 := nSquare(t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721, 8) + t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721 := fp12Mul(t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721, t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521) + t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721 := nSquare(t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721, 6) + t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721 := fp12Mul(t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721, t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521) + t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721 := nSquare(t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721, 10) + t800, t801, t810, t811, t820, t821, t900, t901, t910, t911, t920, t921 := fp12Mul(t600, t601, t610, t611, t620, t621, t700, t701, t710, t711, t720, t721, t800, t801, t810, t811, t820, t821, t900, t901, t910, t911, t920, t921) + t800, t801, t810, t811, t820, t821, t900, t901, t910, t911, t920, t921 := nSquare(t800, t801, t810, t811, t820, t821, t900, t901, t910, t911, t920, t921, 6) + t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521 := fp12Mul(t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521, t800, t801, t810, t811, t820, t821, t900, t901, t910, t911, t920, t921) + c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 := fp12Mul(t400, t401, t410, t411, t420, t421, t500, t501, t510, t511, t520, t521, c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121) + } + + /// @notice Computes the conjugation of a Fp12 element. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A'. + function fp12Conjugate(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) -> c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 { + c000 := a000 + c001 := a001 + c010 := a010 + c011 := a011 + c020 := a020 + c021 := a021 + c100, c101, c110, c111, c120, c121 := fp6Neg(a100, a101, a110, a111, a120, a121) + } + + /// @notice Computes the square of a Fp12 element in the cyclotomic subgroup. + /// @dev See https://eprint.iacr.org/2010/542.pdf for further details. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A^2. + function fp12CyclotomicSquare(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) -> c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 { + let t00, t01 := fp2Mul(a110, a111, a110, a111) + let t10, t11 := fp2Mul(a000, a001, a000, a001) + let t20, t21 := fp2Add(a110, a111, a000, a001) + t20, t21 := fp2Mul(t20, t21, t20, t21) + t20, t21 := fp2Sub(t20, t21, t00, t01) + t20, t21 := fp2Sub(t20, t21, t10, t11) + let t30, t31 := fp2Mul(a020, a021, a020, a021) + let t40, t41 := fp2Mul(a100, a101, a100, a101) + let t50, t51 := fp2Add(a020, a021, a100, a101) + t50, t51 := fp2Mul(t50, t51, t50, t51) + t50, t51 := fp2Sub(t50, t51, t30, t31) + t50, t51 := fp2Sub(t50, t51, t40, t41) + let t60, t61 := fp2Mul(a120, a121, a120, a121) + let t70, t71 := fp2Mul(a010, a011, a010, a011) + let t80, t81 := fp2Add(a120, a121, a010, a011) + t80, t81 := fp2Mul(t80, t81, t80, t81) + t80, t81 := fp2Sub(t80, t81, t60, t61) + t80, t81 := fp2Sub(t80, t81, t70, t71) + t80, t81 := mulByXi(t80, t81) + t00, t01 := mulByXi(t00, t01) + t00, t01 := fp2Add(t00, t01, t10, t11) + t30, t31 := mulByXi(t30, t31) + t30, t31 := fp2Add(t30, t31, t40, t41) + t60, t61 := mulByXi(t60, t61) + t60, t61 := fp2Add(t60, t61, t70, t71) + + c000, c001 := fp2Sub(t00, t01, a000, a001) + c000, c001 := fp2Add(c000, c001, c000, c001) + c000, c001 := fp2Add(c000, c001, t00, t01) + + c010, c011 := fp2Sub(t30, t31, a010, a011) + c010, c011 := fp2Add(c010, c011, c010, c011) + c010, c011 := fp2Add(c010, c011, t30, t31) + + c020, c021 := fp2Sub(t60, t61, a020, a021) + c020, c021 := fp2Add(c020, c021, c020, c021) + c020, c021 := fp2Add(c020, c021, t60, t61) + + c100, c101 := fp2Add(t80, t81, a100, a101) + c100, c101 := fp2Add(c100, c101, c100, c101) + c100, c101 := fp2Add(c100, c101, t80, t81) + + c110, c111 := fp2Add(t20, t21, a110, a111) + c110, c111 := fp2Add(c110, c111, c110, c111) + c110, c111 := fp2Add(c110, c111, t20, t21) + + c120, c121 := fp2Add(t50, t51, a120, a121) + c120, c121 := fp2Add(c120, c121, c120, c121) + c120, c121 := fp2Add(c120, c121, t50, t51) + } + + /// @notice Computes the exponentiation of a Fp12 element in the cyclotomic subgroup to 2n. + /// @dev We compute A^2n as n cyclotomic squares. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A^2n. + function nSquare(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121, n) -> c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 { + c000 := a000 + c001 := a001 + c010 := a010 + c011 := a011 + c020 := a020 + c021 := a021 + c100 := a100 + c101 := a101 + c110 := a110 + c111 := a111 + c120 := a120 + c121 := a121 + for { let i := 0 } lt(i, n) { i := add(i, 1) } { + c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 := fp12CyclotomicSquare(c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121) + } + } + + // FROBENIUS + + + /// @notice Computes the exponentiation of a Fp12 element to p. + /// @dev Algorithm 28 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A^p. + function frobenius(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) -> c00, c01, c10, c11, c20, c21, c30, c31, c40, c41, c50, c51 { + let t10, t11 := fp2Conjugate(a000, a001) + let t20, t21 := fp2Conjugate(a100, a101) + let t30, t31 := fp2Conjugate(a010, a011) + let t40, t41 := fp2Conjugate(a110, a111) + let t50, t51 := fp2Conjugate(a020, a021) + let t60, t61 := fp2Conjugate(a120, a121) + + t20, t21 := mulByGamma11(t20, t21) + t30, t31 := mulByGamma12(t30, t31) + t40, t41 := mulByGamma13(t40, t41) + t50, t51 := mulByGamma14(t50, t51) + t60, t61 := mulByGamma15(t60, t61) + + c00 := t10 + c01 := t11 + c10 := t30 + c11 := t31 + c20 := t50 + c21 := t51 + c30 := t20 + c31 := t21 + c40 := t40 + c41 := t41 + c50 := t60 + c51 := t61 + } + + /// @notice Computes the exponentiation of a Fp12 element to p^2. + /// @dev Algorithm 29 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A^(p^2). + function frobeniusSquare(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) -> c00, c01, c10, c11, c20, c21, c30, c31, c40, c41, c50, c51 { + let t10 := a000 + let t11 := a001 + let t20, t21 := mulByGamma21(a100, a101) + let t30, t31 := mulByGamma22(a010, a011) + let t40, t41 := mulByGamma23(a110, a111) + let t50, t51 := mulByGamma24(a020, a021) + let t60, t61 := mulByGamma25(a120, a121) + + c00 := t10 + c01 := t11 + c10 := t30 + c11 := t31 + c20 := t50 + c21 := t51 + c30 := t20 + c31 := t21 + c40 := t40 + c41 := t41 + c50 := t60 + c51 := t61 + } + + /// @notice Computes the exponentiation of a Fp12 element to p^3. + /// @dev @dev Algorithm 29 in: https://eprint.iacr.org/2010/354.pdf. + /// @param a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @return c000, c001, c010, c011, c020, c021, c100, c101, c110, c111, c120, c121 The coefficients of the element C = A^(p^3). + function frobeniusCube(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) -> c00, c01, c10, c11, c20, c21, c30, c31, c40, c41, c50, c51 { + let t10, t11 := fp2Conjugate(a000, a001) + let t20, t21 := fp2Conjugate(a100, a101) + let t30, t31 := fp2Conjugate(a010, a011) + let t40, t41 := fp2Conjugate(a110, a111) + let t50, t51 := fp2Conjugate(a020, a021) + let t60, t61 := fp2Conjugate(a120, a121) + + t20, t21 := mulByGamma31(t20, t21) + t30, t31 := mulByGamma32(t30, t31) + t40, t41 := mulByGamma33(t40, t41) + t50, t51 := mulByGamma34(t50, t51) + t60, t61 := mulByGamma35(t60, t61) + + c00 := t10 + c01 := t11 + c10 := t30 + c11 := t31 + c20 := t50 + c21 := t51 + c30 := t20 + c31 := t21 + c40 := t40 + c41 := t41 + c50 := t60 + c51 := t61 + } + + // GAMMA_1_i + /// @notice Computes the multiplication between a fp2 element by the constants g_1,i. + /// @dev Where g_1,i = u^(i(p-1)/6) + /// @dev This value was precomputed using Python. Already in montgomery form. + /// @dev See https://eprint.iacr.org/2010/354.pdf for further details. + /// @params a00, a01 The coefficients of the Fp2 element A. + /// @return c00, c01 The coefficients of the element C = A*g_1,i. + + function mulByGamma11(a00, a01) -> c00, c01 { + let g00 := 1334504125441109323775816677333762124980877086439557453392802825656291576071 + let g01 := 7532670101108748540749979597679923402841328813027773483599019704565791010162 + c00, c01 := fp2Mul(a00, a01, g00, g01) + } + + function mulByGamma12(a00, a01) -> c00, c01 { + let g00 := 11461073415658098971834280704587444395456423268720245247603935854280982113072 + let g01 := 17373957475705492831721812124331982823197004514106338927670775596783233550167 + c00, c01 := fp2Mul(a00, a01, g00, g01) + } + + function mulByGamma13(a00, a01) -> c00, c01 { + let g00 := 16829996427371746075450799880956928810557034522864196246648550205375670302249 + let g01 := 20140510615310063345578764457068708762835443761990824243702724480509675468743 + c00, c01 := fp2Mul(a00, a01, g00, g01) + } + + function mulByGamma14(a00, a01) -> c00, c01 { + let g00 := 9893659366031634526915473325149983243417508801286144596494093251884139331218 + let g01 := 16514792769865828027011044701859348114858257981779976519405133026725453154633 + c00, c01 := fp2Mul(a00, a01, g00, g01) + } + + function mulByGamma15(a00, a01) -> c00, c01 { + let g00 := 8443299194457421137480282511969901974227997168695360756777672575877693116391 + let g01 := 21318636632361225103955470331868462398471880609949088574192481281746934874025 + c00, c01 := fp2Mul(a00, a01, g00, g01) + } + + // GAMMA_2_i + /// @notice Computes the multiplication between a fp2 element by the constants g_2,i. + /// @dev Where g_2,i = g_1,i * g'_1,i + /// @dev This value was precomputed using Python. Already in montgomery form. + /// @dev See https://eprint.iacr.org/2010/354.pdf for further details. + /// @params a00, a01 The coefficients of the Fp2 element A. + /// @return c00, c01 The coefficients of the element C = A*g_2,i. + + function mulByGamma21(a00, a01) -> c00, c01 { + let g0 := 1881798392815877688876180778159931906057091683336018750908411925848733129714 + c00, c01 := fp2ScalarMul(a00, a01, g0) + } + + function mulByGamma22(a00, a01) -> c00, c01 { + let g0 := 17419166386535333598783630241015674584964973961482396687585055285806960741276 + c00, c01 := fp2ScalarMul(a00, a01, g0) + } + + function mulByGamma23(a00, a01) -> c00, c01 { + let g0 := 15537367993719455909907449462855742678907882278146377936676643359958227611562 + c00, c01 := fp2ScalarMul(a00, a01, g0) + } + + function mulByGamma24(a00, a01) -> c00, c01 { + let g0 := 20006444479023397533370224967097343182639219473961804911780625968796493078869 + c00, c01 := fp2ScalarMul(a00, a01, g0) + } + + function mulByGamma25(a00, a01) -> c00, c01 { + let g0 := 4469076485303941623462775504241600503731337195815426975103982608838265467307 + c00, c01 := fp2ScalarMul(a00, a01, g0) + } + + // GAMMA_3_i + /// @notice Computes the multiplication between a fp2 element by the constants g_3,i. + /// @dev Where g_3,i = g_1,i * g_2,i + /// @dev This value was precomputed using Python. Already in montgomery form. + /// @dev See https://eprint.iacr.org/2010/354.pdf for further details. + /// @params a00, a01 The coefficients of the Fp2 element A. + /// @return c00, c01 The coefficients of the element C = A*g_3,i. + + function mulByGamma31(a00, a01) -> c00, c01 { + let g00 := 3649295186494431467217240962842301358951278585756714214031945394966344685949 + let g01 := 17372117152826387298350653207345606612066102743297871578090761045572893546809 + c00, c01 := fp2Mul(a00, a01, g00, g01) + } + + function mulByGamma32(a00, a01) -> c00, c01 { + let g00 := 14543349330631744552586812320441124107441202078168618766450326117520897829805 + let g01 := 4646831431411403714092965637071058625728899792817054432901795759277546050476 + c00, c01 := fp2Mul(a00, a01, g00, g01) + } + + function mulByGamma33(a00, a01) -> c00, c01 { + let g00 := 5058246444467529146795605864300346278139276634433627416040487689269555906334 + let g01 := 1747732256529211876667641288188566325860867395306999418986313414135550739840 + c00, c01 := fp2Mul(a00, a01, g00, g01) + } + + function mulByGamma34(a00, a01) -> c00, c01 { + let g00 := 3025265262868802913511075437173590487338001780554453930995247874855578067679 + let g01 := 10425289180741305073643362413949631488281652900778689227251281048515799234257 + c00, c01 := fp2Mul(a00, a01, g00, g01) + } + + function mulByGamma35(a00, a01) -> c00, c01 { + let g00 := 9862576063628467829192720579684130652367741026604221989510773554027227469215 + let g01 := 16681752610922605480353377694363181135019829138759259603037557916788351015335 + c00, c01 := fp2Mul(a00, a01, g00, g01) + } + + // PAIRING FUNCTIONS + + /// @notice Computes the double of a G2 point and its tangent line. + /// @dev The point is in projective coordinates. + /// @dev See https://eprint.iacr.org/2013/722.pdf for further details. + /// @params xq0, xq1 The coefficients of the Fp2 X coordinate of the Q point. + /// @params yq0, yq1 The coefficients of the Fp2 X coordinate of the Q point. + /// @params zq0, zq1 The coefficients of the Fp2 X coordinate of the Q point. + /// @return xt0, xt1 The coefficients of the Fp2 X coordinate of T = 2Q. + /// @return yt0, yt1 The coefficients of the Fp2 X coordinate of T = 2Q. + /// @return zt0, zt1 The coefficients of the Fp2 X coordinate of T = 2Q. + /// @return l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51 The coefficients of the tangent line to Q. + function doubleStep(xq0, xq1, yq0, yq1, zq0, zq1) -> l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51, xt0, xt1, yt0, yt1, zt0, zt1 { + let zero := 0 + let twoInv := MONTGOMERY_TWO_INV() + let t00, t01 := fp2Mul(xq0, xq1, yq0, yq1) + let t10, t11 := fp2ScalarMul(t00, t01, twoInv) + let t20, t21 := fp2Mul(yq0, yq1, yq0, yq1) + let t30, t31 := fp2Mul(zq0, zq1, zq0, zq1) + let t40, t41 := fp2Add(t30, t31, t30, t31) + t40, t41 := fp2Add(t40, t41, t30, t31) + let t50, t51 := MONTGOMERY_TWISTED_CURVE_COEFFS() + t50, t51 := fp2Mul(t40, t41, t50, t51) + let t60, t61 :=fp2Add(t50, t51, t50, t51) + t60, t61 := fp2Add(t60, t61, t50, t51) + let t70, t71 := fp2Add(t20, t21, t60, t61) + t70, t71 := fp2ScalarMul(t70, t71, twoInv) + let t80, t81 := fp2Add(yq0, yq1, zq0, zq1) + t80, t81 := fp2Mul(t80, t81, t80, t81) + let t90, t91 := fp2Add(t30, t31, t20, t21) + t80, t81 := fp2Sub(t80, t81, t90, t91) + let t100, t101 := fp2Sub(t50, t51, t20, t21) + let t110, t111 := fp2Mul(xq0, xq1, xq0, xq1) + let t120, t121 := fp2Mul(t50, t51, t50, t51) + let t130, t131 := fp2Add(t120, t121, t120, t121) + t130, t131 := fp2Add(t130, t131, t120, t121) + + // l0 + l00, l01 := fp2Neg(t80, t81) + l10 := zero + l11 := zero + l20 := zero + l21 := zero + + // l1 + l30, l31 := fp2Add(t110, t111, t110, t111) + l30, l31 := fp2Add(l30, l31, t110, t111) + + // l2 + l40 := t100 + l41 := t101 + + l50 := zero + l51 := zero + + // Tx + xt0, xt1 := fp2Sub(t20, t21, t60, t61) + xt0, xt1 := fp2Mul(xt0, xt1, t10, t11) + + // Ty + yt0, yt1 := fp2Mul(t70, t71, t70, t71) + yt0, yt1 := fp2Sub(yt0, yt1, t130, t131) + + // Tz + zt0, zt1 := fp2Mul(t20, t21, t80, t81) + } + + /// @notice Computes the addition of two G2 points and the line through them. + /// @dev It's called mixed addition because Q is in affine coordinates ands T in projective coordinates. + /// @dev See https://eprint.iacr.org/2013/722.pdf for further details. + /// @params xq0, xq1 The coefficients of the Fp2 X coordinate of the Q point. + /// @params yq0, yq1 The coefficients of the Fp2 Y coordinate of the Q point. + /// @params xt0, xt1 The coefficients of the Fp2 X coordinate of the T point. + /// @params yt0, yt1 The coefficients of the Fp2 Y coordinate of the T point. + /// @params zt0, zt1 The coefficients of the Fp2 Z coordinate of the T point. + /// @return xc0, xc1 The coefficients of the Fp2 X coordinate of C = Q + T. + /// @return yc0, yc1 The coefficients of the Fp2 X coordinate of C = Q + T. + /// @return zc0, zc1 The coefficients of the Fp2 X coordinate of C = Q + T. + /// @return l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51 The coefficients of the line through T and Q. + function mixedAdditionStep(xq0, xq1, yq0, yq1, xt0, xt1, yt0, yt1, zt0, zt1) -> l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51, xc0, xc1, yc0, yc1, zc0, zc1 { + let zero := 0 + let t00, t01 := fp2Mul(yq0,yq1,zt0,zt1) + let t10, t11 := fp2Sub(yt0, yt1, t00, t01) + t00, t01 := fp2Mul(xq0, xq1, zt0, zt1) + let t20, t21 := fp2Sub(xt0, xt1, t00, t01) + let t30, t31 := fp2Mul(t10, t11, t10, t11) + let t40, t41 := fp2Mul(t20, t21, t20, t21) + let t50, t51 := fp2Mul(t20, t21, t40, t41) + let t60, t61 := fp2Mul(zt0, zt1, t30, t31) + let t70, t71 := fp2Mul(xt0, xt1, t40, t41) + t00, t01 := fp2Add(t70, t71, t70, t71) + let t80, t81 := fp2Add(t50, t51, t60, t61) + t80, t81 := fp2Sub(t80, t81, t00, t01) + t00, t01 := fp2Mul(yt0, yt1, t50, t51) + + // Xc0 + xc0, xc1 := fp2Mul(t20, t21, t80, t81) + + // Yc0 + yc0, yc1 := fp2Sub(t70, t71, t80, t81) + yc0, yc1 := fp2Mul(yc0, yc1, t10, t11) + yc0, yc1 := fp2Sub(yc0, yc1, t00, t01) + + // Zc0 + zc0, zc1 := fp2Mul(t50, t51, zt0, zt1) + t00, t01 := fp2Mul(t20, t21, yq0, yq1) + let t90, t91 := fp2Mul(xq0, xq1, t10, t11) + t90, t91 := fp2Sub(t90, t91, t00, t01) + + // l0 + l00 := t20 + l01 := t21 + l10 := zero + l11 := zero + l20 := zero + l21 := zero + + // l1 + l30, l31 := fp2Neg(t10, t11) + + // l2 + l40 := t90 + l41 := t91 + l50 := zero + l51 := zero + } + + /// @notice Computes the line through two G2 points. + /// @dev Like in the mixed_addition_step, Q is in affine coordinates ands T in projective coordinates. + /// @params xq0, xq1 The coefficients of the Fp2 X coordinate of the Q point. + /// @params yq0, yq1 The coefficients of the Fp2 Y coordinate of the Q point. + /// @params xt0, xt1 The coefficients of the Fp2 X coordinate of the T point. + /// @params yt0, yt1 The coefficients of the Fp2 Y coordinate of the T point. + /// @params zt0, zt1 The coefficients of the Fp2 Z coordinate of the T point. + /// @return l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51 The coefficients of the line through T and Q. + function computeLine(xq0, xq1, yq0, yq1, xt0, xt1, yt0, yt1, zt0, zt1) -> l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51 { + let zero := 0 + let t00, t01 := fp2Mul(yq0,yq1,zt0,zt1) + let t10, t11 := fp2Sub(yt0, yt1, t00, t01) + t00, t01 := fp2Mul(xq0, xq1, zt0, zt1) + let t20, t21 := fp2Sub(xt0, xt1, t00, t01) + let t30, t31 := fp2Mul(t20, t21, yq0, yq1) + let t40, t41 := fp2Mul(xq0, xq1, t10, t11) + t40, t41 := fp2Sub(t40, t41, t30, t31) + + // l0 + l00 := t20 + l01 := t21 + l10 := zero + l11 := zero + l20 := zero + l21 := zero + + // l1 + l30, l31 := fp2Neg(t10, t11) + + // l2 + l40 := t40 + l41 := t41 + l50 := zero + l51 := zero + } + + /// @notice Computes the final exponentiation to the result given by the Millers Loop. + /// @dev It computes the exponentiation of a Fp12 elemento to e, with e = (p^12 -1)/r + /// @dev We can split this exponentitation in three parts: e = (p^6 - 1)(p^2 + 1)((p^4 - p^2 + 1)/r) + /// @dev The first 2 parts are easy to compute using the Frobenius operator. + /// @dev To calcualte this we use the first 5 lines of Algorithm 31 in: https://eprint.iacr.org/2010/354.pdf + /// @dev For the hard part we use the Fuentes et al. method. Algorithm 6 in: https://eprint.iacr.org/2015/192.pdf + /// @params a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121 The coefficients of the Fp12 element A. + /// @return f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 The coefficients of A^((p^12 -1)/r) + function finalExponentiation(a000, a001, a010, a011, a020, a021, a100, a101, a110, a111, a120, a121) -> f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 { + f000 := a000 + f001 := a001 + f010 := a010 + f011 := a011 + f020 := a020 + f021 := a021 + f100 := a100 + f101 := a101 + f110 := a110 + f111 := a111 + f120 := a120 + f121 := a121 + + // Easy Part + let t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121 := fp12Conjugate(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Inv(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121) + t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121 := fp12Mul(t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121, f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121) + let t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121 := frobeniusSquare(t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121, t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121) + + // Hard Part + t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121 := fp12Expt(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121) + t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121 := fp12Conjugate(t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121) + t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121 := fp12CyclotomicSquare(t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121) + t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121 := fp12CyclotomicSquare(t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121) + t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121 := fp12Mul(t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121, t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121) + let t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121 := fp12Expt(t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121) + t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121 := fp12Conjugate(t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121) + let t3000, t3001, t3010, t3011, t3020, t3021, t3100, t3101, t3110, t3111, t3120, t3121 := fp12Conjugate(t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121) + t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121 := fp12Mul(t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121, t3000, t3001, t3010, t3011, t3020, t3021, t3100, t3101, t3110, t3111, t3120, t3121) + t3000, t3001, t3010, t3011, t3020, t3021, t3100, t3101, t3110, t3111, t3120, t3121 := fp12CyclotomicSquare(t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121) + let t4000, t4001, t4010, t4011, t4020, t4021, t4100, t4101, t4110, t4111, t4120, t4121 := fp12Expt(t3000, t3001, t3010, t3011, t3020, t3021, t3100, t3101, t3110, t3111, t3120, t3121) + t4000, t4001, t4010, t4011, t4020, t4021, t4100, t4101, t4110, t4111, t4120, t4121 := fp12Mul(t4000, t4001, t4010, t4011, t4020, t4021, t4100, t4101, t4110, t4111, t4120, t4121, t1000, t1001, t1010, t1011, t1020, t1021, t1100, t1101, t1110, t1111, t1120, t1121) + t3000, t3001, t3010, t3011, t3020, t3021, t3100, t3101, t3110, t3111, t3120, t3121 := fp12Mul(t4000, t4001, t4010, t4011, t4020, t4021, t4100, t4101, t4110, t4111, t4120, t4121, t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121) + t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121 := fp12Mul(t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121, t4000, t4001, t4010, t4011, t4020, t4021, t4100, t4101, t4110, t4111, t4120, t4121) + t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121 := fp12Mul(t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121, f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121) + t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121 := frobenius(t3000, t3001, t3010, t3011, t3020, t3021, t3100, t3101, t3110, t3111, t3120, t3121) + t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121 := fp12Mul(t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121, t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121) + t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121 := frobeniusSquare(t4000, t4001, t4010, t4011, t4020, t4021, t4100, t4101, t4110, t4111, t4120, t4121) + t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121 := fp12Mul(t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121, t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121) + t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121 := fp12Conjugate(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121) + t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121 := fp12Mul(t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121, t3000, t3001, t3010, t3011, t3020, t3021, t3100, t3101, t3110, t3111, t3120, t3121) + t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121 := frobeniusCube(t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(t2000, t2001, t2010, t2011, t2020, t2021, t2100, t2101, t2110, t2111, t2120, t2121, t0000, t0001, t0010, t0011, t0020, t0021, t0100, t0101, t0110, t0111, t0120, t0121) + } + + /// @notice Computes the Millers Loop for the optimal ate pairing. + /// @dev Algorithm 1 in: https://eprint.iacr.org/2010/354.pdf + /// @dev It takes two points: P that belongs to the curve G1, in affine coordinates (Fp elements) + /// @dev Point Q belongs to the twisted G2 curve, in affine coordinates (Fp2 elements) + /// @params xp, yp The coordinates of the point P. + /// @params xq0, xq1 The coefficients of the X coordinate of point Q. + /// @params yq0, yq1 The coefficients of the Y coordinate of point Q. + /// @return f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 The Fp12 element result of the Miller Loop + function millerLoop(xq0, xq1, yq0, yq1, xp, yp) -> f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 { + let t00, t01, t10, t11, t20, t21 := g2ProjectiveFromAffine(xq0, xq1, yq0, yq1) + let mq00, mq01, mq10, mq11 := g2AffineNeg(xq0, xq1, yq0, yq1) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := FP12_ONE() + let naf := NAF_REPRESENTATIVE() + let n_iter := 63 + let l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51 := FP12_ONE() + + // Computes the first iteration of Millers loop outside to avoid unecesariy square + // NAF[64] == 0 + l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51, t00, t01, t10, t11, t20, t21 := doubleStep(t00, t01, t10, t11, t20, t21) + l00, l01 := fp2ScalarMul(l00, l01, yp) + l30, l31 := fp2ScalarMul(l30, l31, xp) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121, l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51) + + // Computes the second iteration of Millers loop outside + // NAF[63] == -1. + // Here T = 2Q, so doing a dobule step and a mixed addition step with -Q looks like: (2(2Q)-Q) = 3Q. + // This is equivalent to a mixed addition step with Q: (2Q + Q) = 3Q + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121,f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121) + l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51 := computeLine(mq00, mq01, mq10, mq11, t00, t01, t10, t11, t20, t21) + l00, l01 := fp2ScalarMul(l00, l01, yp) + l30, l31 := fp2ScalarMul(l30, l31, xp) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121, l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51) + l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51, t00, t01, t10, t11, t20, t21 := mixedAdditionStep(xq0, xq1, yq0, yq1, t00, t01, t10, t11, t20, t21) + l00, l01 := fp2ScalarMul(l00, l01, yp) + l30, l31 := fp2ScalarMul(l30, l31, xp) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121, l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51) + + for {let i := 0} lt(i, n_iter) { i := add(i, 1) } { + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Square(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121) + + l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51, t00, t01, t10, t11, t20, t21 := doubleStep(t00, t01, t10, t11, t20, t21) + l00, l01 := fp2ScalarMul(l00, l01, yp) + l30, l31 := fp2ScalarMul(l30, l31, xp) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121, l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51) + + // naf digit = 1 + if and(naf, 2) { + l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51, t00, t01, t10, t11, t20, t21 := mixedAdditionStep(xq0, xq1, yq0, yq1, t00, t01, t10, t11, t20, t21) + l00, l01 := fp2ScalarMul(l00, l01, yp) + l30, l31 := fp2ScalarMul(l30, l31, xp) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121, l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51) + } + + // naf digit = -1 + if and(naf, 4) { + l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51, t00, t01, t10, t11, t20, t21 := mixedAdditionStep(mq00, mq01, mq10, mq11, t00, t01, t10, t11, t20, t21) + l00, l01 := fp2ScalarMul(l00, l01, yp) + l30, l31 := fp2ScalarMul(l30, l31, xp) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121, l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51) + } + + naf := shr(3, naf) + } + + let r00, r01 := fp2Conjugate(xq0, xq1) + let r10, r11 := fp2Conjugate(yq0, yq1) + r00, r01 := mulByGamma12(r00, r01) + r10, r11 := mulByGamma13(r10, r11) + + let r20, r21 := mulByGamma22(xq0, xq1) + let r30, r31 := mulByGamma23(yq0, yq1) + r30, r31 := fp2Neg(r30, r31) + + l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51, t00, t01, t10, t11, t20, t21 := mixedAdditionStep(r00, r01, r10, r11, t00, t01, t10, t11, t20, t21) + l00, l01 := fp2ScalarMul(l00, l01, yp) + l30, l31 := fp2ScalarMul(l30, l31, xp) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121, l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51) + + l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51, t00, t01, t10, t11, t20, t21 := mixedAdditionStep(r20, r21, r30, r31, t00, t01, t10, t11, t20, t21) + l00, l01 := fp2ScalarMul(l00, l01, yp) + l30, l31 := fp2ScalarMul(l30, l31, xp) + f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := fp12Mul(f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121, l00, l01, l10, l11, l20, l21, l30, l31, l40, l41, l50, l51) + } + + /// @notice Computes the Pairing between two points P and Q. + /// @dev Applies the Millers Loop and the final exponentiation to return the result of the pairing. + /// @params g1x, g1y The coordinates of the point P of the curve G1. + /// @params g2_x0, g2_x1 The coefficients of the X coordinate of point Q on the twisted curve G2. + /// @params g2_y0, g2_y1 The coefficients of the Y coordinate of point Q on the twisted curve G2. + /// @return f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 The Fp12 element result of the pairing e(P,Q) + function pair(g1_x, g1_y, g2_x0, g2_x1, g2_y0, g2_y1) -> f000, f001, f010, f011, f100, f101, f110, f111, f200, f201, f210, f211 { + f000, f001, f010, f011, f100, f101, f110, f111, f200, f201, f210, f211 := millerLoop(g2_x0, g2_x1, g2_y0, g2_y1, g1_x, g1_y) + f000, f001, f010, f011, f100, f101, f110, f111, f200, f201, f210, f211 := finalExponentiation(f000, f001, f010, f011, f100, f101, f110, f111, f200, f201, f210, f211) + } + + // FALLBACK + + let inputSize := calldatasize() + + // Empty input is valid and results in returning one. + if eq(inputSize, 0) { + mstore(0, 1) + return(0, 32) + } + + // If the input length is not a multiple of 192, the call fails. + if mod(inputSize, PAIR_LENGTH()) { + // Bad pairing input + burnGas() + } + + let r000, r001, r010, r011, r020, r021, r100, r101, r110, r111, r120, r121 := FP12_ONE() + + // Calldata "parsing" + for { let i := 0 } lt(i, inputSize) { i := add(i, PAIR_LENGTH()) } { + /* G1 */ + calldatacopy(i, i, 32) // x + calldatacopy(add(i, 32), add(i, 32), 32) // y + + let g1_x := mload(i) + let g1_y := mload(add(i, 32)) + + if iszero(and(coordinateIsOnFieldOrder(g1_x), coordinateIsOnFieldOrder(g1_y))) { + burnGas() + } + + g1_x := intoMontgomeryForm(g1_x) + g1_y := intoMontgomeryForm(g1_y) + + let g1IsInfinity := g1AffinePointIsInfinity(g1_x, g1_y) + + if and(iszero(g1IsInfinity), iszero(g1AffinePointIsOnCurve(g1_x, g1_y))) { + burnGas() + } + + /* G2 */ + let g2_x1_offset := add(i, 64) + let g2_x0_offset := add(i, 96) + let g2_y1_offset := add(i, 128) + let g2_y0_offset := add(i, 160) + + calldatacopy(g2_x1_offset, g2_x1_offset, 32) + calldatacopy(g2_x0_offset, g2_x0_offset, 32) + calldatacopy(g2_y1_offset, g2_y1_offset, 32) + calldatacopy(g2_y0_offset, g2_y0_offset, 32) + + let g2_x1 := mload(g2_x1_offset) + let g2_x0 := mload(g2_x0_offset) + let g2_y1 := mload(g2_y1_offset) + let g2_y0 := mload(g2_y0_offset) + + // TODO: Double check if this is right + if iszero(and(coordinateIsOnFieldOrder(g2_x0), coordinateIsOnFieldOrder(g2_x1))) { + burnGas() + } + + // TODO: Double check if this is right + if iszero(and(coordinateIsOnFieldOrder(g2_y0), coordinateIsOnFieldOrder(g2_y1))) { + burnGas() + } + + if g2AffinePointIsInfinity(g2_x0, g2_x1, g2_y0, g2_y1) { + continue + } + + g2_x0 := intoMontgomeryForm(g2_x0) + g2_x1 := intoMontgomeryForm(g2_x1) + g2_y0 := intoMontgomeryForm(g2_y0) + g2_y1 := intoMontgomeryForm(g2_y1) + + if iszero(g2IsInSubGroup(g2_x0,g2_x1, g2_y0, g2_y1, MONTGOMERY_ONE(), 0)) { + burnGas() + } + + if iszero(g2AffinePointIsOnCurve(g2_x0, g2_x1, g2_y0, g2_y1)) { + burnGas() + } + + // We must continue if g1 is the point at infinity after validating both g1 and g2 + // That's why although knowing this before parsing and validating g2 we check it later. + if g1IsInfinity { + continue + } + + let f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121 := pair(g1_x, g1_y, g2_x0, g2_x1, g2_y0, g2_y1) + + r000, r001, r010, r011, r020, r021, r100, r101, r110, r111, r120, r121 := fp12Mul(r000, r001, r010, r011, r020, r021, r100, r101, r110, r111, r120, r121, f000, f001, f010, f011, f020, f021, f100, f101, f110, f111, f120, f121) + } + + // Pair check + if and(eq(r000, MONTGOMERY_ONE()), iszero(or(r001, or(r010, r011)))) { + if iszero(or(or(r020, r021), or(r100, r101))) { + if iszero(or(or(r110, r111), or(r120, r121))) { + mstore(0, 1) + return(0, 32) + } + } + } + + mstore(0, 0) + return(0, 32) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/precompiles/Ecrecover.yul b/.test-node-subtree/etc/system-contracts/contracts/precompiles/Ecrecover.yul new file mode 100644 index 00000000..d0e5924b --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/precompiles/Ecrecover.yul @@ -0,0 +1,100 @@ +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice The contract used to emulate EVM's ecrecover precompile. + * @dev It uses `precompileCall` to call the zkEVM built-in precompiles. + */ +object "Ecrecover" { + code { + return(0, 0) + } + object "Ecrecover_deployed" { + code { + //////////////////////////////////////////////////////////////// + // CONSTANTS + //////////////////////////////////////////////////////////////// + + // Group order of secp256k1, see https://en.bitcoin.it/wiki/Secp256k1 + function SECP256K1_GROUP_SIZE() -> ret { + ret := 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 + } + + /// @dev The gas cost of processing ecrecover circuit precompile. + function ECRECOVER_GAS_COST() -> ret { + ret := 1112 + } + + //////////////////////////////////////////////////////////////// + // HELPER FUNCTIONS + //////////////////////////////////////////////////////////////// + + // @dev Packs precompile parameters into one word. + // Note: functions expect to work with 32/64 bits unsigned integers. + // Caller should ensure the type matching before! + function unsafePackPrecompileParams( + uint32_inputOffsetInWords, + uint32_inputLengthInWords, + uint32_outputOffsetInWords, + uint32_outputLengthInWords, + uint64_perPrecompileInterpreted + ) -> rawParams { + rawParams := uint32_inputOffsetInWords + rawParams := or(rawParams, shl(32, uint32_inputLengthInWords)) + rawParams := or(rawParams, shl(64, uint32_outputOffsetInWords)) + rawParams := or(rawParams, shl(96, uint32_outputLengthInWords)) + rawParams := or(rawParams, shl(192, uint64_perPrecompileInterpreted)) + } + + /// @dev Executes the `precompileCall` opcode. + function precompileCall(precompileParams, gasToBurn) -> ret { + // Compiler simulation for calling `precompileCall` opcode + ret := verbatim_2i_1o("precompile", precompileParams, gasToBurn) + } + + //////////////////////////////////////////////////////////////// + // FALLBACK + //////////////////////////////////////////////////////////////// + + let digest := calldataload(0) + let v := calldataload(32) + let r := calldataload(64) + let s := calldataload(96) + + // Validate the input by the yellow paper rules (Appendix E. Precompiled contracts) + let vIsInvalid := iszero(or(eq(v, 27), eq(v, 28))) + let sIsInvalid := or(eq(s, 0), gt(s, sub(SECP256K1_GROUP_SIZE(), 1))) + let rIsInvalid := or(eq(r, 0), gt(r, sub(SECP256K1_GROUP_SIZE(), 1))) + + if or(vIsInvalid, or(sIsInvalid, rIsInvalid)) { + return(0, 0) + } + + // Store the data in memory, so the ecrecover circuit will read it + mstore(0, digest) + mstore(32, sub(v, 27)) + mstore(64, r) + mstore(96, s) + + let precompileParams := unsafePackPrecompileParams( + 0, // input offset in words + 4, // input length in words (the signed digest, v, r, s) + 0, // output offset in words + 2, // output length in words (success, signer) + 0 // No special meaning, ecrecover circuit doesn't check this value + ) + let gasToPay := ECRECOVER_GAS_COST() + + // Check whether the call is successfully handled by the ecrecover circuit + let success := precompileCall(precompileParams, gasToPay) + let internalSuccess := mload(0) + + switch and(success, internalSuccess) + case 0 { + return(0, 0) + } + default { + return(32, 32) + } + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/precompiles/Keccak256.yul b/.test-node-subtree/etc/system-contracts/contracts/precompiles/Keccak256.yul new file mode 100644 index 00000000..b078d580 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/precompiles/Keccak256.yul @@ -0,0 +1,128 @@ +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice The contract used to emulate EVM's keccak256 opcode. + * @dev It accepts the data to be hashed, pad it by the specification + * and uses `precompileCall` to call the zkEVM built-in precompiles. + * @dev Thus keccak256 precompile circuit operates over padded data to perform efficient sponge round computation. + */ +object "Keccak256" { + code { + return(0, 0) + } + object "Keccak256_deployed" { + code { + //////////////////////////////////////////////////////////////// + // CONSTANTS + //////////////////////////////////////////////////////////////// + + /// @dev The size of the processing keccak256 block in bytes. + function BLOCK_SIZE() -> ret { + ret := 136 + } + + /// @dev The gas cost of processing one keccak256 round. + function KECCAK_ROUND_GAS_COST() -> ret { + ret := 40 + } + + //////////////////////////////////////////////////////////////// + // HELPER FUNCTIONS + //////////////////////////////////////////////////////////////// + + // @dev Packs precompile parameters into one word. + // Note: functions expect to work with 32/64 bits unsigned integers. + // Caller should ensure the type matching before! + function unsafePackPrecompileParams( + uint32_inputOffsetInWords, + uint32_inputLengthInWords, + uint32_outputOffsetInWords, + uint32_outputLengthInWords, + uint64_perPrecompileInterpreted + ) -> rawParams { + rawParams := uint32_inputOffsetInWords + rawParams := or(rawParams, shl(32, uint32_inputLengthInWords)) + rawParams := or(rawParams, shl(64, uint32_outputOffsetInWords)) + rawParams := or(rawParams, shl(96, uint32_outputLengthInWords)) + rawParams := or(rawParams, shl(192, uint64_perPrecompileInterpreted)) + } + + /// @dev Executes the `precompileCall` opcode. + function precompileCall(precompileParams, gasToBurn) -> ret { + // Compiler simulation for calling `precompileCall` opcode + ret := verbatim_2i_1o("precompile", precompileParams, gasToBurn) + } + + //////////////////////////////////////////////////////////////// + // FALLBACK + //////////////////////////////////////////////////////////////// + + // Copy calldata to memory for pad it + let bytesSize := calldatasize() + calldatacopy(0, 0, bytesSize) + + let precompileParams + let gasToPay + + // Most often keccak256 is called with "short" input, so optimize it as a special case. + // NOTE: we consider the special case for sizes less than `BLOCK_SIZE() - 1`, so + // there is only one round and it is and padding can be done branchless + switch lt(bytesSize, sub(BLOCK_SIZE(), 1)) + case true { + // Write the 0x01 after the payload bytes and 0x80 at last byte of padded bytes + mstore(bytesSize, 0x0100000000000000000000000000000000000000000000000000000000000000) + mstore( + sub(BLOCK_SIZE(), 1), + 0x8000000000000000000000000000000000000000000000000000000000000000 + ) + + precompileParams := unsafePackPrecompileParams( + 0, // input offset in words + 5, // input length in words (Math.ceil(136/32) = 5) + 0, // output offset in words + 1, // output length in words + 1 // number of rounds + ) + gasToPay := KECCAK_ROUND_GAS_COST() + } + default { + let padLen := sub(BLOCK_SIZE(), mod(bytesSize, BLOCK_SIZE())) + let paddedByteSize := add(bytesSize, padLen) + + switch eq(padLen, 1) + case true { + // Write 0x81 after the payload bytes + mstore(bytesSize, 0x8100000000000000000000000000000000000000000000000000000000000000) + } + default { + // Write the 0x01 after the payload bytes and 0x80 at last byte of padded bytes + mstore(bytesSize, 0x0100000000000000000000000000000000000000000000000000000000000000) + mstore( + sub(paddedByteSize, 1), + 0x8000000000000000000000000000000000000000000000000000000000000000 + ) + } + + let numRounds := div(paddedByteSize, BLOCK_SIZE()) + precompileParams := unsafePackPrecompileParams( + 0, // input offset in words + div(add(paddedByteSize, 31), 32), // input length in words (safe to pass, never exceed `type(uint32).max`) + 0, // output offset in words + 1, // output length in words + numRounds // number of rounds (safe to pass, never exceed `type(uint64).max`) + ) + gasToPay := mul(KECCAK_ROUND_GAS_COST(), numRounds) + } + + let success := precompileCall(precompileParams, gasToPay) + + switch success + case 0 { + revert(0, 0) + } + default { + return(0, 32) + } + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/precompiles/ModExp.yul b/.test-node-subtree/etc/system-contracts/contracts/precompiles/ModExp.yul new file mode 100644 index 00000000..b8964785 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/precompiles/ModExp.yul @@ -0,0 +1,802 @@ +object "ModExp" { + code { } + object "ModExp_deployed" { + code { + + // CONSTANTS + function LIMB_SIZE_IN_BYTES() -> limbSize { + limbSize := 0x20 + } + + function LIMB_SIZE_IN_BITS() -> limbSize { + limbSize := 0x100 + } + + // HELPER FUNCTIONS + function bigIntLimbsWithoutZeros(ptr, totalLimbs) -> limbs { + limbs := 0 + for { let i := 0 } lt(i, totalLimbs) { i := add(i, 1) } { + let limb := mload(add(ptr, shl(5, i))) + if limb { + limbs := add(limbs, 1) + } + } + } + + function bigIntLimbs(length) -> limbs, misalignment { + limbs := div(length, LIMB_SIZE_IN_BYTES()) + misalignment := mod(length, LIMB_SIZE_IN_BYTES()) + if misalignment { + limbs := add(limbs, 1) + } + } + + /// @notice Stores a zero in big unsigned integer form in memory. + /// @param nLimbs The number of limbs needed to represent the operand. + /// @param toAddress The pointer to the MSB of the destination. + function zeroWithLimbSizeAt(nLimbs, toAddress) { + let overflow := add(toAddress, shl(5, nLimbs)) + for { } lt(toAddress, overflow) { toAddress := add(toAddress, LIMB_SIZE_IN_BYTES()) } { + mstore(toAddress, 0) + } + } + + /// @notice Copy a big unsigned integer from one memory location to another. + /// @param nLimbs The number of limbs needed to represent the operand. + /// @param fromAddress The pointer to the MSB of the number to copy. + /// @param toAddress The pointer to the MSB of the destination. + function copyBigUint(nLimbs, fromAddress, toAddress) { + let total_bytes := shl(5, nLimbs) + for { let i } lt(i, total_bytes) { i := add(i, LIMB_SIZE_IN_BYTES()) } { + mstore(add(i, toAddress), mload(add(i, fromAddress))) + } + } + + /// @notice Computes an addition and checks for overflow. + /// @param augend The value to add to. + /// @param addend The value to add. + /// @return sum The sum of the two values. + /// @return overflowed True if the addition overflowed, false otherwise. + function overflowingAdd(augend, addend) -> sum, overflowed { + sum := add(augend, addend) + overflowed := lt(sum, augend) + } + + /// @notice Computes the difference between two 256 bit number and keeps + /// account of the borrow bit. + /// @param minuend The left side of the difference (i.e. the a in a - b). + /// @param subtrahend The right side of the difference (i.e. the b in a - b). + /// @return difference i.e. the c in c = a - b. + /// @return overflowed If there was any borrow on the subtraction, is returned as 1. + function overflowingSubWithBorrow(minuend, subtrahend, borrow) -> difference, overflowed { + difference := sub(minuend, add(subtrahend, borrow)) + overflowed := gt(difference, minuend) + } + + /// @notice Retrieves the highest half of the multiplication result. + /// @param multiplicand The value to multiply. + /// @param multiplier The multiplier. + /// @return ret The highest half of the multiplication result. + function getHighestHalfOfMultiplication(multiplicand, multiplier) -> ret { + ret := verbatim_2i_1o("mul_high", multiplicand, multiplier) + } + + /// @notice Checks whether calldata[start, start + len) is zero. + /// @param start The pointer to the calldata where the big number starts. + /// @param len The number of bytes that the big number occupies. + /// @return res A boolean indicating whether the big number is zero (true) or not (false). + function callDataBufferIsZero(start, len) -> res { + // Initialize result as true, assuming the number is zero until proven otherwise. + res := true + + // Calculate the ending pointer of the big number in memory. + let end := add(start, len) + // Calculate the number of bytes in the last (potentially partial) word of the big number. + let lastWordBytes := mod(len, 32) + // Calculate the ending pointer of the last full 32-byte word. + let endOfLastFullWord := sub(end, lastWordBytes) + + // Loop through each full 32-byte word to check for non-zero bytes. + for { let ptr := start } lt(ptr, endOfLastFullWord) { ptr := add(ptr, 32) } { + let word := calldataload(ptr) + if word { + res := false + break + } + } + + // Check if the last partial word has any non-zero bytes. + if lastWordBytes { + // Create a mask that isolates the valid bytes in the last word. + // The mask has its first `lastWordBytes` bytes set to `0xff`. + let mask := sub(shl(shl(3, lastWordBytes), 1), 1) + let word := shr(sub(LIMB_SIZE_IN_BITS(), shl(3, lastWordBytes)), calldataload(endOfLastFullWord)) + // Use the mask to isolate the valid bytes and check if any are non-zero. + if and(word, mask) { + res := false + } + } + } + + /// @notice Checks whether a big number is zero. + /// @param start The pointer to the calldata where the big number starts. + /// @param len The number of bytes that the big number occupies. + /// @return res A boolean indicating whether the big number is zero (true) or not (false). + function bigUIntIsZero(start, len) -> res { + // Initialize result as true, assuming the number is zero until proven otherwise. + res := true + + // Calculate the ending pointer of the big number in memory. + let end := add(start, len) + // Calculate the number of bytes in the last (potentially partial) word of the big number. + let lastWordBytes := mod(len, 32) + // Calculate the ending pointer of the last full 32-byte word. + let endOfLastFullWord := sub(end, lastWordBytes) + + // Loop through each full 32-byte word to check for non-zero bytes. + for { let ptr := start } lt(ptr, endOfLastFullWord) { ptr := add(ptr, 32) } { + let word := calldataload(ptr) + if word { + res := false + break + } + } + + // Check if the last partial word has any non-zero bytes. + if lastWordBytes { + // Create a mask that isolates the valid bytes in the last word. + // The mask has its first `lastWordBytes` bytes set to `0xff`. + let mask := sub(shl(shl(3, lastWordBytes), 1), 1) + let word := calldataload(endOfLastFullWord) + // Use the mask to isolate the valid bytes and check if any are non-zero. + if and(word, mask) { + res := false + } + } + } + + /// @notice Checks whether a big number is one. + /// @param start The pointer to the calldata where the big number starts. + /// @param len The number of bytes that the big number occupies. + /// @return res A boolean indicating whether the big number is one (true) or not (false). + function callDataBufferIsOne(start, len) -> res { + if len { + let lastBytePtr := sub(add(start, len), 1) + let lastByte := byte(0, calldataload(lastBytePtr)) + + // Check if the last byte is one. + let lastByteIsOne := eq(lastByte, 1) + // Check if all other bytes are zero using the callDataBufferIsZero function + // The length for this check is (len - 1) because we exclude the last byte. + let otherBytesAreZeroes := callDataBufferIsZero(start, sub(len, 1)) + + // The number is one if the last byte is one and all other bytes are zero. + res := and(lastByteIsOne, otherBytesAreZeroes) + } + } + + /// @notice Performs the big unsigned integer left shift (<<). + /// @dev The result is stored from `shiftedPtr` to `shiftedPtr + (LIMB_SIZE_IN_BYTES * nLimbs)`. + /// @param numberPtr The pointer to the MSB of the number to shift. + /// @param nLimbs The number of limbs needed to represent the operands. + /// @param shiftedPtr The pointer to the MSB of the shifted number. + function bigUIntShl(times, numberPtr, nLimbs, shiftedPtr) { + switch times + case 0 { + // If the pointers are different and the amount of bits to shift is zero, + // then we copy the number, otherwise, we do nothing. + if iszero(eq(numberPtr, shiftedPtr)) { + let currentLimbPtr := numberPtr + let currentShiftedLimbPtr := shiftedPtr + for { let i } lt(i, nLimbs) { i := add(i, 1) } { + mstore(currentShiftedLimbPtr, mload(currentLimbPtr)) + currentShiftedLimbPtr := add(currentShiftedLimbPtr, LIMB_SIZE_IN_BYTES()) + currentLimbPtr := add(currentLimbPtr, LIMB_SIZE_IN_BYTES()) + } + } + } + default { + let effectiveShifts := mod(times, LIMB_SIZE_IN_BITS()) + let b_inv := sub(LIMB_SIZE_IN_BITS(), effectiveShifts) + let limbsToShiftOut := div(times, LIMB_SIZE_IN_BITS()) + let shiftDivInv := sub(LIMB_SIZE_IN_BITS(), limbsToShiftOut) + + switch iszero(effectiveShifts) + case 1 { + // When numberPtr could be equal to shiftedPtr that means that the result + // will be stored in the same pointer as the value to shift. To avoid + // overlaping, as this is a left shift we read and store from left to + // right. + + let currentLimbPtrOffset := shl(5, limbsToShiftOut) + let currentLimbPtr := add(numberPtr, currentLimbPtrOffset) + let currentShiftedLimbPtr := shiftedPtr + for { let i := limbsToShiftOut } lt(i, nLimbs) { i := add(i, 1) } { + mstore(currentShiftedLimbPtr, mload(currentLimbPtr)) + currentLimbPtr := add(currentLimbPtr, LIMB_SIZE_IN_BYTES()) + currentShiftedLimbPtr := add(currentShiftedLimbPtr, LIMB_SIZE_IN_BYTES()) + } + // Fill with zeros the limbs that will shifted out limbs. + // We need to fill the zeros after in the edge case that numberPtr == shiftedPtr. + for { let i } lt(i, limbsToShiftOut) { i := add(i, 1) } { + mstore(currentShiftedLimbPtr, 0) + currentShiftedLimbPtr := add(currentShiftedLimbPtr, LIMB_SIZE_IN_BYTES()) + } + } + default { + // When there are effectiveShifts we need to do a bit more of work. + // We go from right to left, shifting the current limb and adding the + // previous one shifted to the left by b_inv bits. + let currentLimbPtrOffset := shl(5, limbsToShiftOut) + let currentLimbPtr := add(numberPtr, currentLimbPtrOffset) + let nextLimbPtr := add(currentLimbPtr, LIMB_SIZE_IN_BYTES()) + let currentShiftedLimbPtr := shiftedPtr + for { let i := limbsToShiftOut } lt(i, nLimbs) { i := add(i, 1) } { + let shiftedLimb := or(shr(b_inv, mload(nextLimbPtr)), shl(effectiveShifts, mload(currentLimbPtr))) + mstore(currentShiftedLimbPtr, shiftedLimb) + nextLimbPtr := add(nextLimbPtr, LIMB_SIZE_IN_BYTES()) + currentLimbPtr := add(currentLimbPtr, LIMB_SIZE_IN_BYTES()) + currentShiftedLimbPtr := add(currentShiftedLimbPtr, LIMB_SIZE_IN_BYTES()) + } + // Finally the non-zero LSB limb. + mstore(currentShiftedLimbPtr, shl(effectiveShifts, mload(currentShiftedLimbPtr))) + currentShiftedLimbPtr := add(currentShiftedLimbPtr, LIMB_SIZE_IN_BYTES()) + // Fill with zeros the shifted in limbs. + for { let i } lt(i, limbsToShiftOut) { i := add(i, 1) } { + mstore(currentShiftedLimbPtr, 0) + currentShiftedLimbPtr := add(currentShiftedLimbPtr, LIMB_SIZE_IN_BYTES()) + } + } + } + } + + /// @notice Add two big numbers. + /// @param augendPtr The pointer where the big number on the left operand starts. + /// @param addendPtr The pointer where the big number on right operand starts. + /// @param nLimbs The number of 32-byte words that the big numbers occupy. + /// @param sumPtr The pointer where the result of the addition will be stored. + /// @return overflowed A boolean indicating whether the addition overflowed (true) or not (false). + function bigUIntAdd(augendPtr, addendPtr, nLimbs, sumPtr) -> overflowed { + let totalLength := shl(5, nLimbs) + let carry + + let augendCurrentLimbPtr := add(augendPtr, totalLength) + let addendCurrentLimbPtr := add(addendPtr, totalLength) + + // Loop through each full 32-byte word to add the two big numbers. + for { let i := 1 } or(eq(i,nLimbs), lt(i, nLimbs)) { i := add(i, 1) } { + // Check limb from the right (least significant limb) + let currentLimbOffset := shl(5, i) + augendCurrentLimbPtr := sub(augendCurrentLimbPtr, currentLimbOffset) + addendCurrentLimbPtr := sub(addendCurrentLimbPtr, currentLimbOffset) + + let addendLimb := mload(addendCurrentLimbPtr) + let augendLimb := mload(augendCurrentLimbPtr) + let sum, overflow := overflowingAdd(augendLimb, addendLimb) + let sumWithPreviousCarry, carrySumOverflow := overflowingAdd(sum, carry) + sum := sumWithPreviousCarry + carry := or(overflow, carrySumOverflow) + let limbResultPtr := sub(add(sumPtr,totalLength), currentLimbOffset) + mstore(limbResultPtr, sum) + } + overflowed := carry + + } + + function getLimbValueAtOffset(limbPointer, anOffset) -> limbValue { + limbValue := mload(add(anOffset, limbPointer)) + } + + function storeLimbValueAtOffset(limbPointer, anOffset, aValue) { + mstore(add(limbPointer, anOffset), aValue) + } + + /// @notice Computes the difference between two 256 bit number and keeps + /// account of the borrow bit + /// in lshPointer and rhsPointer. + /// @dev Reference: https://github.com/lambdaclass/lambdaworks/blob/main/math/src/unsigned_integer/element.rs#L785 + /// @param leftLimb The left side of the difference (i.e. the a in a - b). + /// @param rightLimb The right side of the difference (i.e. the b in a - b). + /// @return subtractionResult i.e. the c in c = a - b. + /// @return returnBorrow If there was any borrow on the subtraction, is returned as 1. + function subLimbsWithBorrow(leftLimb, rightLimb, limbBorrow) -> subtractionResult, returnBorrow { + let rightPlusBorrow := add(rightLimb, limbBorrow) + subtractionResult := sub(leftLimb, rightPlusBorrow) + returnBorrow := gt(subtractionResult, leftLimb) + } + /// @notice Computes the BigUint subtraction between the number stored + /// in minuendPtr and subtrahendPtr. + /// @dev Reference: https://github.com/lambdaclass/lambdaworks/blob/main/math/src/unsigned_integer/element.rs#L795 + /// @param minuendPtr The start of the left hand side subtraction Big Number. + /// @param subtrahendPtr The start of the right hand side subtraction Big Number. + /// @return nLimbs The number of limbs of both numbers. + /// @return differencePtr Where the result will be stored. + function bigUIntSubWithBorrow(minuendPtr, subtrahendPtr, nLimbs, differencePtr) -> borrow { + let minuendCurrentLimb + let subtrahendCurrentLimb + let differenceCurrentLimb + borrow := 0 + let limbOffset + for { let i := nLimbs } gt(i, 0) { i := sub(i, 1) } { + limbOffset := shl(5, sub(i,1)) + let minuendCurrentLimb := getLimbValueAtOffset(minuendPtr, limbOffset) + let subtrahendCurrentLimb := getLimbValueAtOffset(subtrahendPtr, limbOffset) + differenceCurrentLimb, borrow := overflowingSubWithBorrow(minuendCurrentLimb, subtrahendCurrentLimb, borrow) + storeLimbValueAtOffset(differencePtr, limbOffset, differenceCurrentLimb) + } + } + + /// @notice Performs the multiplication between two bigUInts + /// @dev The result is stored from `productPtr` to `productPtr + (LIMB_SIZE * nLimbs)`. + /// @param multiplicandPtr The start index in memory of the first number. + /// @param multiplierPtr The start index in memory of the second number. + /// @param nLimbs The number of limbs needed to represent the operands. + function bigUIntMul(multiplicandPtr, multiplierPtr, nLimbs, productPtr) { + zeroWithLimbSizeAt(shl(1, nLimbs), productPtr) // product = 0 + + let retIndex, retWordAfter, retWordBefore + // Iterating over each limb in the first number. + for { let i := nLimbs } gt(i, 0) { i := sub(i, 1) } { + let carry + + // Iterating over each limb in the second number. + for { let j := nLimbs } gt(j, 0) { j := sub(j, 1) } { + // Loading the i-th and j-th limbs of the first and second numbers. + let word1 := mload(add(multiplicandPtr, shl(5, sub(i, 1)))) + let word2 := mload(add(multiplierPtr, shl(5, sub(j, 1)))) + + let product, carryFlag := overflowingAdd(mul(word1, word2), carry) + carry := add(getHighestHalfOfMultiplication(word1, word2), carryFlag) + + // Calculate the index to store the product. + retIndex := add(productPtr, shl(5, sub(add(i, j), 1))) + retWordBefore := mload(retIndex) // Load the previous value at the result index. + retWordAfter, carryFlag := overflowingAdd(retWordBefore, product) + + mstore(retIndex, retWordAfter) + carry := add(carry, carryFlag) + } + + // Store the last word which comes from the final carry. + retIndex := add(productPtr, shl(5, sub(i, 1))) + mstore(retIndex, carry) + } + } + + // @notice Computes the bit size of an unsigned integer. + // @dev Return value boundary: `0 <= bitSize <= 256` + // @param number An unsigned integer value. + // @return bitSize Number of bits required to represent `number`. + function UIntBitSize(number) -> bitSize { + // Increment bitSize until there are no significant bits left. + bitSize := 0 + for { let shift_me := number } lt(0, shift_me) { shift_me := shr(1, shift_me) } { + bitSize := add(bitSize, 1) + } + } + + /// @notice Computes the bit size of a big unsigned integer. + /// @param basePtr Base pointer for a big unsigned integer. + /// @param nLimbs The number of limbs needed to represent the operand. + /// @return bitSize Number of bits of the big unsigned integer. + function bigUIntBitSize(basePtr, nLimbs) -> bitSize { + bitSize := shl(8, nLimbs) + + // Iterate until finding the most significant limb or reach the end of the limbs. + let limb + let offset + for { let i } and(lt(i, nLimbs), iszero(limb)) { i := add(i, 1) } { + bitSize := sub(bitSize, 256) // Decrement one limb worth of bits. + let ptr_i := add(basePtr, offset) // = basePtr + i * 32 bytes + limb := mload(ptr_i) + offset := add(offset, LIMB_SIZE_IN_BYTES()) + } + + // At this point, `limb == limbs[i - 1]`. Where `i` equals the + // last value it took. + + // At this point, `bitSize` equals the amount of bits in the + // limbs following the most significant limb. + + bitSize := add(bitSize, UIntBitSize(limb)) + } + + /// @notice Performs in-place `x | 1` operation. + /// @dev This function will mutate the memory space `mem[basePtr...(basePtr + nLimbs * 32)]` + /// @dev It consumes constant time, aka `O(1)`. + /// @param basePtr Base pointer for a big unsigned integer. + /// @param nLimbs Number of 32 Byte limbs composing the big unsigned integer. + function bigUIntInPlaceOrWith1(basePtr, nLimbs) { + let offset := shl(5, sub(nLimbs, 1)) + let limbPtr := add(basePtr, offset) + let limb := mload(limbPtr) + mstore(limbPtr, or(limb, 0x1)) + } + + /// @notice Performs one shift to the left for a big unsigned integer (<<). + /// @dev The shift is performed in-place, mutating the memory space of the number. + /// @param numberPtr The pointer to the MSB of the number to shift. + /// @param nLimbs The number of limbs needed to represent the operand. + function bigUIntOneShiftLeft(numberPtr, nLimbs) { + let p := add(numberPtr, shl(5, nLimbs)) // numberPtr + 32 * nLimbs + let carryBit + for { } lt(numberPtr, p) { } { + p := sub(p, 32) + let limb := mload(p) + let msb := shr(255, limb) + limb := or(shl(1, limb), carryBit) + mstore(p, limb) + carryBit := msb + } + } + + /// @notice Performs one shift to the right for a big unsigned integer (>>). + /// @dev The shift is performed in-place, mutating the memory space of the number. + /// @param numberPtr The pointer to the MSB of the number to shift. + /// @param nLimbs The number of limbs needed to represent the operand. + function bigUIntOneShiftRight(numberPtr, nLimbs) { + let overflowPtr := add(numberPtr, shl(5, nLimbs)) + let carryBit + for { let p := numberPtr } lt(p, overflowPtr) { p := add(p, 32) } { + let limb := mload(p) + let lsb := and(limb, 1) + limb := or(shr(1, limb), carryBit) + carryBit := shl(255, lsb) + mstore(p, limb) + } + } + + /// @notice Computes the quotiend and reminder of dividing two big unsigned integers. + /// @dev + /// @dev Temporary buffers: + /// @dev ------------------ + /// @dev + /// @dev This function requires two temporary buffers for internal storage: + /// @dev - Both buffers must provide `nLimbs * 32` bytes of writable memory space. + /// @dev - Neither buffer should overlap with each other. + /// @dev - Neither needs to be initialized to any particular value. + /// @dev - Consider the written values as undefined after the function returns. + /// @dev + /// @dev Return values: + /// @dev -------------- + /// @dev + /// @dev - resulting `quotient` will be written `mem[basePtr, basePtr + 32 * nLimbs)` + /// @dev - resulting `reminder` will be written `mem[basePtr, basePtr + 32 * nLimbs)` + /// @dev + /// @param dividend_ptr Base pointer for a big unsigned integer representing the dividend. + /// @param divisor_ptr Base pointer for a big unsigned integer representing the divisor. + /// @param tmp_ptr_1 Base pointer for a contiguous memory space of `nLimbs` for internal usage. Will be overwritten. + /// @param tmp_ptr_2 Base pointer for a contiguous memory space of `nLimbs` for internal usage. Will be overwritten. + /// @param nLimbs Amount of limbs for each big unsigned integer. + /// @param quotient_ptr Base pointer for a big unsigned integer to write the division quotient. + /// @param rem_ptr Base pointer for a big unsigned integer to write the division remainder. + function bigUIntRem(dividend_ptr, divisor_ptr, tmp_ptr_1, tmp_ptr_2, nLimbs, realLimbs, modulusBitSize, rem_ptr) { + // Assign meaningful internal names to the temporary buffers passed as parameters. We use abstract names for + // parameters to prevent the leakage of implementation details. + zeroWithLimbSizeAt(nLimbs, tmp_ptr_1) // tmp_ptr_1 = 0 + zeroWithLimbSizeAt(nLimbs, tmp_ptr_2) // tmp_ptr_2 = 0 + + copyBigUint(nLimbs, dividend_ptr, rem_ptr) // rem = dividend + + let bd := sub(shl(8, realLimbs), modulusBitSize) + bigUIntShl(bd, divisor_ptr, nLimbs, tmp_ptr_1) // c == divisor << bd + + for { } iszero(0) { } { + let borrow := bigUIntSubWithBorrow(rem_ptr, tmp_ptr_1, nLimbs, tmp_ptr_2) + + if iszero(borrow) { + copyBigUint(nLimbs, tmp_ptr_2, rem_ptr) + } + + if iszero(bd) { + break + } + + bd := sub(bd, 1) + bigUIntOneShiftRight(tmp_ptr_1, nLimbs) // c = c >> 1 + } + } + + function bigUIntIsGreaterThanOne(nLimbs, basePtr) -> ret { + // Pointer to the least significant limb. + let p := add(basePtr, shl(5, sub(nLimbs, 1))) + + // Least significant limb. + let limb := mload(p) + + // If the least significant limb is greater than 1, we know for + // sure that the big unsigned integer will be greater than 1. + ret := gt(limb, 1) + + // If we don't know yet whether the big unsigned integer is + // greater than one, we will have to look if there exists a more + // significative limb thats greater than 0. + // + // We are iterating backwards, because the big unsigned integers + // we are working with may be left padded with zeros to match + // the size of other big unsigned integers. This way we have a + // better chance to consume less iterations. In the worst case + // scenario, where the answer is false, we will have to read the + // whole number from memory, making this algorithm `O(nLimbs)`. + for { } and(lt(basePtr, p), eq(ret, false)) { } { + p := sub(p, LIMB_SIZE_IN_BYTES()) + ret := lt(0, mload(p)) + } + } + + function bigUIntModTwo(nLimbs, basePtr) -> ret { + let p := add(basePtr, shl(5, sub(nLimbs, 1))) // Least significant limb addr. + ret := and(mload(p), 0x1) + } + + function flip(lhs, rhs) -> ret_lhs, ret_rhs { + ret_lhs := rhs + ret_rhs := lhs + } + + function bigUIntLowerHalfPtr(nLimbs, basePtr) -> p { + let upperHalfSizeInBytes := shl(4, nLimbs) // nLimbs * 32 / 2 + p := add(basePtr, upperHalfSizeInBytes) + } + + function oneLimbImplementation() -> { + let base := calldataload(96) + let exponent := calldataload(128) + let modulus := calldataload(160) + + // Note: This check covers the case where length of the modulo is zero or one. + // base^exponent % 0 = 0 || base^exponent % 1 = 0 || 0^exponent % modulus = 0 + if or(lt(modulus, 2), iszero(base)) { + mstore(0, 0) + return(0, 32) + } + + // 1^exponent % modulus = 1 || base^0 % modulus = 1 + if or(eq(base, 1), iszero(exponent)) { + mstore(0, 1) + return(0, 32) + } + + let pow := 1 + base := mod(base, modulus) + for {} gt(exponent, 0) {} { + if eq(mod(exponent, 2), 1) { + pow := mulmod(pow, base, modulus) + } + exponent := shr(1, exponent) + base := mulmod(base, base, modulus) + } + + mstore(0, pow) + return(0, 32) + } + + // @notice Computes the big uint modular exponentiation `result[] := base[] ** exponent[] % modulus[]`. + // @param nLimbs Amount of limbs that compose each of the big unsigned integer parameters. + // @param basePtr Base pointer to a big unsigned integer representing the `base[]`. It's most significant half must be zeros. + // @param exponentPtr Base pointer to a big unsigned integer representing the `exponent[]`. It's most significant half must be zeros. + // @param modulusPtr Base pointer to a big unsigned integer representing the `modulus[]`. Must be greater than 0. It's most significant half must be zeros. + // @param resultPtr Base pointer to a big unsigned integer to store the result[]. Must be initialized to zeros. + function bigUIntModularExponentiation(nLimbs, basePtr, exponentPtr, modulusPtr, resultPtr, scratchBuf1Ptr, scratchBuf2Ptr, scratchBuf3Ptr) { + // Algorithm pseudocode: + // See: https://en.wikipedia.org/wiki/Modular_exponentiation#Pseudocode + // function modular_pow(base, exponent, modulus) is + // if modulus = 1 then + // return 0 + // Assert :: (modulus - 1) * (modulus - 1) does not overflow base + // result := 1 + // base := base mod modulus + // while exponent > 0 do + // if (exponent mod 2 == 1) then + // result := (result * base) mod modulus + // exponent := exponent >> 1 + // base := (base * base) mod modulus + // return result + + // PSEUDOCODE: `if modulus = 1 then return 0`. + // We are using the precondition that `result == 0` and `0 < modulus`. + // FIXME: Does the algorithm work without this check? We may be paying the cost of running this function just for a rare test case. + if bigUIntIsGreaterThanOne(nLimbs, modulusPtr) { + + // Assert :: (modulus - 1) * (modulus - 1) does not overflow base + // We are certain that this is true because our precondition requires the most significant half of exponent to be zeros. + + // PSEUDOCODE: `result := 1` + // Again, we are using the precondition that `result[] == 0` + bigUIntInPlaceOrWith1(resultPtr, nLimbs) + let modulusBitSize := bigUIntBitSize(modulusPtr, nLimbs) + let exponentBitSize := bigUIntBitSize(exponentPtr, nLimbs) + + // PSEUDOCODE: `base := base mod modulus` + // FIXME: Is ok to mutate the base[] we were given? Shall we use a temporal buffer? + let limbsToRem := bigIntLimbsWithoutZeros(basePtr, nLimbs) + bigUIntRem(basePtr, modulusPtr, scratchBuf1Ptr, scratchBuf2Ptr, nLimbs, limbsToRem, modulusBitSize, scratchBuf3Ptr) + basePtr, scratchBuf3Ptr := flip(basePtr, scratchBuf3Ptr) + + // PSEUDOCODE: `while exponent > 0 do` + // FIXME: Is ok to mutate the exponent[] we were given? Shall we use a temporal buffer? + for { let i } lt(i, exponentBitSize) { i := add(i, 1) } { + let base_low_ptr := bigUIntLowerHalfPtr(nLimbs, basePtr) + // PSEUDOCODE: `if (exponent mod 2 == 1) then` + if bigUIntModTwo(nLimbs, exponentPtr) { + + // PSEUDOCODE: `result := (result * base) mod modulus` + // Since result[] is our return value, we are allowed to mutate it. + let result_low_ptr := bigUIntLowerHalfPtr(nLimbs, resultPtr) + + // scratch_buf_1 <- result * base. NOTICE that the higher half of `scratch_buf_1` may be non-0. + bigUIntMul(result_low_ptr, base_low_ptr, shr(1, nLimbs), scratchBuf1Ptr) + // result <- scratch_buf_1 % modulus. The upper half of return is guaranteed to be 0. + let limbsToRem := bigIntLimbsWithoutZeros(scratchBuf1Ptr, nLimbs) + bigUIntRem(scratchBuf1Ptr, modulusPtr, scratchBuf3Ptr, scratchBuf2Ptr, nLimbs, limbsToRem, modulusBitSize, resultPtr) + } + + // PSEUDOCODE: `exponent := exponent >> 1` + // FIXME: Is ok to mutate the exponent[] we were given? Shall we use a temporal buffer? + bigUIntOneShiftRight(exponentPtr, nLimbs) + + // PSEUDOCODE: `base := (base * base) mod modulus` + // scratch_buf_2 <- base * base + bigUIntMul(base_low_ptr, base_low_ptr, shr(1, nLimbs), scratchBuf2Ptr) + + let limbsToRem := bigIntLimbsWithoutZeros(scratchBuf2Ptr, nLimbs) + // base <- temp % modulus + bigUIntRem(scratchBuf2Ptr, modulusPtr, scratchBuf1Ptr, scratchBuf3Ptr, nLimbs, limbsToRem, modulusBitSize, basePtr) + } + } + } + + /// @notice Pad a big uint with zeros to the left until newLimbNumber is reached. + /// @dev The result is stored from `resultPtr` to `resultPtr + (LIMB_SIZE_IN_BYTES * newLimbNumber)`. + /// @dev If currentLimbNumber is equal to newLimbNumber, then the result is the same as the input. + /// @param ptr The pointer to the MSB of the number to pad. + /// @param currentLimbNumber The number of limbs needed to represent the operand. + /// @param newLimbNumber The number of limbs wanted to represent the operand. + /// @param resultPtr The pointer to the MSB of the padded number. + function bigUIntPadWithZeros(ptr, currentLimbNumber, newLimbNumber, resultPtr) { + for { let i } lt(i, currentLimbNumber) { i := add(i, 1) } { + // Move the limb to the right position + mstore(add(resultPtr, shl(5, sub(sub(newLimbNumber, 1), i))), mload(add(ptr, shl(5, sub(sub(currentLimbNumber,1), i))))) + } + } + + // Last limbs refers to the most significant limb in big-endian representation. + function parseCalldata(calldataValuePtr, calldataValueLen, resPtr) -> memoryValueLen { + // The in-memory value length in bytes of the calldata value. + memoryValueLen := calldataValueLen + let numberOfLimbs := div(calldataValueLen, LIMB_SIZE_IN_BYTES()) + let lastLimbMisalignmentInBytes := mod(calldataValueLen, LIMB_SIZE_IN_BYTES()) + let firstLimbExtraBytes := sub(LIMB_SIZE_IN_BYTES(), lastLimbMisalignmentInBytes) + let lastLimbBytes := sub(LIMB_SIZE_IN_BYTES(), firstLimbExtraBytes) + let misalignedWordPtr := sub(calldataValuePtr, firstLimbExtraBytes) + if lastLimbMisalignmentInBytes { + // If there is a misalignment, then we need to add one more limb to the result length. + numberOfLimbs := add(numberOfLimbs, 1) + memoryValueLen := shl(5, numberOfLimbs) + let misalignedLimb := calldataload(misalignedWordPtr) + let firstWordExtraBits := shl(3, firstLimbExtraBytes) + misalignedLimb := shl(firstWordExtraBits, misalignedLimb) + misalignedLimb := shr(firstWordExtraBits, misalignedLimb) + mstore(resPtr, misalignedLimb) + } + + let currentLimbCalldataPtr := calldataValuePtr + let currentLimbMemoryPtr := resPtr + for { let currentLimbNumber } lt(currentLimbNumber, numberOfLimbs) { currentLimbNumber := add(currentLimbNumber, 1) } { + if and(iszero(currentLimbNumber), gt(lastLimbMisalignmentInBytes, 0)) { + // If the MSL is misaligned, then at this point it has been handled and we should + // skip the first iteration (which handles the MSL if it is not misaligned). + currentLimbCalldataPtr := add(currentLimbCalldataPtr, lastLimbBytes) + currentLimbMemoryPtr := add(currentLimbMemoryPtr, LIMB_SIZE_IN_BYTES()) + continue + } + let currentLimb := calldataload(currentLimbCalldataPtr) + mstore(currentLimbMemoryPtr, currentLimb) + currentLimbCalldataPtr := add(currentLimbCalldataPtr, LIMB_SIZE_IN_BYTES()) + currentLimbMemoryPtr := add(currentLimbMemoryPtr, LIMB_SIZE_IN_BYTES()) + } + } + + //////////////////////////////////////////////////////////////// + // FALLBACK + //////////////////////////////////////////////////////////////// + let baseLen := calldataload(0) + let expLen := calldataload(32) + let modLen := calldataload(64) + + // Handle a special case when both the base and mod length are zeroes. + if and(iszero(baseLen), iszero(modLen)) { + return(0, 0) + } + + if and(and(eq(baseLen, 32), eq(expLen, 32)), eq(modLen, 32)) { + oneLimbImplementation() + } + + let basePtr := 96 + let expPtr := add(basePtr, baseLen) + let modPtr := add(expPtr, expLen) + + // Note: This check covers the case where length of the modulo is zero. + // base^exponent % 0 = 0 + if or(callDataBufferIsZero(modPtr, modLen), callDataBufferIsOne(modPtr, modLen)) { + // Fulfill memory with all zeroes. + for { let ptr } lt(ptr, modLen) { ptr := add(ptr, 32) } { + mstore(ptr, 0) + } + return(0, modLen) + } + + // 1^exponent % modulus = 1 + if callDataBufferIsOne(basePtr, baseLen) { + // Fulfill memory with all zeroes. + for { let ptr } lt(ptr, modLen) { ptr := add(ptr, 32) } { + mstore(ptr, 0) + } + mstore8(sub(modLen, 1), 1) + return(0, modLen) + } + + // base^0 % modulus = 1 + if callDataBufferIsZero(expPtr, expLen) { + // Fulfill memory with all zeroes. + for { let ptr } lt(ptr, modLen) { ptr := add(ptr, 32) } { + mstore(ptr, 0) + } + mstore8(sub(modLen, 1), 1) + return(0, modLen) + } + + // 0^exponent % modulus = 0 + if callDataBufferIsZero(basePtr, baseLen) { + // Fulfill memory with all zeroes. + for { let ptr } lt(ptr, modLen) { ptr := add(ptr, 32) } { + mstore(ptr, 0) + } + return(0, modLen) + } + + let limbsBaseLen, misalignment := bigIntLimbs(baseLen) + let limbsExpLen, misalignment := bigIntLimbs(expLen) + let limbsModLen, misalignment := bigIntLimbs(modLen) + + let ptrBaseLimbs + parseCalldata(basePtr, baseLen, ptrBaseLimbs) + + let ptrExpLimbs := shl(5, limbsBaseLen) + parseCalldata(expPtr, expLen, ptrExpLimbs) + + let ptrModLimbs := add(ptrExpLimbs, shl(5, limbsExpLen)) + parseCalldata(modPtr, modLen, ptrModLimbs) + + let maxLimbNumber := limbsBaseLen + if lt(maxLimbNumber, limbsExpLen) { + maxLimbNumber := limbsExpLen + } + if lt(maxLimbNumber, limbsModLen) { + maxLimbNumber := limbsModLen + } + + maxLimbNumber := add(maxLimbNumber, maxLimbNumber) + let memForMaxLimbNumber := shl(5, maxLimbNumber) + let baseStartPtr := add(ptrModLimbs, shl(5, limbsModLen)) + let exponentStartPtr := add(baseStartPtr, memForMaxLimbNumber) + let moduloStartPtr := add(exponentStartPtr, memForMaxLimbNumber) + + bigUIntPadWithZeros(ptrBaseLimbs, limbsBaseLen, maxLimbNumber, baseStartPtr) + bigUIntPadWithZeros(ptrExpLimbs, limbsExpLen, maxLimbNumber, exponentStartPtr) + bigUIntPadWithZeros(ptrModLimbs, limbsModLen, maxLimbNumber, moduloStartPtr) + + let scratchBufferPtr1 := add(moduloStartPtr, memForMaxLimbNumber) + let scratchBufferPtr2 := add(scratchBufferPtr1, memForMaxLimbNumber) + let scratchBufferPtr3 := add(scratchBufferPtr2, memForMaxLimbNumber) + let resultPtr := add(scratchBufferPtr3, memForMaxLimbNumber) + + bigUIntModularExponentiation(maxLimbNumber, baseStartPtr, exponentStartPtr, moduloStartPtr, resultPtr, scratchBufferPtr1, scratchBufferPtr2, scratchBufferPtr3) + + let finalResultEnd := add(resultPtr, memForMaxLimbNumber) + let finalResultStart := sub(finalResultEnd, modLen) + return(finalResultStart, modLen) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/precompiles/P256VERIFY.yul b/.test-node-subtree/etc/system-contracts/contracts/precompiles/P256VERIFY.yul new file mode 100644 index 00000000..9ace7842 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/precompiles/P256VERIFY.yul @@ -0,0 +1,605 @@ +object "P256VERIFY" { + code { } + object "P256VERIFY_deployed" { + code { + // Constants + + // CURVE CONSTANTS + + /// @notice Constant function for curve reduced elliptic group order. + /// @dev P is a prime number which defines the field which is a domain of the curve parameters. + /// @dev See https://neuromancer.sk/std/secg/secp256r1 for further details. + /// @return p The curve reduced elliptic group order. + function P() -> p { + p := 0xffffffff00000001000000000000000000000000ffffffffffffffffffffffff + } + + /// @notice Constant function for curve subgroup order. + /// @dev N is the order of generator G. + /// @dev See https://neuromancer.sk/std/secg/secp256r1 for further details. + /// @return n The curve subgroup order. + function N() -> n { + n := 0xffffffff00000000ffffffffffffffffbce6faada7179e84f3b9cac2fc632551 + } + + // MONTGOMERY CONSTANTS + + /// @notice Constant function for value one in Montgomery form for modulus P(). + /// @dev This value was precomputed using Python. + /// @return m_one The value one in Montgomery form. + function MONTGOMERY_ONE_P() -> m_one { + m_one := 26959946660873538059280334323183841250350249843923952699046031785985 + } + + /// @notice Constant function for value one in Montgomery form for modulus N(). + /// @dev This value was precomputed using Python. + /// @return m_one The value one in Montgomery form for modulus N(). + function MONTGOMERY_ONE_N() -> m_one { + m_one := 26959946660873538059280334323273029441504803697035324946844617595567 + } + + /// @notice Constant function curve parameter `a` in Montgomery form for modulus P(). + /// @dev See https://neuromancer.sk/std/secg/secp256r1 for further details. + /// @dev This value was precomputed using Python. + /// @return m_a The curve parameter `a` in Montgomery form for modulus P(). + function MONTGOMERY_A_P() -> m_a { + m_a := 115792089129476408780076832771566570560534619664239564663761773211729002495996 + } + + /// @notice Constant function curve parameter `b` in Montgomery form for modulus P(). + /// @dev See https://neuromancer.sk/std/secg/secp256r1 for further details. + /// @dev This value was precomputed using Python. + /// @return m_b The curve parameter `b` in Montgomery form for modulus P(). + function MONTGOMERY_B_P() -> m_b { + m_b := 99593677540221402957765480916910020772520766868399186769503856397241456836063 + } + + /// @notice Constant function for the generator point in Montgomery form for modulus P() in projective form. + /// @dev This value was precomputed using Python. + /// @return m_gx The x projective coordinate of the generator point in Montgomery form for modulus P(). + /// @return m_gy The y projective coordinate of the generator point in Montgomery form for modulus P(). + /// @return m_gz The z projective coordinate of the generator point in Montgomery form for modulus P(). + function MONTGOMERY_PROJECTIVE_G_P() -> m_gx, m_gy, m_gz { + m_gx := 0x18905F76A53755C679FB732B7762251075BA95FC5FEDB60179E730D418A9143C + m_gy := 0x8571FF1825885D85D2E88688DD21F3258B4AB8E4BA19E45CDDF25357CE95560A + m_gz := MONTGOMERY_ONE_P() + } + + /// @notice Constant function for the pre-computation of R^2 % P for the Montgomery REDC algorithm. + /// @dev R^2 is the Montgomery residue of the value 2^512. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value R^2 modulus the curve group order. + function R2_MOD_P() -> ret { + ret := 134799733323198995502561713907086292154532538166959272814710328655875 + } + + /// @notice Constant function for the pre-computation of R^2 % N for the Montgomery REDC algorithm. + /// @dev R^2 is the Montgomery residue of the value 2^512. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value R^2 modulus the curve group order. + function R2_MOD_N() -> ret { + ret := 46533765739406314298121036767150998762426774378559716911348521029833835802274 + } + + /// @notice Constant function for the pre-computation of P' for the Montgomery REDC algorithm. + /// @dev P' is a value such that PP' = -1 mod R, with N being the curve group order. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value P'. + function P_PRIME() -> ret { + ret := 115792089210356248768974548684794254293921932838497980611635986753331132366849 + } + + /// @notice Constant function for the pre-computation of N' for the Montgomery REDC algorithm. + /// @dev N' is a value such that NN' = -1 mod R, with N being the curve group order. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value N'. + function N_PRIME() -> ret { + ret := 43790243024438006127650828685417305984841428635278707415088219106730833919055 + } + + // Function Helpers + + /// @dev Executes the `precompileCall` opcode. + function precompileCall(precompileParams, gasToBurn) -> ret { + // Compiler simulation for calling `precompileCall` opcode + ret := verbatim_2i_1o("precompile", precompileParams, gasToBurn) + } + + /// @notice Burns remaining gas until revert. + /// @dev This function is used to burn gas in the case of a failed precompile call. + function burnGas() { + // Precompiles that do not have a circuit counterpart + // will burn the provided gas by calling this function. + precompileCall(0, gas()) + } + + // MONTGOMERY + + /// @notice Computes the inverse in Montgomery Form of a number in Montgomery Form. + /// @dev Reference: https://github.com/lambdaclass/lambdaworks/blob/main/math/src/field/fields/montgomery_backed_prime_fields.rs#L169 + /// @dev Let `base` be a number in Montgomery Form, then base = a*R mod modulus being `a` the base number (not in Montgomery Form) + /// @dev Let `inv` be the inverse of a number `a` in Montgomery Form, then inv = a^(-1)*R mod modulus + /// @dev The original binary extended euclidean algorithms takes a number a and returns a^(-1) mod N + /// @dev In our case N is modulus, and we'd like the input and output to be in Montgomery Form (a*R mod modulus + /// @dev and a^(-1)*R mod modulus respectively). + /// @dev If we just pass the input as a number in Montgomery Form the result would be a^(-1)*R^(-1) mod modulus, + /// @dev but we want it to be a^(-1)*R mod modulus. + /// @dev For that, we take advantage of the algorithm's linearity and multiply the result by R^2 mod modulus + /// @dev to get R^2*a^(-1)*R^(-1) mod modulus = a^(-1)*R mod modulus as the desired result in Montgomery Form. + /// @dev `inv` takes the value of `b` or `c` being the result sometimes `b` and sometimes `c`. In paper + /// @dev multiplying `b` or `c` by R^2 mod modulus results on starting their values as b = R^2 mod modulus and c = 0. + /// @param base A number `a` in Montgomery Form, then base = a*R mod modulus. + /// @param modulus The modulus. + /// @param r2 The pre-computed value of R^2 mod n. + /// @return inv The inverse of a number `a` in Montgomery Form, then inv = a^(-1)*R mod modulus. + function binaryExtendedEuclideanAlgorithm(base, modulus, r2) -> inv { + // Precomputation of 1 << 255 + let mask := 57896044618658097711785492504343953926634992332820282019728792003956564819968 + // modulus >> 255 == 0 -> modulus & 1 << 255 == 0 + let modulusHasSpareBits := iszero(and(modulus, mask)) + + let u := base + let v := modulus + // Avoids unnecessary reduction step. + let b := r2 + let c := 0x0 + + for {} and(iszero(eq(u, 0x1)), iszero(eq(v, 0x1))) {} { + for {} iszero(and(u, 0x1)) {} { + u := shr(1, u) + switch and(b, 0x1) + case 0 { + b := shr(1, b) + } + case 1 { + let newB, carry := overflowingAdd(b, modulus) + b := shr(1, newB) + + if and(iszero(modulusHasSpareBits), carry) { + b := or(b, mask) + } + } + } + + for {} iszero(and(v, 0x1)) {} { + v := shr(1, v) + switch and(c, 0x1) + case 0 { + c := shr(1, c) + } + case 1 { + let newC, carry := overflowingAdd(c, modulus) + c := shr(1, newC) + + if and(iszero(modulusHasSpareBits), carry) { + c := or(c, mask) + } + } + } + + switch gt(v, u) + case 0 { + u := sub(u, v) + if lt(b, c) { + b := add(b, modulus) + } + b := sub(b, c) + } + case 1 { + v := sub(v, u) + if lt(c, b) { + c := add(c, modulus) + } + c := sub(c, b) + } + } + + switch eq(u, 0x1) + case 0 { + inv := c + } + case 1 { + inv := b + } + } + + /// @notice Computes an addition and checks for overflow. + /// @param augend The value to add to. + /// @param addend The value to add. + /// @return sum The sum of the two values. + /// @return overflowed True if the addition overflowed, false otherwise. + function overflowingAdd(augend, addend) -> sum, overflowed { + sum := add(augend, addend) + overflowed := lt(sum, augend) + } + + /// @notice Retrieves the highest half of the multiplication result. + /// @param multiplicand The value to multiply. + /// @param multiplier The multiplier. + /// @return ret The highest half of the multiplication result. + function getHighestHalfOfMultiplication(multiplicand, multiplier) -> ret { + ret := verbatim_2i_1o("mul_high", multiplicand, multiplier) + } + + /// @notice Implementation of the Montgomery reduction algorithm (a.k.a. REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication//The_REDC_algorithm + /// @param lowestHalfOfT The lowest half of the value T. + /// @param higherHalfOfT The higher half of the value T. + /// @param n The modulus. + /// @param nPrime The pre-computed value of N' for the Montgomery REDC algorithm. + /// @return S The result of the Montgomery reduction. + function REDC(TLo, THi, n, nPrime) -> S { + let m := mul(TLo, nPrime) + let tHi, tHiOverflowed1 := overflowingAdd(THi, getHighestHalfOfMultiplication(m, n)) + let aLo, aLoOverflowed := overflowingAdd(TLo, mul(m, n)) + let tHiOverflowed2 := 0 + if aLoOverflowed { + tHi, tHiOverflowed2 := overflowingAdd(tHi, 1) + } + S := tHi + if or(or(tHiOverflowed1, tHiOverflowed2), iszero(lt(tHi, n))) { + S := sub(tHi, n) + } + } + + /// @notice Encodes a field element into the Montgomery form using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication//The_REDC_algorithmfor further details on transforming a field element into the Montgomery form. + /// @param a The field element to encode. + /// @param n The modulus. + /// @param nPrime The pre-computed value of N' for the Montgomery REDC algorithm. + /// @param r2 The pre-computed value of R^2 mod n. + /// @return ret The field element in Montgomery form. + function intoMontgomeryForm(a, n, nPrime, r2) -> ret { + let hi := getHighestHalfOfMultiplication(a, r2) + let lo := mul(a, r2) + ret := REDC(lo, hi, n, nPrime) + } + + /// @notice Decodes a field element out of the Montgomery form using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication//The_REDC_algorithm for further details on transforming a field element out of the Montgomery form. + /// @param m The field element in Montgomery form to decode. + /// @param n The modulus. + /// @param nPrime The pre-computed value of N' for the Montgomery REDC algorithm. + /// @return ret The decoded field element. + function outOfMontgomeryForm(m, n, nPrime) -> ret { + let hi := 0 + let lo := m + ret := REDC(lo, hi, n, nPrime) + } + + /// @notice Computes the Montgomery addition. + /// @param augend The augend in Montgomery form. + /// @param addend The addend in Montgomery form. + /// @param n The modulus. + /// @return ret The result of the Montgomery addition. + function montgomeryAdd(augend, addend, n) -> ret { + ret := addmod(augend, addend, n) + } + + /// @notice Computes the Montgomery subtraction. + /// @param minuend The minuend in Montgomery form. + /// @param subtrahend The subtrahend in Montgomery form. + /// @param n The modulus. + /// @return ret The result of the Montgomery subtraction. + function montgomerySub(minuend, subtrahend, n) -> ret { + ret := montgomeryAdd(minuend, sub(n, subtrahend), n) + } + + /// @notice Computes the Montgomery multiplication using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication//The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param multiplicand The multiplicand in Montgomery form. + /// @param multiplier The multiplier in Montgomery form. + /// @param n The modulus. + /// @param nPrime The pre-computed value of N' for the Montgomery REDC algorithm. + /// @return ret The result of the Montgomery multiplication. + function montgomeryMul(multiplicand, multiplier, n, nPrime) -> ret { + let hi := getHighestHalfOfMultiplication(multiplicand, multiplier) + let lo := mul(multiplicand, multiplier) + ret := REDC(lo, hi, n, nPrime) + } + + /// @notice Computes the Montgomery modular inverse skipping the Montgomery reduction step. + /// @dev The Montgomery reduction step is skept because a modification in the binary extended Euclidean algorithm is used to compute the modular inverse. + /// @dev See the function `binaryExtendedEuclideanAlgorithm` for further details. + /// @param a The field element in Montgomery form to compute the modular inverse of. + /// @param n The modulus. + /// @param r2 The pre-computed value of R^2 mod n. + /// @return invmod The result of the Montgomery modular inverse (in Montgomery form). + function montgomeryModularInverse(a, n, r2) -> invmod { + invmod := binaryExtendedEuclideanAlgorithm(a, n, r2) + } + + // CURVE ARITHMETICS + + /// @notice Checks if a field element is on the curve group order. + /// @dev A field element is on the curve group order if it is on the range [0, curveGroupOrder). + /// @param felt The field element to check. + /// @return ret True if the field element is in the range, false otherwise. + function fieldElementIsOnFieldOrder(felt) -> ret { + ret := lt(felt, P()) + } + + /// @notice Checks if a field element is on the subgroup order. + /// @dev A field element is on the subgroup order if it is on the range [0, subgroupOrder). + /// @param felt The field element to check. + /// @return ret True if the field element is in the range, false otherwise. + function fieldElementIsOnSubgroupOrder(felt) -> ret { + ret := lt(felt, N()) + } + + /// @notice Checks if affine coordinates are on the curve group order. + /// @dev Affine coordinates are on the curve group order if both coordinates are on the range [0, curveGroupOrder). + /// @param xp The x coordinate of the point P to check. + /// @param yp The y coordinate of the point P to check. + /// @return ret True if the coordinates are in the range, false otherwise. + function affinePointCoordinatesAreOnFieldOrder(xp, yp) -> ret { + ret := and(fieldElementIsOnFieldOrder(xp), fieldElementIsOnFieldOrder(yp)) + } + + /// @notice Checks if a point in affine coordinates is the point at infinity. + /// @dev The point at infinity is defined as the point (0, 0). + /// @dev See https://eips.ethereum.org/EIPS/eip-196 for further details. + /// @param xp The x coordinate of the point P in Montgomery form for modulus P(). + /// @param yp The y coordinate of the point P in Montgomery form for modulus P(). + /// @return ret True if the point is the point at infinity, false otherwise. + function affinePointIsInfinity(xp, yp) -> ret { + ret := iszero(or(xp, yp)) + } + + // @notice Checks if a point in affine coordinates in Montgomery form is on the curve. + // @dev The curve in question is the secp256r1 curve. + // @dev The Short Weierstrass equation of the curve is y^2 = x^3 + ax + b. + // @param xp The x coordinate of the point P in Montgomery form for modulus P(). + // @param yp The y coordinate of the point P in Montgomery form for modulus P(). + // @return ret True if the point is on the curve, false otherwise. + function affinePointIsOnCurve(xp, yp) -> ret { + let left := montgomeryMul(yp, yp, P(), P_PRIME()) + let right := montgomeryAdd(montgomeryMul(xp, montgomeryMul(xp, xp, P(), P_PRIME()), P(), P_PRIME()), montgomeryAdd(montgomeryMul(MONTGOMERY_A_P(), xp, P(), P_PRIME()), MONTGOMERY_B_P(), P()), P()) + ret := eq(left, right) + } + + /// @notice Converts a point in affine coordinates to projective coordinates in Montgomery form for modulus P(). + /// @dev The point at infinity is defined as the point (0, 0, 0). + /// @dev For performance reasons, the point is assumed to be previously checked to be on the + /// @dev curve and not the point at infinity. + /// @param xp The x coordinate of the point P in affine coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in affine coordinates in Montgomery form. + /// @return xr The x coordinate of the point P in projective coordinates in Montgomery form. + /// @return yr The y coordinate of the point P in projective coordinates in Montgomery form. + /// @return zr The z coordinate of the point P in projective coordinates in Montgomery form. + function projectiveFromAffine(xp, yp) -> xr, yr, zr { + xr := xp + yr := yp + zr := MONTGOMERY_ONE_P() + } + + /// @notice Checks if a point in projective coordinates is the point at infinity. + /// @dev The point at infinity is defined as the point (0, 0, 0). + /// @param xp The x coordinate of the point P in projective coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in projective coordinates in Montgomery form. + /// @param zp The z coordinate of the point P in projective coordinates in Montgomery form. + /// @return ret True if the point is the point at infinity, false otherwise. + function projectivePointIsInfinity(xp, yp, zp) -> ret { + ret := iszero(zp) + } + + /// @notice Doubles a point in projective coordinates in Montgomery form for modulus P(). + /// @dev See https://www.nayuki.io/page/elliptic-curve-point-addition-in-projective-coordinates for further details. + /// @dev For performance reasons, the point is assumed to be previously checked to be on the + /// @dev curve and not the point at infinity. + /// @param xp The x coordinate of the point P in projective coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in projective coordinates in Montgomery form. + /// @param zp The z coordinate of the point P in projective coordinates in Montgomery form. + /// @return xr The x coordinate of the point 2P in projective coordinates in Montgomery form. + /// @return yr The y coordinate of the point 2P in projective coordinates in Montgomery form. + /// @return zr The z coordinate of the point 2P in projective coordinates in Montgomery form. + function projectiveDouble(xp, yp, zp) -> xr, yr, zr { + let x_squared := montgomeryMul(xp, xp, P(), P_PRIME()) + let z_squared := montgomeryMul(zp, zp, P(), P_PRIME()) + let az_squared := montgomeryMul(MONTGOMERY_A_P(), z_squared, P(), P_PRIME()) + let t := montgomeryAdd(montgomeryAdd(x_squared, montgomeryAdd(x_squared, x_squared, P()), P()), az_squared, P()) + let yz := montgomeryMul(yp, zp, P(), P_PRIME()) + let u := montgomeryAdd(yz, yz, P()) + let uxy := montgomeryMul(u, montgomeryMul(xp, yp, P(), P_PRIME()), P(), P_PRIME()) + let v := montgomeryAdd(uxy, uxy, P()) + let w := montgomerySub(montgomeryMul(t, t, P(), P_PRIME()), montgomeryAdd(v, v, P()), P()) + + xr := montgomeryMul(u, w, P(), P_PRIME()) + let uy := montgomeryMul(u, yp, P(), P_PRIME()) + let uy_squared := montgomeryMul(uy, uy, P(), P_PRIME()) + yr := montgomerySub(montgomeryMul(t, montgomerySub(v, w, P()), P(), P_PRIME()), montgomeryAdd(uy_squared, uy_squared, P()), P()) + zr := montgomeryMul(u, montgomeryMul(u, u, P(), P_PRIME()), P(), P_PRIME()) + } + + /// @notice Adds two points in projective coordinates in Montgomery form for modulus P(). + /// @dev See https://www.nayuki.io/page/elliptic-curve-point-addition-in-projective-coordinates for further details. + /// @dev For performance reasons, the points are assumed to be previously checked to be on the + /// @dev curve and not the point at infinity. + /// @param xp The x coordinate of the point P in projective coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in projective coordinates in Montgomery form. + /// @param zp The z coordinate of the point P in projective coordinates in Montgomery form. + /// @param xq The x coordinate of the point Q in projective coordinates in Montgomery form. + /// @param yq The y coordinate of the point Q in projective coordinates in Montgomery form. + /// @param zq The z coordinate of the point Q in projective coordinates in Montgomery form. + /// @return xr The x coordinate of the point P + Q in projective coordinates in Montgomery form. + /// @return yr The y coordinate of the point P + Q in projective coordinates in Montgomery form. + /// @return zr The z coordinate of the point P + Q in projective coordinates in Montgomery form. + function projectiveAdd(xp, yp, zp, xq, yq, zq) -> xr, yr, zr { + let qIsInfinity := projectivePointIsInfinity(xq, yq, zq) + let pIsInfinity := projectivePointIsInfinity(xp, yp, zp) + if pIsInfinity { + // Infinity + Q = Q + xr := xq + yr := yq + zr := zq + leave + } + if qIsInfinity { + // P + Infinity = P + xr := xp + yr := yp + zr := zp + leave + } + + let t0 := montgomeryMul(yp, zq, P(), P_PRIME()) + let t1 := montgomeryMul(yq, zp, P(), P_PRIME()) + let t := montgomerySub(t0, t1, P()) + let u0 := montgomeryMul(xp, zq, P(), P_PRIME()) + let u1 := montgomeryMul(xq, zp, P(), P_PRIME()) + let u := montgomerySub(u0, u1, P()) + + // t = (yp*zq - yq*zp); u = (xp*zq - xq*zp) + if iszero(or(t, u)) { + // P + P = 2P + xr, yr, zr := projectiveDouble(xp, yp, zp) + leave + } + + // P1 + P2 = P3 + let u2 := montgomeryMul(u, u, P(), P_PRIME()) + let u3 := montgomeryMul(u2, u, P(), P_PRIME()) + let v := montgomeryMul(zp, zq, P(), P_PRIME()) + let w := montgomerySub(montgomeryMul(montgomeryMul(t, t, P(), P_PRIME()), v, P(), P_PRIME()), montgomeryMul(u2, montgomeryAdd(u0, u1, P()), P(), P_PRIME()), P()) + + xr := montgomeryMul(u, w, P(), P_PRIME()) + yr := montgomerySub(montgomeryMul(t, montgomerySub(montgomeryMul(u0, u2, P(), P_PRIME()), w, P()), P(), P_PRIME()), montgomeryMul(t0, u3, P(), P_PRIME()), P()) + zr := montgomeryMul(u3, v, P(), P_PRIME()) + } + + /// @notice Computes the linear combination of curve points: t0*Q + t1*G = R + /// @param xq The x coordinate of the point Q in projective coordinates in Montgomery form. + /// @param yq The y coordinate of the point Q in projective coordinates in Montgomery form. + /// @param zq The z coordinate of the point Q in projective coordinates in Montgomery form. + /// @param t0 The scalar to multiply the generator G by. + /// @param t1 The scalar to multiply the point Q by. + /// @return xr The x coordinate of the resulting point R in projective coordinates in Montgomery form. + /// @return yr The y coordinate of the resulting point R in projective coordinates in Montgomery form. + /// @return zr The z coordinate of the resulting point R in projective coordinates in Montgomery form. + function shamirLinearCombination(xq, yq, zq, t0, t1) -> xr, yr, zr { + let xg, yg, zg := MONTGOMERY_PROJECTIVE_G_P() + let xh, yh, zh := projectiveAdd(xg, yg, zg, xq, yq, zq) + let index, ret := findMostSignificantBitIndex(t0, t1) + switch ret + case 1 { + xr := xq + yr := yq + zr := zq + } + case 2 { + xr := xg + yr := yg + zr := zg + } + case 3 { + xr := xh + yr := yh + zr := zh + } + let ret + for {} gt(index, 0) {} { + index := sub(index, 1) + xr, yr, zr := projectiveDouble(xr, yr, zr) + ret := compareBits(index, t0, t1) + switch ret + case 1 { + xr, yr, zr := projectiveAdd(xr, yr, zr, xq, yq, zq) + } + case 2 { + xr, yr, zr := projectiveAdd(xr, yr, zr, xg, yg, zg) + } + case 3 { + xr, yr, zr := projectiveAdd(xr, yr, zr, xh, yh, zh) + } + } + } + + /// @notice Computes the largest index of the most significant bit among two scalars, + /// @notice and indicates which scalar it belongs to. + /// @param t0 The first scalar. + /// @param t1 The second scalar. + /// @return index The position of the most significant bit among t0 and t1. + /// @return ret Indicates which scalar the most significant bit belongs to. + /// @return return 1 if it belongs to t1, returns 2 if it belongs to t0, + /// @return and returns 3 if both have the most significant bit in the same position. + function findMostSignificantBitIndex(t0, t1) -> index, ret { + index := 255 + ret := 0 + for {} eq(ret, 0) { index := sub(index, 1) } { + ret := compareBits(index, t0, t1) + } + index := add(index, 1) + } + + /// @notice Compares the bits between two scalars at a specific position. + /// @param index The position to compare. + /// @param t0 The first scalar. + /// @param t1 The second scalar. + /// @return ret A value that indicates the value of the bits. + /// @return ret is 0 if both are 0. + /// @return ret is 1 if the bit of t0 is 0 and the bit of t1 is 1. + /// @return ret is 2 if the bit of t0 is 1 and the bit of t1 is 0. + /// @return ret is 3 if both bits are 1. + function compareBits(index, t0, t1) -> ret { + ret := add(mul(and(shr(index, t0), 1), 2), and(shr(index, t1), 1)) + } + + // Fallback + let hash := calldataload(0) + let r := calldataload(32) + let s := calldataload(64) + let x := calldataload(96) + let y := calldataload(128) + + if or(or(iszero(r), iszero(fieldElementIsOnSubgroupOrder(r))), or(iszero(s), iszero(fieldElementIsOnSubgroupOrder(s)))) { + burnGas() + } + + if or(affinePointIsInfinity(x, y), iszero(affinePointCoordinatesAreOnFieldOrder(x, y))) { + burnGas() + } + + x := intoMontgomeryForm(x, P(), P_PRIME(), R2_MOD_P()) + y := intoMontgomeryForm(y, P(), P_PRIME(), R2_MOD_P()) + + if iszero(affinePointIsOnCurve(x, y)) { + burnGas() + } + + let z + x, y, z := projectiveFromAffine(x, y) + + // TODO: Check if r, s, s1, t0 and t1 operations are optimal in Montgomery form or not + + hash := intoMontgomeryForm(hash, N(), N_PRIME(), R2_MOD_N()) + let rTmp := r + r := intoMontgomeryForm(r, N(), N_PRIME(), R2_MOD_N()) + s := intoMontgomeryForm(s, N(), N_PRIME(), R2_MOD_N()) + + let s1 := montgomeryModularInverse(s, N(), R2_MOD_N()) + + let t0 := outOfMontgomeryForm(montgomeryMul(hash, s1, N(), N_PRIME()), N(), N_PRIME()) + let t1 := outOfMontgomeryForm(montgomeryMul(r, s1, N(), N_PRIME()), N(), N_PRIME()) + + let xr, yr, zr := shamirLinearCombination(x, y, z, t0, t1) + if iszero(zr) { + mstore(0, 0) + return(0, 32) + } + + // As we only need xr in affine form, we can skip transforming the `y` coordinate. + let z_inv := montgomeryModularInverse(zr, P(), R2_MOD_P()) + xr := montgomeryMul(xr, z_inv, P(), P_PRIME()) + xr := outOfMontgomeryForm(xr, P(), P_PRIME()) + + xr := mod(xr, N()) + + mstore(0, eq(xr, rTmp)) + return(0, 32) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/precompiles/SHA256.yul b/.test-node-subtree/etc/system-contracts/contracts/precompiles/SHA256.yul new file mode 100644 index 00000000..fba02d5e --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/precompiles/SHA256.yul @@ -0,0 +1,103 @@ +/** + * @author Matter Labs + * @custom:security-contact security@matterlabs.dev + * @notice The contract used to emulate EVM's sha256 precompile. + * @dev It accepts the data to be hashed, pad it by the specification + * and uses `precompileCall` to call the zkEVM built-in precompiles. + * @dev Thus sha256 precompile circuit operates over padded data to perform efficient sponge round computation. + */ +object "SHA256" { + code { + return(0, 0) + } + object "SHA256_deployed" { + code { + //////////////////////////////////////////////////////////////// + // CONSTANTS + //////////////////////////////////////////////////////////////// + + /// @dev The size of the processing sha256 block in bytes. + function BLOCK_SIZE() -> ret { + ret := 64 + } + + /// @dev The gas cost of processing one sha256 round. + function SHA256_ROUND_GAS_COST() -> ret { + ret := 7 + } + + //////////////////////////////////////////////////////////////// + // HELPER FUNCTIONS + //////////////////////////////////////////////////////////////// + + // @dev Packs precompile parameters into one word. + // Note: functions expect to work with 32/64 bits unsigned integers. + // Caller should ensure the type matching before! + function unsafePackPrecompileParams( + uint32_inputOffsetInWords, + uint32_inputLengthInWords, + uint32_outputOffsetInWords, + uint32_outputLengthInWords, + uint64_perPrecompileInterpreted + ) -> rawParams { + rawParams := uint32_inputOffsetInWords + rawParams := or(rawParams, shl(32, uint32_inputLengthInWords)) + rawParams := or(rawParams, shl(64, uint32_outputOffsetInWords)) + rawParams := or(rawParams, shl(96, uint32_outputLengthInWords)) + rawParams := or(rawParams, shl(192, uint64_perPrecompileInterpreted)) + } + + /// @dev Executes the `precompileCall` opcode. + function precompileCall(precompileParams, gasToBurn) -> ret { + // Compiler simulation for calling `precompileCall` opcode + ret := verbatim_2i_1o("precompile", precompileParams, gasToBurn) + } + + //////////////////////////////////////////////////////////////// + // FALLBACK + //////////////////////////////////////////////////////////////// + + // Copy calldata to memory for pad it + let bytesSize := calldatasize() + calldatacopy(0, 0, bytesSize) + + // The sha256 padding includes additional 8 bytes of the total message's length in bits, + // so calculate the "full" message length with it. + let extendBytesLen := add(bytesSize, 8) + + let padLen := sub(BLOCK_SIZE(), mod(extendBytesLen, BLOCK_SIZE())) + let paddedBytesSize := add(extendBytesLen, padLen) + + // The original message size in bits + let binSize := mul(bytesSize, 8) + // Same bin size, but shifted to the left, needed for the padding + let leftShiftedBinSize := shl(sub(256, 64), binSize) + + // Write 0x80000... as padding according the sha256 specification + mstore(bytesSize, 0x8000000000000000000000000000000000000000000000000000000000000000) + // then will be some zeroes and BE encoded bit length + mstore(sub(paddedBytesSize, 8), leftShiftedBinSize) + + let numRounds := div(paddedBytesSize, BLOCK_SIZE()) + let precompileParams := unsafePackPrecompileParams( + 0, // input offset in words + // Always divisable by 32, since `BLOCK_SIZE()` is 64 bytes + div(paddedBytesSize, 32), // input length in words (safe to pass, never exceed `type(uint32).max`) + 0, // output offset in words + 1, // output length in words + numRounds // number of rounds (safe to pass, never exceed `type(uint64).max`) + ) + let gasToPay := mul(SHA256_ROUND_GAS_COST(), numRounds) + + let success := precompileCall(precompileParams, gasToPay) + + switch success + case 0 { + revert(0, 0) + } + default { + return(0, 32) + } + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/precompiles/secp256k1VERIFY.yul b/.test-node-subtree/etc/system-contracts/contracts/precompiles/secp256k1VERIFY.yul new file mode 100644 index 00000000..c017bf17 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/precompiles/secp256k1VERIFY.yul @@ -0,0 +1,607 @@ +object "SECP256K1VERIFY" { + code { } + object "SECP256K1VERIFY_deployed" { + code { + // Constants + + // CURVE CONSTANTS + + /// @notice Constant function for curve reduced elliptic group order. + /// @dev See https://neuromancer.sk/std/secg/secp256k1 for further details. + /// @return p The curve reduced elliptic group order. + function P() -> p { + p := 0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffefffffc2f + } + + /// @notice Constant function for curve subgroup order. + /// @dev See https://neuromancer.sk/std/secg/secp256k1 for further details. + /// @return n The curve subgroup order. + function N() -> n { + n := 0xfffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364141 + } + + // MONTGOMERY CONSTANTS + + /// @notice Constant function for value one in Montgomery form for modulus P(). + /// @dev This value was precomputed using Python. + /// @return m_one The value one in Montgomery form. + function MONTGOMERY_ONE_P() -> m_one { + m_one := 4294968273 + } + + /// @notice Constant function for value one in Montgomery form for modulus N(). + /// @dev This value was precomputed using Python. + /// @return m_one The value one in Montgomery form for modulus N(). + function MONTGOMERY_ONE_N() -> m_one { + m_one := 432420386565659656852420866394968145599 + } + + /// @notice Constant function curve parameter `b` in Montgomery form for modulus P(). + /// @dev See https://neuromancer.sk/std/secg/secp256r1 for further details. + /// @dev This value was precomputed using Python. + /// @return m_b The curve parameter `b` in Montgomery form for modulus P(). + function MONTGOMERY_B_P() -> m_b { + m_b := 30064777911 + } + + /// @notice Constant function for the generator point in Montgomery form for modulus P() in projective form. + /// @dev This value was precomputed using Python. + /// @return m_gx The x projective coordinate of the generator point in Montgomery form for modulus P(). + /// @return m_gy The y projective coordinate of the generator point in Montgomery form for modulus P(). + /// @return m_gz The z projective coordinate of the generator point in Montgomery form for modulus P(). + function MONTGOMERY_PROJECTIVE_G_P() -> m_gx, m_gy, m_gz { + m_gx := 69433378337113668455105412783699478161510570509662971881309371014080806920343 + m_gy := 93740989812233943577428291822008373258935927472951925563046116858250011585506 + m_gz := MONTGOMERY_ONE_P() + } + + /// @notice Constant function for the pre-computation of R^2 % P for the Montgomery REDC algorithm. + /// @dev R^2 is the Montgomery residue of the value 2^512. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value R^2 modulus the curve group order. + function R2_MOD_P() -> ret { + ret := 18446752466076602529 + } + + /// @notice Constant function for the pre-computation of R^2 % N for the Montgomery REDC algorithm. + /// @dev R^2 is the Montgomery residue of the value 2^512. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value R^2 modulus the curve group order. + function R2_MOD_N() -> ret { + ret := 71195301480278335217902614543643724933430614355449737089222010364394701574464 + } + + /// @notice Constant function for the pre-computation of P' for the Montgomery REDC algorithm. + /// @dev P' is a value such that PP' = -1 mod R, with N being the curve group order. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + /// @return ret The value P'. + function P_PRIME() -> ret { + ret := 91248989341183975618893650062416139444822672217621753343178995607987479196977 + } + + /// @notice Constant function for the pre-computation of N' for the Montgomery REDC algorithm. + /// @dev N' is a value such that NN' = -1 mod R, with N being the curve group order. + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication#The_REDC_algorithm for further detals. + /// @dev This value was precomputed using Python. + function N_PRIME() -> ret { + ret := 98562742561918706241446412617699626731532222289571144322335133855687966765375 + } + + // Function Helpers + + /// @dev Executes the `precompileCall` opcode. + function precompileCall(precompileParams, gasToBurn) -> ret { + // Compiler simulation for calling `precompileCall` opcode + ret := verbatim_2i_1o("precompile", precompileParams, gasToBurn) + } + + /// @notice Burns remaining gas until revert. + /// @dev This function is used to burn gas in the case of a failed precompile call. + function burnGas() { + // Precompiles that do not have a circuit counterpart + // will burn the provided gas by calling this function. + precompileCall(0, gas()) + } + + // MONTGOMERY + + /// @notice Computes the inverse in Montgomery Form of a number in Montgomery Form. + /// @dev Reference: https://github.com/lambdaclass/lambdaworks/blob/main/math/src/field/fields/montgomery_backed_prime_fields.rs#L169 + /// @dev Let `base` be a number in Montgomery Form, then base = a*R mod modulus being `a` the base number (not in Montgomery Form) + /// @dev Let `inv` be the inverse of a number `a` in Montgomery Form, then inv = a^(-1)*R mod modulus + /// @dev The original binary extended euclidean algorithms takes a number a and returns a^(-1) mod N + /// @dev In our case N is modulus, and we'd like the input and output to be in Montgomery Form (a*R mod modulus + /// @dev and a^(-1)*R mod modulus respectively). + /// @dev If we just pass the input as a number in Montgomery Form the result would be a^(-1)*R^(-1) mod modulus, + /// @dev but we want it to be a^(-1)*R mod modulus. + /// @dev For that, we take advantage of the algorithm's linearity and multiply the result by R^2 mod modulus + /// @dev to get R^2*a^(-1)*R^(-1) mod modulus = a^(-1)*R mod modulus as the desired result in Montgomery Form. + /// @dev `inv` takes the value of `b` or `c` being the result sometimes `b` and sometimes `c`. In paper + /// @dev multiplying `b` or `c` by R^2 mod modulus results on starting their values as b = R^2 mod modulus and c = 0. + /// @param base A number `a` in Montgomery Form, then base = a*R mod modulus. + /// @param modulus The modulus. + /// @param d The pre-computed value of R^2 mod modulus. + /// @return inv The inverse of a number `a` in Montgomery Form, then inv = a^(-1)*R mod modulus. + function binaryExtendedEuclideanAlgorithm(base, modulus, d) -> inv { + // Precomputation of 1 << 255 + let mask := 57896044618658097711785492504343953926634992332820282019728792003956564819968 + // modulus >> 255 == 0 -> modulus & 1 << 255 == 0 + let modulusHasSpareBits := iszero(and(modulus, mask)) + + let u := base + let v := modulus + // Avoids unnecessary reduction step. + let b := d + let c := 0x0 + + for {} and(iszero(eq(u, 0x1)), iszero(eq(v, 0x1))) {} { + for {} iszero(and(u, 0x1)) {} { + u := shr(1, u) + let currentB := b + switch and(currentB, 0x1) + case 0 { + b := shr(1, b) + } + case 1 { + let newB, carry := overflowingAdd(b, modulus) + b := shr(1, newB) + + if and(iszero(modulusHasSpareBits), carry) { + b := or(b, mask) + } + } + } + + for {} iszero(and(v, 0x1)) {} { + v := shr(1, v) + let currentC := c + switch and(currentC, 0x1) + case 0 { + c := shr(1, c) + } + case 1 { + let newC, carry := overflowingAdd(c, modulus) + c := shr(1, newC) + + if and(iszero(modulusHasSpareBits), carry) { + c := or(c, mask) + } + } + } + + switch gt(v, u) + case 0 { + u := sub(u, v) + if lt(b, c) { + b := add(b, modulus) + } + b := sub(b, c) + } + case 1 { + v := sub(v, u) + if lt(c, b) { + c := add(c, modulus) + } + c := sub(c, b) + } + } + + switch eq(u, 0x1) + case 0 { + inv := c + } + case 1 { + inv := b + } + } + + /// @notice Computes an addition and checks for overflow. + /// @param augend The value to add to. + /// @param addend The value to add. + /// @return sum The sum of the two values. + /// @return overflowed True if the addition overflowed, false otherwise. + function overflowingAdd(augend, addend) -> sum, overflowed { + sum := add(augend, addend) + overflowed := lt(sum, augend) + } + + /// @notice Retrieves the highest half of the multiplication result. + /// @param multiplicand The value to multiply. + /// @param multiplier The multiplier. + /// @return ret The highest half of the multiplication result. + function getHighestHalfOfMultiplication(multiplicand, multiplier) -> ret { + ret := verbatim_2i_1o("mul_high", multiplicand, multiplier) + } + + /// @notice Implementation of the Montgomery reduction algorithm (a.k.a. REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication//The_REDC_algorithm + /// @param lowestHalfOfT The lowest half of the value T. + /// @param higherHalfOfT The higher half of the value T. + /// @param n The modulus. + /// @param nPrime The pre-computed value of N'. + /// @return S The result of the Montgomery reduction. + function REDC(TLo, THi, n, nPrime) -> S { + let m := mul(TLo, nPrime) + let tHi, tHiOverflowed := overflowingAdd(THi, getHighestHalfOfMultiplication(m, n)) + let aLo, aLoOverflowed := overflowingAdd(TLo, mul(m, n)) + if tHiOverflowed { + // TODO: Check if this addition could overflow. + tHi := add(tHi, sub(0, n)) + } + if aLoOverflowed { + tHi, tHiOverflowed := overflowingAdd(tHi, 1) + } + if tHiOverflowed { + tHi, tHiOverflowed := overflowingAdd(tHi, sub(0, n)) + } + S := tHi + + if iszero(lt(tHi, n)) { + S := sub(tHi, n) + } + } + + /// @notice Encodes a field element into the Montgomery form using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication//The_REDC_algorithmfor further details on transforming a field element into the Montgomery form. + /// @param a The field element to encode. + /// @param n The modulus. + /// @param nPrime The pre-computed value of N' for the Montgomery REDC algorithm. + /// @param r2 The pre-computed value of R^2 mod n. + /// @return ret The field element in Montgomery form. + function intoMontgomeryForm(a, n, nPrime, r2) -> ret { + let hi := getHighestHalfOfMultiplication(a, r2) + let lo := mul(a, r2) + ret := REDC(lo, hi, n, nPrime) + } + + /// @notice Decodes a field element out of the Montgomery form using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication//The_REDC_algorithm for further details on transforming a field element out of the Montgomery form. + /// @param m The field element in Montgomery form to decode. + /// @param n The modulus. + /// @param nPrime The pre-computed value of N' for the Montgomery REDC algorithm. + /// @return ret The decoded field element. + function outOfMontgomeryForm(m, n, nPrime) -> ret { + let hi := 0 + let lo := m + ret := REDC(lo, hi, n, nPrime) + } + + /// @notice Computes the Montgomery addition. + /// @param augend The augend in Montgomery form. + /// @param addend The addend in Montgomery form. + /// @param n The modulus. + /// @return ret The result of the Montgomery addition. + function montgomeryAdd(augend, addend, n) -> ret { + ret := addmod(augend, addend, n) + } + + /// @notice Computes the Montgomery subtraction. + /// @param minuend The minuend in Montgomery form. + /// @param subtrahend The subtrahend in Montgomery form. + /// @param n The modulus. + /// @return ret The result of the Montgomery subtraction. + function montgomerySub(minuend, subtrahend, n) -> ret { + ret := montgomeryAdd(minuend, sub(n, subtrahend), n) + } + + /// @notice Computes the Montgomery multiplication using the Montgomery reduction algorithm (REDC). + /// @dev See https://en.wikipedia.org/wiki/Montgomery_modular_multiplication//The_REDC_algorithm for further details on the Montgomery multiplication. + /// @param multiplicand The multiplicand in Montgomery form. + /// @param multiplier The multiplier in Montgomery form. + /// @param n The modulus. + /// @param nPrime The pre-computed value of N' for the Montgomery REDC algorithm. + /// @return ret The result of the Montgomery multiplication. + function montgomeryMul(multiplicand, multiplier, n, nPrime) -> ret { + let hi := getHighestHalfOfMultiplication(multiplicand, multiplier) + let lo := mul(multiplicand, multiplier) + ret := REDC(lo, hi, n, nPrime) + } + + /// @notice Computes the Montgomery modular inverse skipping the Montgomery reduction step. + /// @dev The Montgomery reduction step is skept because a modification in the binary extended Euclidean algorithm is used to compute the modular inverse. + /// @dev See the function `binaryExtendedEuclideanAlgorithm` for further details. + /// @param a The field element in Montgomery form to compute the modular inverse of. + /// @param n The modulus. + /// @param r2 The pre-computed value of R^2 mod n. + /// @return invmod The result of the Montgomery modular inverse (in Montgomery form). + function montgomeryModularInverse(a, n, r2) -> invmod { + invmod := binaryExtendedEuclideanAlgorithm(a, n, r2) + } + + // CURVE ARITHMETICS + + /// @notice Checks if a field element is on the curve group order. + /// @dev A field element is on the curve group order if it is on the range [0, curveGroupOrder). + /// @param felt The field element to check. + /// @return ret True if the field element is in the range, false otherwise. + function fieldElementIsOnFieldOrder(felt) -> ret { + ret := lt(felt, P()) + } + + /// @notice Checks if a field element is on the subgroup order. + /// @dev A field element is on the subgroup order if it is on the range [0, subgroupOrder). + /// @param felt The field element to check. + /// @return ret True if the field element is in the range, false otherwise. + function fieldElementIsOnSubgroupOrder(felt) -> ret { + ret := lt(felt, N()) + } + + /// @notice Checks if affine coordinates are on the curve group order. + /// @dev Affine coordinates are on the curve group order if both coordinates are on the range [0, curveGroupOrder). + /// @param xp The x coordinate of the point P to check. + /// @param yp The y coordinate of the point P to check. + /// @return ret True if the coordinates are in the range, false otherwise. + function affinePointCoordinatesAreOnFieldOrder(xp, yp) -> ret { + ret := and(fieldElementIsOnFieldOrder(xp), fieldElementIsOnFieldOrder(yp)) + } + + /// @notice Checks if a point in affine coordinates is the point at infinity. + /// @dev The point at infinity is defined as the point (0, 0). + /// @dev See https://eips.ethereum.org/EIPS/eip-196 for further details. + /// @param xp The x coordinate of the point P in Montgomery form. + /// @param yp The y coordinate of the point P in Montgomery form. + /// @return ret True if the point is the point at infinity, false otherwise. + function affinePointIsInfinity(xp, yp) -> ret { + ret := iszero(or(xp, yp)) + } + + // @notice Checks if a point in affine coordinates in Montgomery form is on the curve. + // @dev The curve in question is the secp256r1 curve. + // @dev The Short Weierstrass equation of the curve is y^2 = x^3 + ax + b. + // @param xp The x coordinate of the point P in Montgomery form. + // @param yp The y coordinate of the point P in Montgomery form. + // @return ret True if the point is on the curve, false otherwise. + function affinePointIsOnCurve(xp, yp) -> ret { + let left := montgomeryMul(yp, yp, P(), P_PRIME()) + let right := montgomeryAdd(montgomeryMul(xp, montgomeryMul(xp, xp, P(), P_PRIME()), P(), P_PRIME()), MONTGOMERY_B_P(), P()) + ret := eq(left, right) + } + + /// @notice Converts a point in affine coordinates to projective coordinates in Montgomery form. + /// @dev The point at infinity is defined as the point (0, 0, 0). + /// @dev For performance reasons, the point is assumed to be previously checked to be on the + /// @dev curve and not the point at infinity. + /// @param xp The x coordinate of the point P in affine coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in affine coordinates in Montgomery form. + /// @return xr The x coordinate of the point P in projective coordinates in Montgomery form. + /// @return yr The y coordinate of the point P in projective coordinates in Montgomery form. + /// @return zr The z coordinate of the point P in projective coordinates in Montgomery form. + function projectiveFromAffine(xp, yp) -> xr, yr, zr { + xr := xp + yr := yp + zr := MONTGOMERY_ONE_P() + } + + /// @notice Checks if a point in projective coordinates is the point at infinity. + /// @dev The point at infinity is defined as the point (0, 0, 0). + /// @param xp The x coordinate of the point P in projective coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in projective coordinates in Montgomery form. + /// @param zp The z coordinate of the point P in projective coordinates in Montgomery form. + /// @return ret True if the point is the point at infinity, false otherwise. + function projectivePointIsInfinity(xp, yp, zp) -> ret { + ret := iszero(zp) + } + + /// @notice Doubles a point in projective coordinates in Montgomery form. + /// @dev See https://www.nayuki.io/page/elliptic-curve-point-addition-in-projective-coordinates for further details. + /// @dev For performance reasons, the point is assumed to be previously checked to be on the + /// @dev curve and not the point at infinity. + /// @param xp The x coordinate of the point P in projective coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in projective coordinates in Montgomery form. + /// @param zp The z coordinate of the point P in projective coordinates in Montgomery form. + /// @return xr The x coordinate of the point 2P in projective coordinates in Montgomery form. + /// @return yr The y coordinate of the point 2P in projective coordinates in Montgomery form. + /// @return zr The z coordinate of the point 2P in projective coordinates in Montgomery form. + function projectiveDouble(xp, yp, zp) -> xr, yr, zr { + let x_squared := montgomeryMul(xp, xp, P(), P_PRIME()) + let t := montgomeryAdd(x_squared, montgomeryAdd(x_squared, x_squared, P()), P()) + let yz := montgomeryMul(yp, zp, P(), P_PRIME()) + let u := montgomeryAdd(yz, yz, P()) + let uxy := montgomeryMul(u, montgomeryMul(xp, yp, P(), P_PRIME()), P(), P_PRIME()) + let v := montgomeryAdd(uxy, uxy, P()) + let w := montgomerySub(montgomeryMul(t, t, P(), P_PRIME()), montgomeryAdd(v, v, P()), P()) + + xr := montgomeryMul(u, w, P(), P_PRIME()) + let uy := montgomeryMul(u, yp, P(), P_PRIME()) + let uy_squared := montgomeryMul(uy, uy, P(), P_PRIME()) + yr := montgomerySub(montgomeryMul(t, montgomerySub(v, w, P()), P(), P_PRIME()), montgomeryAdd(uy_squared, uy_squared, P()), P()) + zr := montgomeryMul(u, montgomeryMul(u, u, P(), P_PRIME()), P(), P_PRIME()) + } + + /// @notice Adds two points in projective coordinates in Montgomery form. + /// @dev See https://www.nayuki.io/page/elliptic-curve-point-addition-in-projective-coordinates for further details. + /// @dev For performance reasons, the points are assumed to be previously checked to be on the + /// @dev curve and not the point at infinity. + /// @param xp The x coordinate of the point P in projective coordinates in Montgomery form. + /// @param yp The y coordinate of the point P in projective coordinates in Montgomery form. + /// @param zp The z coordinate of the point P in projective coordinates in Montgomery form. + /// @param xq The x coordinate of the point Q in projective coordinates in Montgomery form. + /// @param yq The y coordinate of the point Q in projective coordinates in Montgomery form. + /// @param zq The z coordinate of the point Q in projective coordinates in Montgomery form. + /// @return xr The x coordinate of the point P + Q in projective coordinates in Montgomery form. + /// @return yr The y coordinate of the point P + Q in projective coordinates in Montgomery form. + /// @return zr The z coordinate of the point P + Q in projective coordinates in Montgomery form. + function projectiveAdd(xp, yp, zp, xq, yq, zq) -> xr, yr, zr { + let qIsInfinity := projectivePointIsInfinity(xq, yq, zq) + let pIsInfinity := projectivePointIsInfinity(xp, yp, zp) + if and(pIsInfinity, qIsInfinity) { + // Infinity + Infinity = Infinity + xr := 0 + yr := MONTGOMERY_ONE_P() + zr := 0 + leave + } + if pIsInfinity { + // Infinity + Q = Q + xr := xq + yr := yq + zr := zq + leave + } + if qIsInfinity { + // P + Infinity = P + xr := xp + yr := yp + zr := zp + leave + } + if eq(montgomeryMul(xp, zq, P(), P_PRIME()), montgomeryMul(xq, zp, P(), P_PRIME())) { + if eq(montgomeryMul(yp, zq, P(), P_PRIME()), montgomeryMul(yq, zp, P(), P_PRIME())) { + // P + P = 2P + xr, yr, zr := projectiveDouble(xp, yp, zp) + leave + } + // P + (-P) = Infinity + xr := 0 + yr := MONTGOMERY_ONE_P() + zr := 0 + leave + } + + // P1 + P2 = P3 + let t0 := montgomeryMul(yq, zp, P(), P_PRIME()) + let t1 := montgomeryMul(yp, zq, P(), P_PRIME()) + let t := montgomerySub(t0, t1, P()) + let u0 := montgomeryMul(xq, zp, P(), P_PRIME()) + let u1 := montgomeryMul(xp, zq, P(), P_PRIME()) + let u := montgomerySub(u0, u1, P()) + let u2 := montgomeryMul(u, u, P(), P_PRIME()) + let u3 := montgomeryMul(u2, u, P(), P_PRIME()) + let v := montgomeryMul(zq, zp, P(), P_PRIME()) + let w := montgomerySub(montgomeryMul(montgomeryMul(t, t, P(), P_PRIME()), v, P(), P_PRIME()), montgomeryMul(u2, montgomeryAdd(u0, u1, P()), P(), P_PRIME()), P()) + + xr := montgomeryMul(u, w, P(), P_PRIME()) + yr := montgomerySub(montgomeryMul(t, montgomerySub(montgomeryMul(u0, u2, P(), P_PRIME()), w, P()), P(), P_PRIME()), montgomeryMul(t0, u3, P(), P_PRIME()), P()) + zr := montgomeryMul(u3, v, P(), P_PRIME()) + } + + /// @notice Computes the linear combination of curve points: t0*Q + t1*G = R + /// @param xq The x coordinate of the point Q in projective coordinates in Montgomery form. + /// @param yq The y coordinate of the point Q in projective coordinates in Montgomery form. + /// @param zq The z coordinate of the point Q in projective coordinates in Montgomery form. + /// @param t0 The scalar to multiply the point Q by. + /// @param t1 The scalar to multiply the generator G by. + /// @return xr The x coordinate of the resulting point R in projective coordinates in Montgomery form. + /// @return yr The y coordinate of the resulting point R in projective coordinates in Montgomery form. + /// @return zr The z coordinate of the resulting point R in projective coordinates in Montgomery form. + function shamirLinearCombination(xq, yq, zq, t0, t1) -> xr, yr, zr { + let xg, yg, zg := MONTGOMERY_PROJECTIVE_G_P() + let xh, yh, zh := projectiveAdd(xg, yg, zg, xq, yq, zq) + let index, ret := findMostSignificantBitIndex(t0, t1) + switch ret + case 1 { + xr := xq + yr := yq + zr := zq + } + case 2 { + xr := xg + yr := yg + zr := zg + } + case 3 { + xr := xh + yr := yh + zr := zh + } + let ret + for {} gt(index, 0) {} { + index := sub(index, 1) + xr, yr, zr := projectiveDouble(xr, yr, zr) + ret := compareBits(index, t0, t1) + switch ret + case 1 { + xr, yr, zr := projectiveAdd(xr, yr, zr, xq, yq, zq) + } + case 2 { + xr, yr, zr := projectiveAdd(xr, yr, zr, xg, yg, zg) + } + case 3 { + xr, yr, zr := projectiveAdd(xr, yr, zr, xh, yh, zh) + } + } + } + + /// @notice Computes the largest index of the most significant bit among two scalars, + /// @notice and indicates which scalar it belongs to. + /// @param t0 The first scalar. + /// @param t1 The second scalar. + /// @return index The position of the most significant bit among t0 and t1. + /// @return ret Indicates which scalar the most significant bit belongs to. + /// @return return 1 if it belongs to t1, returns 2 if it belongs to t0, + /// @return and returns 3 if both have the most significant bit in the same position. + function findMostSignificantBitIndex(t0, t1) -> index, ret { + index := 255 + ret := 0 + for {} eq(ret, 0) { index := sub(index, 1) } { + ret := compareBits(index, t0, t1) + } + index := add(index, 1) + } + + /// @notice Compares the bits between two scalars at a specific position. + /// @param index The position to compare. + /// @param t0 The first scalar. + /// @param t1 The second scalar. + /// @return ret A value that indicates the value of the bits. + /// @return ret is 0 if both are 0. + /// @return ret is 1 if the bit of t0 is 0 and the bit of t1 is 1. + /// @return ret is 2 if the bit of t0 is 1 and the bit of t1 is 0. + /// @return ret is 3 if both bits are 1. + function compareBits(index, t0, t1) -> ret { + ret := add(mul(and(shr(index, t0), 1), 2), and(shr(index, t1), 1)) + } + + // Fallback + let hash := calldataload(0) + let r := calldataload(32) + let s := calldataload(64) + let x := calldataload(96) + let y := calldataload(128) + + + if or(or(iszero(r), iszero(fieldElementIsOnSubgroupOrder(r))), or(iszero(s), iszero(fieldElementIsOnSubgroupOrder(s)))) { + burnGas() + } + + if or(affinePointIsInfinity(x, y), iszero(affinePointCoordinatesAreOnFieldOrder(x, y))) { + burnGas() + } + + x := intoMontgomeryForm(x, P(), P_PRIME(), R2_MOD_P()) + y := intoMontgomeryForm(y, P(), P_PRIME(), R2_MOD_P()) + + if iszero(affinePointIsOnCurve(x, y)) { + burnGas() + } + + let z + x, y, z := projectiveFromAffine(x, y) + + hash := intoMontgomeryForm(hash, N(), N_PRIME(), R2_MOD_N()) + r := intoMontgomeryForm(r, N(), N_PRIME(), R2_MOD_N()) + s := intoMontgomeryForm(s, N(), N_PRIME(), R2_MOD_N()) + + let s1 := montgomeryModularInverse(s, N(), R2_MOD_N()) + + let t0 := outOfMontgomeryForm(montgomeryMul(hash, s1, N(), N_PRIME()), N(), N_PRIME()) + let t1 := outOfMontgomeryForm(montgomeryMul(r, s1, N(), N_PRIME()), N(), N_PRIME()) + + let xr, yr, zr := shamirLinearCombination(x, y, z, t0, t1) + + // As we only need xr in affine form, we can skip transforming the `y` coordinate. + let z_inv := montgomeryModularInverse(zr, P(), R2_MOD_P()) + xr := montgomeryMul(xr, z_inv, P(), P_PRIME()) + xr := outOfMontgomeryForm(xr, P(), P_PRIME()) + + r := outOfMontgomeryForm(r, N(), N_PRIME()) + xr := mod(xr, N()) + + mstore(0, eq(xr, r)) + return(0, 32) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/Callable.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/Callable.sol new file mode 100644 index 00000000..e7477e0c --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/Callable.sol @@ -0,0 +1,19 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +contract Callable { + event Called(uint256 value, bytes data); + + fallback() external payable { + uint256 len; + assembly { + len := calldatasize() + } + bytes memory data = new bytes(len); + assembly { + calldatacopy(add(data, 0x20), 0, len) + } + emit Called(msg.value, data); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/DelegateCaller.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/DelegateCaller.sol new file mode 100644 index 00000000..caa5aae6 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/DelegateCaller.sol @@ -0,0 +1,20 @@ +// SPDX-License-Identifier: MIT + +pragma solidity ^0.8.0; + +contract DelegateCaller { + function delegateCall(address _to) external payable { + assembly { + calldatacopy(0, 0, calldatasize()) + let result := delegatecall(gas(), _to, 0, calldatasize(), 0, 0) + returndatacopy(0, 0, returndatasize()) + switch result + case 0 { + revert(0, returndatasize()) + } + default { + return(0, returndatasize()) + } + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/Deployable.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/Deployable.sol new file mode 100644 index 00000000..be35861a --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/Deployable.sol @@ -0,0 +1,19 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +contract Deployable { + event Deployed(uint256 value, bytes data); + + constructor() payable { + uint256 len; + assembly { + len := codesize() + } + bytes memory data = new bytes(len); + assembly { + codecopy(add(data, 0x20), 0, len) + } + emit Deployed(msg.value, data); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/DummyUpgrade.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/DummyUpgrade.sol new file mode 100644 index 00000000..b369f9a9 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/DummyUpgrade.sol @@ -0,0 +1,11 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +contract DummyUpgrade { + event Upgraded(); + + function performUpgrade() public { + emit Upgraded(); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/EventWriterTest.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/EventWriterTest.sol new file mode 100644 index 00000000..faf09cd7 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/EventWriterTest.sol @@ -0,0 +1,31 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +contract EventWriterTest { + event ZeroTopics(bytes data) anonymous; + event OneTopic(bytes data); + event TwoTopics(uint256 indexed topic1, bytes data); + event ThreeTopics(uint256 indexed topic1, uint256 indexed topic2, bytes data); + event FourTopics(uint256 indexed topic1, uint256 indexed topic2, uint256 indexed topic3, bytes data); + + function zeroTopics(bytes calldata data) external { + emit ZeroTopics(data); + } + + function oneTopic(bytes calldata data) external { + emit OneTopic(data); + } + + function twoTopics(uint256 topic1, bytes calldata data) external { + emit TwoTopics(topic1, data); + } + + function threeTopics(uint256 topic1, uint256 topic2, bytes calldata data) external { + emit ThreeTopics(topic1, topic2, data); + } + + function fourTopics(uint256 topic1, uint256 topic2, uint256 topic3, bytes calldata data) external { + emit FourTopics(topic1, topic2, topic3, data); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/MockERC20Approve.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/MockERC20Approve.sol new file mode 100644 index 00000000..c9931389 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/MockERC20Approve.sol @@ -0,0 +1,16 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +contract MockERC20Approve { + event Approved(address to, uint256 value); + + function approve(address spender, uint256 value) external returns (bool) { + emit Approved(spender, value); + return true; + } + + function allowance(address owner, address spender) external view returns (uint256) { + return 0; + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/MockKnownCodesStorage.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/MockKnownCodesStorage.sol new file mode 100644 index 00000000..7cec142e --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/MockKnownCodesStorage.sol @@ -0,0 +1,19 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +contract MockKnownCodesStorage { + event MockBytecodePublished(bytes32 indexed bytecodeHash); + + function markBytecodeAsPublished(bytes32 _bytecodeHash) external { + emit MockBytecodePublished(_bytecodeHash); + } + + // To be able to deploy original know codes storage again + function getMarker(bytes32) public pure returns (uint256 marker) { + return 1; + } + + // To prevent failing during calls from the bootloader + fallback() external {} +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/MockL1Messenger.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/MockL1Messenger.sol new file mode 100644 index 00000000..b24da511 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/MockL1Messenger.sol @@ -0,0 +1,16 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +contract MockL1Messenger { + event MockBytecodeL1Published(bytes32 indexed bytecodeHash); + + function requestBytecodeL1Publication(bytes32 _bytecodeHash) external { + emit MockBytecodeL1Published(_bytecodeHash); + } + + // To prevent failing during calls from the bootloader + function sendToL1(bytes calldata) external returns (bytes32) { + return bytes32(0); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/NotSystemCaller.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/NotSystemCaller.sol new file mode 100644 index 00000000..0c85deb6 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/NotSystemCaller.sol @@ -0,0 +1,30 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +contract NotSystemCaller { + address immutable to; + + constructor(address _to) { + to = _to; + } + + fallback() external payable { + address _to = to; + assembly { + calldatacopy(0, 0, calldatasize()) + + let result := call(gas(), _to, callvalue(), 0, calldatasize(), 0, 0) + + returndatacopy(0, 0, returndatasize()) + + switch result + case 0 { + revert(0, returndatasize()) + } + default { + return(0, returndatasize()) + } + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/SystemCaller.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/SystemCaller.sol new file mode 100644 index 00000000..58adfce2 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/SystemCaller.sol @@ -0,0 +1,25 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {SystemContractsCaller} from "../libraries/SystemContractsCaller.sol"; + +contract SystemCaller { + address immutable to; + + constructor(address _to) { + to = _to; + } + + fallback() external payable { + bytes memory result = SystemContractsCaller.systemCallWithPropagatedRevert( + uint32(gasleft()), + to, + uint128(msg.value), + msg.data + ); + assembly { + return(add(result, 0x20), mload(result)) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/TestSystemContract.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/TestSystemContract.sol new file mode 100644 index 00000000..8eba841d --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/TestSystemContract.sol @@ -0,0 +1,137 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import "../Constants.sol"; + +import "../DefaultAccount.sol"; + +import "../libraries/EfficientCall.sol"; +import "../interfaces/ISystemContract.sol"; +import {SystemContractHelper} from "../libraries/SystemContractHelper.sol"; +import {TestSystemContractHelper} from "./TestSystemContractHelper.sol"; + +/// @notice An example of a system contract that be used for local testing. +/// @dev It is not used anywhere except for testing +contract TestSystemContract is ISystemContract { + modifier onlySelf() { + require(msg.sender == address(this)); + _; + } + + function testPrecompileCall() external view { + // Without precompile call + { + uint256 gasBefore = gasleft(); + uint256 gasAfter = gasleft(); + require(gasBefore - gasAfter < 10, "Spent too much gas"); + } + + { + uint256 gasBefore = gasleft(); + SystemContractHelper.unsafePrecompileCall(0, 10000); + uint256 gasAfter = gasleft(); + require(gasBefore - gasAfter > 10000, "Did not spend enough gas"); + require(gasBefore - gasAfter < 10100, "Spent too much gas"); + } + } + + function testMimicCallAndValue(address whoToMimic, uint128 value) external { + // Note that we don't need to actually have the needed balance to set the `msg.value` for the next call + SystemContractHelper.setValueForNextFarCall(value); + this.performMimicCall( + address(this), + whoToMimic, + abi.encodeCall(TestSystemContract.saveContext, ()), + false, + false + ); + + require(latestMsgSender == whoToMimic, "mimicCall does not work"); + require(latestMsgValue == value, "setValueForNextFarCall does not work"); + } + + address public latestMsgSender; + uint128 public latestMsgValue; + uint256 public extraAbiData1; + uint256 public extraAbiData2; + + function saveContext() external payable { + latestMsgSender = msg.sender; + latestMsgValue = uint128(msg.value); + extraAbiData1 = SystemContractHelper.getExtraAbiData(0); + extraAbiData2 = SystemContractHelper.getExtraAbiData(1); + } + + function testOnlySystemModifier() external { + // Firstly, system contracts should be able to call it + (bool success, ) = address(this).call(abi.encodeCall(TestSystemContract.requireOnlySystem, ())); + require(success, "System contracts can call onlySystemCall methods"); + + // Non-system contract accounts should not be able to call it. + success = this.performRawMimicCall( + address(this), + address(MAX_SYSTEM_CONTRACT_ADDRESS + 1), + abi.encodeCall(TestSystemContract.requireOnlySystem, ()), + false, + false + ); + require(!success, "Normal acounts cannot call onlySystemCall methods without proper flags"); + + success = this.performRawMimicCall( + address(this), + address(MAX_SYSTEM_CONTRACT_ADDRESS + 1), + abi.encodeCall(TestSystemContract.requireOnlySystem, ()), + false, + true + ); + require(success, "Normal acounts cannot call onlySystemCall methods without proper flags"); + } + + function requireOnlySystem() external onlySystemCall {} + + function testSystemMimicCall() external { + this.performSystemMimicCall( + address(this), + address(MAX_SYSTEM_CONTRACT_ADDRESS + 1), + abi.encodeCall(TestSystemContract.saveContext, ()), + false, + 100, + 120 + ); + + require(extraAbiData1 == 100, "extraAbiData1 passed incorrectly"); + require(extraAbiData2 == 120, "extraAbiData2 passed incorrectly"); + } + + function performMimicCall( + address to, + address whoToMimic, + bytes calldata data, + bool isConstructor, + bool isSystem + ) external onlySelf returns (bytes memory) { + return EfficientCall.mimicCall(uint32(gasleft()), to, data, whoToMimic, isConstructor, isSystem); + } + + function performRawMimicCall( + address to, + address whoToMimic, + bytes calldata data, + bool isConstructor, + bool isSystem + ) external onlySelf returns (bool) { + return EfficientCall.rawMimicCall(uint32(gasleft()), to, data, whoToMimic, isConstructor, isSystem); + } + + function performSystemMimicCall( + address to, + address whoToMimic, + bytes calldata data, + bool isConstructor, + uint256 extraAbiParam1, + uint256 extraAbiParam2 + ) external onlySelf { + TestSystemContractHelper.systemMimicCall(to, whoToMimic, data, isConstructor, extraAbiParam1, extraAbiParam2); + } +} diff --git a/.test-node-subtree/etc/system-contracts/contracts/test-contracts/TestSystemContractHelper.sol b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/TestSystemContractHelper.sol new file mode 100644 index 00000000..2f9f7073 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/contracts/test-contracts/TestSystemContractHelper.sol @@ -0,0 +1,108 @@ +// SPDX-License-Identifier: MIT + +pragma solidity 0.8.20; + +import {MAX_SYSTEM_CONTRACT_ADDRESS, MSG_VALUE_SYSTEM_CONTRACT} from "../Constants.sol"; + +import "../libraries/SystemContractsCaller.sol"; +import "../libraries/SystemContractHelper.sol"; +import "../libraries/Utils.sol"; + +library TestSystemContractHelper { + /// @notice Perform a `mimicCall` with `isSystem` flag, with the ability to pass extra abi data. + /// @param to The address to call + /// @param whoToMimic The `msg.sender` for the next call. + /// @param data The calldata + /// @param isConstructor Whether the call should contain the `isConstructor` flag. + /// @param extraAbiParam1 The first extraAbi param to pass with the call + /// @param extraAbiParam2 The second extraAbi param to pass with the call + /// @return The returndata if the call was successful. Reverts otherwise. + /// @dev If called not in kernel mode, it will result in a revert (enforced by the VM) + function systemMimicCall( + address to, + address whoToMimic, + bytes calldata data, + bool isConstructor, + uint256 extraAbiParam1, + uint256 extraAbiParam2 + ) internal returns (bytes memory) { + bool success = rawSystemMimicCall(to, whoToMimic, data, isConstructor, extraAbiParam1, extraAbiParam2); + + uint256 size; + assembly { + size := returndatasize() + } + if (!success) { + assembly { + returndatacopy(0, 0, size) + revert(0, size) + } + } + + bytes memory result = new bytes(size); + assembly { + mstore(result, size) + returndatacopy(add(result, 0x20), 0, size) + } + return result; + } + + /// @notice Perform a `mimicCall` with `isSystem` flag, with the ability to pass extra abi data. + /// @param to The address to call + /// @param whoToMimic The `msg.sender` for the next call. + /// @param data The calldata + /// @param isConstructor Whether the call should contain the `isConstructor` flag. + /// @param extraAbiParam1 The first extraAbi param to pass with the call + /// @param extraAbiParam2 The second extraAbi param to pass with the call + /// @return success whether the call was successful. + /// @dev If called not in kernel mode, it will result in a revert (enforced by the VM) + function rawSystemMimicCall( + address to, + address whoToMimic, + bytes calldata data, + bool isConstructor, + uint256 extraAbiParam1, + uint256 extraAbiParam2 + ) internal returns (bool success) { + SystemContractHelper.loadCalldataIntoActivePtr(); + + // Currently, zkEVM considers the pointer valid if(ptr.offset < ptr.length || (ptr.length == 0 && ptr.offset == 0)), otherwise panics. + // So, if the data is empty we need to make the `ptr.length = ptr.offset = 0`, otherwise follow standard logic. + if (data.length == 0) { + // Safe to cast, offset is never bigger than `type(uint32).max` + SystemContractHelper.ptrShrinkIntoActive(uint32(msg.data.length)); + } else { + uint256 dataOffset; + assembly { + dataOffset := data.offset + } + + // Safe to cast, offset is never bigger than `type(uint32).max` + SystemContractHelper.ptrAddIntoActive(uint32(dataOffset)); + // Safe to cast, `data.length` is never bigger than `type(uint32).max` + uint32 shrinkTo = uint32(msg.data.length - (data.length + dataOffset)); + SystemContractHelper.ptrShrinkIntoActive(shrinkTo); + } + + uint32 gas = Utils.safeCastToU32(gasleft()); + uint256 farCallAbi = SystemContractsCaller.getFarCallABIWithEmptyFatPointer( + gas, + // Only rollup is supported for now + 0, + CalldataForwardingMode.ForwardFatPointer, + isConstructor, + true + ); + SystemContractHelper.ptrPackIntoActivePtr(farCallAbi); + + address callAddr = SYSTEM_MIMIC_CALL_BY_REF_CALL_ADDRESS; + uint256 cleanupMask = ADDRESS_MASK; + assembly { + // Clearing values before usage in assembly, since Solidity + // doesn't do it by default + whoToMimic := and(whoToMimic, cleanupMask) + + success := call(to, callAddr, 0, 0, whoToMimic, extraAbiParam1, extraAbiParam2) + } + } +} diff --git a/.test-node-subtree/etc/system-contracts/hardhat.config.ts b/.test-node-subtree/etc/system-contracts/hardhat.config.ts new file mode 100644 index 00000000..8e0acfd4 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/hardhat.config.ts @@ -0,0 +1,55 @@ +import "@matterlabs/hardhat-zksync-chai-matchers"; +import "@matterlabs/hardhat-zksync-solc"; +import "@nomiclabs/hardhat-ethers"; +import "@nomiclabs/hardhat-solpp"; +import "@typechain/hardhat"; + +// eslint-disable-next-line @typescript-eslint/no-var-requires +const systemConfig = require("./SystemConfig.json"); + +export default { + zksolc: { + version: "latest", + compilerSource: "binary", + settings: { + isSystem: true, + }, + }, + zkSyncDeploy: { + zkSyncNetwork: "http://localhost:3050", + ethNetwork: "http://localhost:8545", + }, + solidity: { + version: "0.8.20", + settings: { + optimizer: { + enabled: true, + runs: 9999999, + }, + outputSelection: { + "*": { + "*": ["storageLayout"], + }, + }, + }, + }, + solpp: { + defs: (() => { + return { + ECRECOVER_COST_GAS: systemConfig.ECRECOVER_COST_GAS, + KECCAK_ROUND_COST_GAS: systemConfig.KECCAK_ROUND_COST_GAS, + SHA256_ROUND_COST_GAS: systemConfig.SHA256_ROUND_COST_GAS, + }; + })(), + }, + networks: { + hardhat: { + zksync: true, + }, + zkSyncTestNode: { + url: "http://127.0.0.1:8011", + ethNetwork: "", + zksync: true, + }, + }, +}; diff --git a/.test-node-subtree/etc/system-contracts/package.json b/.test-node-subtree/etc/system-contracts/package.json new file mode 100644 index 00000000..ad977d73 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/package.json @@ -0,0 +1,78 @@ +{ + "name": "system-contracts", + "version": "0.1.0", + "repository": "git@github.com:matter-labs/system-contracts.git", + "license": "MIT", + "dependencies": { + "@matterlabs/hardhat-zksync-deploy": "^0.6.5", + "@nomiclabs/hardhat-solpp": "^2.0.1", + "commander": "^9.4.1", + "ethers": "^5.7.0", + "hardhat": "=2.16.0", + "preprocess": "^3.2.0", + "zksync-web3": "^0.14.3" + }, + "devDependencies": { + "@matterlabs/eslint-config-typescript": "^1.1.2", + "@matterlabs/hardhat-zksync-chai-matchers": "^0.1.4", + "@matterlabs/hardhat-zksync-solc": "^0.4.2", + "@matterlabs/prettier-config": "^1.0.3", + "@nomicfoundation/hardhat-chai-matchers": "^1.0.3", + "@nomiclabs/hardhat-ethers": "^2.0.6", + "@typechain/ethers-v5": "^10.0.0", + "@typechain/hardhat": "^7.0.0", + "@types/chai": "^4.3.1", + "@types/lodash": "^4.14.199", + "@types/mocha": "^9.1.1", + "@types/node": "^17.0.34", + "@typescript-eslint/eslint-plugin": "^6.7.4", + "@typescript-eslint/parser": "^6.7.4", + "chai": "^4.3.6", + "eslint": "^8.51.0", + "eslint-import-resolver-typescript": "^3.6.1", + "eslint-plugin-import": "^2.29.0", + "eslint-plugin-prettier": "^5.0.1", + "lodash": "^4.17.21", + "markdownlint-cli": "^0.33.0", + "mocha": "^10.0.0", + "prettier": "^3.0.3", + "prettier-plugin-solidity": "^1.1.3", + "solhint": "^3.6.2", + "template-file": "^6.0.1", + "ts-generator": "^0.1.1", + "ts-node": "^10.7.0", + "typechain": "^8.1.1", + "typescript": "^4.6.4" + }, + "mocha": { + "timeout": 240000, + "exit": true, + "color": false, + "slow": 0, + "require": [ + "ts-node/register" + ] + }, + "scripts": { + "build": "yarn build:sol && yarn build:yul", + "build:sol": "hardhat compile", + "build:yul": "yarn preprocess:yul && yarn compile-yul", + "calculate-hashes:check": "ts-node scripts/calculate-hashes.ts --check-only", + "calculate-hashes:fix": "ts-node scripts/calculate-hashes.ts", + "clean": "yarn clean:sol && yarn clean:yul", + "clean:sol": "hardhat clean", + "clean:yul": "rm -rf ./bootloader/build ./bootloader/tests/artifacts ./contracts/artifacts ./contracts/precompiles/artifacts", + "compile-yul": "ts-node scripts/compile-yul.ts", + "deploy-preimages": "ts-node scripts/deploy-preimages.ts", + "lint:check": "yarn lint:md && yarn lint:sol && yarn lint:ts && yarn prettier:check", + "lint:fix": "yarn lint:md --fix && yarn lint:sol --fix && yarn lint:ts --fix && yarn prettier:fix", + "lint:md": "markdownlint \"**/*.md\"", + "lint:sol": "solhint \"contracts/**/*.sol\"", + "lint:ts": "eslint .", + "preprocess:yul": "rm -rf ./bootloader/build && yarn ts-node scripts/process.ts", + "prettier:check": "prettier --check \"**/*.{js,json,md,sol,ts,yaml}\"", + "prettier:fix": "prettier --write \"**/*.{js,json,md,sol,ts,yaml}\"", + "test": "hardhat test --network zkSyncTestNode", + "test:bootloader": "cd bootloader/test_infra && cargo run" + } +} diff --git a/.test-node-subtree/etc/system-contracts/scripts/calculate-hashes.ts b/.test-node-subtree/etc/system-contracts/scripts/calculate-hashes.ts new file mode 100644 index 00000000..bc7fb007 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/scripts/calculate-hashes.ts @@ -0,0 +1,230 @@ +import { ethers } from "ethers"; +import * as fs from "fs"; +import _ from "lodash"; +import os from "os"; +import { join } from "path"; +import { hashBytecode } from "zksync-web3/build/src/utils"; + +type ContractDetails = { + contractName: string; + bytecodePath: string; + sourceCodePath: string; +}; + +type Hashes = { + bytecodeHash: string; + sourceCodeHash: string; +}; + +type SystemContractHashes = ContractDetails & Hashes; + +const findDirsEndingWith = + (endingWith: string) => + (path: string): string[] => { + const absolutePath = makePathAbsolute(path); + try { + const dirs = fs.readdirSync(absolutePath, { withFileTypes: true }).filter((dirent) => dirent.isDirectory()); + const dirsEndingWithSol = dirs.filter((dirent) => dirent.name.endsWith(endingWith)); + return dirsEndingWithSol.map((dirent) => dirent.name); + } catch (err) { + const msg = err instanceof Error ? err.message : "Unknown error"; + throw new Error(`Failed to read directory: ${absolutePath} Error: ${msg}`); + } + }; + +const SOLIDITY_ARTIFACTS_DIR = "artifacts-zk"; + +const getSolidityContractDetails = (dir: string, contractName: string): ContractDetails => { + const bytecodePath = join(SOLIDITY_ARTIFACTS_DIR, dir, contractName + ".sol", contractName + ".json"); + const sourceCodePath = join(dir, contractName + ".sol"); + return { + contractName, + bytecodePath, + sourceCodePath, + }; +}; + +const getSolidityContractsDetails = (dir: string): ContractDetails[] => { + const bytecodesDir = join(SOLIDITY_ARTIFACTS_DIR, dir); + const dirsEndingWithSol = findDirsEndingWith(".sol")(bytecodesDir); + const contractNames = dirsEndingWithSol.map((d) => d.replace(".sol", "")); + const solidityContractsDetails = contractNames.map((c) => getSolidityContractDetails(dir, c)); + return solidityContractsDetails; +}; + +const YUL_ARTIFACTS_DIR = "artifacts"; + +const getYulContractDetails = (dir: string, contractName: string): ContractDetails => { + const bytecodePath = join(dir, YUL_ARTIFACTS_DIR, contractName + ".yul", contractName + ".yul.zbin"); + const sourceCodePath = join(dir, contractName + ".yul"); + return { + contractName, + bytecodePath, + sourceCodePath, + }; +}; + +const getYulContractsDetails = (dir: string): ContractDetails[] => { + const bytecodesDir = join(dir, YUL_ARTIFACTS_DIR); + const dirsEndingWithYul = findDirsEndingWith(".yul")(bytecodesDir); + const contractNames = dirsEndingWithYul.map((d) => d.replace(".yul", "")); + const yulContractsDetails = contractNames.map((c) => getYulContractDetails(dir, c)); + return yulContractsDetails; +}; + +const makePathAbsolute = (path: string): string => { + return join(__dirname, "..", path); +}; + +const readSourceCode = (details: ContractDetails): string => { + const absolutePath = makePathAbsolute(details.sourceCodePath); + try { + return ethers.utils.hexlify(fs.readFileSync(absolutePath)); + } catch (err) { + const msg = err instanceof Error ? err.message : "Unknown error"; + throw new Error(`Failed to read source code for ${details.contractName}: ${absolutePath} Error: ${msg}`); + } +}; + +const readBytecode = (details: ContractDetails): string => { + const absolutePath = makePathAbsolute(details.bytecodePath); + try { + if (details.bytecodePath.endsWith(".json")) { + const jsonFile = fs.readFileSync(absolutePath, "utf8"); + return ethers.utils.hexlify(JSON.parse(jsonFile).bytecode); + } else { + return ethers.utils.hexlify(fs.readFileSync(absolutePath)); + } + } catch (err) { + const msg = err instanceof Error ? err.message : "Unknown error"; + throw new Error(`Failed to read bytecode for ${details.contractName}: ${details.bytecodePath} Error: ${msg}`); + } +}; + +const getHashes = (contractName: string, sourceCode: string, bytecode: string): Hashes => { + try { + return { + bytecodeHash: ethers.utils.hexlify(hashBytecode(bytecode)), + // The extra checks performed by the hashBytecode function are not needed for the source code, therefore + // sha256 is used for simplicity + sourceCodeHash: ethers.utils.sha256(sourceCode), + }; + } catch (err) { + const msg = err instanceof Error ? err.message : "Unknown error"; + throw new Error(`Failed to calculate hashes for ${contractName} Error: ${msg}`); + } +}; + +const getSystemContractsHashes = (systemContractsDetails: ContractDetails[]): SystemContractHashes[] => + systemContractsDetails.map((contractDetails) => { + const sourceCode = readSourceCode(contractDetails); + const bytecode = readBytecode(contractDetails); + const hashes = getHashes(contractDetails.contractName, sourceCode, bytecode); + + const systemContractHashes: SystemContractHashes = { + ...contractDetails, + ...hashes, + }; + + return systemContractHashes; + }); + +const readSystemContractsHashesFile = (path: string): SystemContractHashes[] => { + const absolutePath = makePathAbsolute(path); + try { + const file = fs.readFileSync(absolutePath, "utf8"); + const parsedFile = JSON.parse(file); + return parsedFile; + } catch (err) { + const msg = err instanceof Error ? err.message : "Unknown error"; + throw new Error(`Failed to read file: ${absolutePath} Error: ${msg}`); + } +}; + +const saveSystemContractsHashesFile = (path: string, systemContractsHashes: SystemContractHashes[]) => { + const absolutePath = makePathAbsolute(path); + try { + fs.writeFileSync(absolutePath, JSON.stringify(systemContractsHashes, null, 2) + os.EOL); + } catch (err) { + const msg = err instanceof Error ? err.message : "Unknown error"; + throw new Error(`Failed to save file: ${absolutePath} Error: ${msg}`); + } +}; + +const findDifferences = (newHashes: SystemContractHashes[], oldHashes: SystemContractHashes[]) => { + const differentElements = _.xorWith(newHashes, oldHashes, _.isEqual); + + const differentUniqueElements = _.uniqWith(differentElements, (a, b) => a.contractName === b.contractName); + + const differencesList = differentUniqueElements.map((diffElem) => { + const newHashesElem = newHashes.find((elem) => elem.contractName === diffElem.contractName); + + const oldHashesElem = oldHashes.find((elem) => elem.contractName === diffElem.contractName); + + const differingFields = _.xorWith( + Object.entries(newHashesElem || {}), + Object.entries(oldHashesElem || {}), + _.isEqual + ); + + const differingFieldsUniqueKeys = _.uniq(differingFields.map(([key]) => key)); + + return { + contract: diffElem.contractName, + differingFields: differingFieldsUniqueKeys, + old: oldHashesElem || {}, + new: newHashesElem || {}, + }; + }); + + return differencesList; +}; + +const SOLIDITY_SOURCE_CODE_PATHS = ["cache-zk/solpp-generated-contracts"]; +const YUL_SOURCE_CODE_PATHS = ["contracts", "contracts/precompiles", "bootloader/build"]; +const OUTPUT_FILE_PATH = "SystemContractsHashes.json"; + +const main = async () => { + const args = process.argv; + if (args.length > 3 || (args.length == 3 && !args.includes("--check-only"))) { + console.log( + "This command can be used with no arguments or with the --check-only flag. Use the --check-only flag to check the hashes without updating the SystemContractsHashes.json file." + ); + process.exit(1); + } + const checkOnly = args.includes("--check-only"); + + const solidityContractsDetails = _.flatten(SOLIDITY_SOURCE_CODE_PATHS.map(getSolidityContractsDetails)); + const yulContractsDetails = _.flatten(YUL_SOURCE_CODE_PATHS.map(getYulContractsDetails)); + const systemContractsDetails = [...solidityContractsDetails, ...yulContractsDetails]; + + const newSystemContractsHashes = getSystemContractsHashes(systemContractsDetails); + const oldSystemContractsHashes = readSystemContractsHashesFile(OUTPUT_FILE_PATH); + if (_.isEqual(newSystemContractsHashes, oldSystemContractsHashes)) { + console.log("Calculated hashes match the hashes in the SystemContractsHashes.json file."); + console.log("Exiting..."); + return; + } + const differences = findDifferences(newSystemContractsHashes, oldSystemContractsHashes); + console.log("Calculated hashes differ from the hashes in the SystemContractsHashes.json file. Differences:"); + console.log(differences); + if (checkOnly) { + console.log("You can use the `yarn calculate-hashes:fix` command to update the SystemContractsHashes.json file."); + console.log("Exiting..."); + process.exit(1); + } else { + console.log("Updating..."); + saveSystemContractsHashesFile(OUTPUT_FILE_PATH, newSystemContractsHashes); + console.log("Update finished"); + console.log("Exiting..."); + return; + } +}; + +main() + .then(() => process.exit(0)) + .catch((err) => { + console.error("Error:", err.message || err); + console.log("Please make sure to run `yarn build` before running this script."); + process.exit(1); + }); diff --git a/.test-node-subtree/etc/system-contracts/scripts/compile-yul.ts b/.test-node-subtree/etc/system-contracts/scripts/compile-yul.ts new file mode 100644 index 00000000..e3fac6f2 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/scripts/compile-yul.ts @@ -0,0 +1,101 @@ +import * as hre from "hardhat"; + +import { getZksolcUrl, saltFromUrl } from "@matterlabs/hardhat-zksync-solc"; +import { spawn as _spawn } from "child_process"; +import * as fs from "fs"; +import { getCompilersDir } from "hardhat/internal/util/global-dir"; +import path from "path"; + +const COMPILER_VERSION = "1.3.22"; +const IS_COMPILER_PRE_RELEASE = false; + +async function compilerLocation(): Promise { + const compilersCache = await getCompilersDir(); + + let salt = ""; + + if (IS_COMPILER_PRE_RELEASE) { + // @ts-ignore + const url = getZksolcUrl("https://github.com/matter-labs/zksolc-prerelease", hre.config.zksolc.version); + salt = saltFromUrl(url); + } + + return path.join(compilersCache, "zksolc", `zksolc-v${COMPILER_VERSION}${salt ? "-" : ""}${salt}`); +} + +// executes a command in a new shell +// but pipes data to parent's stdout/stderr +export function spawn(command: string) { + command = command.replace(/\n/g, " "); + const child = _spawn(command, { stdio: "inherit", shell: true }); + return new Promise((resolve, reject) => { + child.on("error", reject); + child.on("close", (code) => { + code == 0 ? resolve(code) : reject(`Child process exited with code ${code}`); + }); + }); +} + +export async function compileYul(path: string, files: string[], outputDirName: string | null) { + if (!files.length) { + console.log(`No test files provided in folder ${path}.`); + return; + } + const paths = preparePaths(path, files, outputDirName); + + const zksolcLocation = await compilerLocation(); + await spawn( + `${zksolcLocation} ${paths.absolutePathSources}/${paths.outputDir} --optimization 3 --system-mode --yul --bin --overwrite -o ${paths.absolutePathArtifacts}/${paths.outputDir}` + ); +} + +export async function compileYulFolder(path: string) { + const files: string[] = (await fs.promises.readdir(path)).filter((fn) => fn.endsWith(".yul")); + for (const file of files) { + await compileYul(path, [file], `${file}`); + } +} + +function preparePaths(path: string, files: string[], outputDirName: string | null): CompilerPaths { + const filePaths = files + .map((val) => { + return `sources/${val}`; + }) + .join(" "); + const currentWorkingDirectory = process.cwd(); + console.log(`Yarn project directory: ${currentWorkingDirectory}`); + + const outputDir = outputDirName || files[0]; + // This script is located in `system-contracts/scripts`, so we get one directory back. + const absolutePathSources = `${__dirname}/../${path}`; + const absolutePathArtifacts = `${__dirname}/../${path}/artifacts`; + + return new CompilerPaths(filePaths, outputDir, absolutePathSources, absolutePathArtifacts); +} + +class CompilerPaths { + public filePath: string; + public outputDir: string; + public absolutePathSources: string; + public absolutePathArtifacts: string; + constructor(filePath: string, outputDir: string, absolutePathSources: string, absolutePathArtifacts: string) { + this.filePath = filePath; + this.outputDir = outputDir; + this.absolutePathSources = absolutePathSources; + this.absolutePathArtifacts = absolutePathArtifacts; + } +} + +async function main() { + await compileYulFolder("contracts"); + await compileYulFolder("contracts/precompiles"); + await compileYulFolder("bootloader/build"); + await compileYulFolder("bootloader/tests"); +} + +main() + .then(() => process.exit(0)) + .catch((err) => { + console.error("Error:", err.message || err); + process.exit(1); + }); diff --git a/.test-node-subtree/etc/system-contracts/scripts/constants.ts b/.test-node-subtree/etc/system-contracts/scripts/constants.ts new file mode 100644 index 00000000..991f5ef9 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/scripts/constants.ts @@ -0,0 +1,431 @@ +import type { BigNumberish, BytesLike } from "ethers"; +import { constants, ethers } from "ethers"; + +export const BOOTLOADER_FORMAL_ADDRESS = "0x0000000000000000000000000000000000008001"; +export const ETH_ADDRESS = constants.AddressZero; + +export enum Language { + Solidity = "solidity", + Yul = "yul", +} + +export interface SystemContractDescription { + address: string; + codeName: string; +} + +export interface YulContractDescrption extends SystemContractDescription { + lang: Language.Yul; + path: string; +} + +export interface SolidityContractDescription extends SystemContractDescription { + lang: Language.Solidity; +} + +interface ISystemContracts { + [key: string]: YulContractDescrption | SolidityContractDescription; +} + +export const SYSTEM_CONTRACTS: ISystemContracts = { + zeroAddress: { + // zero address has EmptyContract code + address: "0x0000000000000000000000000000000000000000", + codeName: "EmptyContract", + lang: Language.Solidity, + }, + ecrecover: { + address: "0x0000000000000000000000000000000000000001", + codeName: "Ecrecover", + lang: Language.Yul, + path: "precompiles", + }, + sha256: { + address: "0x0000000000000000000000000000000000000002", + codeName: "SHA256", + lang: Language.Yul, + path: "precompiles", + }, + ecAdd: { + address: "0x0000000000000000000000000000000000000006", + codeName: "EcAdd", + lang: Language.Yul, + path: "precompiles", + }, + ecMul: { + address: "0x0000000000000000000000000000000000000007", + codeName: "EcMul", + lang: Language.Yul, + path: "precompiles", + }, + bootloader: { + // Bootloader has EmptyContract code + address: "0x0000000000000000000000000000000000008001", + codeName: "EmptyContract", + lang: Language.Solidity, + }, + accountCodeStorage: { + address: "0x0000000000000000000000000000000000008002", + codeName: "AccountCodeStorage", + lang: Language.Solidity, + }, + nonceHolder: { + address: "0x0000000000000000000000000000000000008003", + codeName: "NonceHolder", + lang: Language.Solidity, + }, + knownCodesStorage: { + address: "0x0000000000000000000000000000000000008004", + codeName: "KnownCodesStorage", + lang: Language.Solidity, + }, + immutableSimulator: { + address: "0x0000000000000000000000000000000000008005", + codeName: "ImmutableSimulator", + lang: Language.Solidity, + }, + contractDeployer: { + address: "0x0000000000000000000000000000000000008006", + codeName: "ContractDeployer", + lang: Language.Solidity, + }, + l1Messenger: { + address: "0x0000000000000000000000000000000000008008", + codeName: "L1Messenger", + lang: Language.Solidity, + }, + msgValueSimulator: { + address: "0x0000000000000000000000000000000000008009", + codeName: "MsgValueSimulator", + lang: Language.Solidity, + }, + l2EthToken: { + address: "0x000000000000000000000000000000000000800a", + codeName: "L2EthToken", + lang: Language.Solidity, + }, + systemContext: { + address: "0x000000000000000000000000000000000000800b", + codeName: "SystemContext", + lang: Language.Solidity, + }, + bootloaderUtilities: { + address: "0x000000000000000000000000000000000000800c", + codeName: "BootloaderUtilities", + lang: Language.Solidity, + }, + eventWriter: { + address: "0x000000000000000000000000000000000000800d", + codeName: "EventWriter", + lang: Language.Yul, + path: "", + }, + compressor: { + address: "0x000000000000000000000000000000000000800e", + codeName: "Compressor", + lang: Language.Solidity, + }, + complexUpgrader: { + address: "0x000000000000000000000000000000000000800f", + codeName: "ComplexUpgrader", + lang: Language.Solidity, + }, + keccak256: { + address: "0x0000000000000000000000000000000000008010", + codeName: "Keccak256", + lang: Language.Yul, + path: "precompiles", + }, +} as const; + +export const EIP712_TX_ID = 113; +export const CHAIN_ID = 270; + +// For now, these types are hardcoded, but maybe it will make sense +export const EIP712_DOMAIN = { + name: "zkSync", + version: "2", + chainId: CHAIN_ID, + // zkSync contract doesn't verify EIP712 signatures. +}; + +export interface TransactionData { + txType: BigNumberish; + from: BigNumberish; + to: BigNumberish; + gasLimit: BigNumberish; + gasPerPubdataByteLimit: BigNumberish; + gasPrice: BigNumberish; + // In the future, we might want to add some + // new fields to the struct. The `txData` struct + // is to be passed to account and any changes to its structure + // would mean a breaking change to these accounts. In order to prevent this, + // we should keep some fields as "reserved". + // It is also recommended that their length is fixed, since + // it would allow easier proof integration (in case we will need + // some special circuit for preprocessing transactions). + reserved: BigNumberish[]; + data: BytesLike; + signature: BytesLike; + // Reserved dynamic type for the future use-case. Using it should be avoided, + // But it is still here, just in case we want to enable some additional functionality. + reservedDynamic: BytesLike; +} + +export interface EIP712Tx { + txType: BigNumberish; + from: BigNumberish; + to: BigNumberish; + value: BigNumberish; + gasLimit: BigNumberish; + gasPerPubdataByteLimit: BigNumberish; + gasPrice: BigNumberish; + nonce: BigNumberish; + data: BytesLike; + signature: BytesLike; +} + +export type Address = string; + +export const EIP712_TX_TYPE = { + Transaction: [ + { name: "txType", type: "uint8" }, + { name: "to", type: "uint256" }, + { name: "value", type: "uint256" }, + { name: "data", type: "bytes" }, + { name: "gasLimit", type: "uint256" }, + { name: "gasPerPubdataByteLimit", type: "uint256" }, + { name: "gasPrice", type: "uint256" }, + { name: "nonce", type: "uint256" }, + ], +}; + +export type DynamicType = "bytes" | "bytes32[]"; +export type FixedType = "address" | "uint256" | "uint128" | "uint32"; +export type FieldType = FixedType | DynamicType; + +function isDynamicType(x: FieldType): x is DynamicType { + return x == "bytes" || x == "bytes32[]"; +} + +function isFixedType(x: FieldType): x is FixedType { + return !isDynamicType(x); +} + +export const TransactionFields: Record = { + txType: "uint256", + from: "address", + to: "address", + gasLimit: "uint32", + gasPerPubdataByteLimit: "uint32", + maxFeePerGas: "uint256", + maxPriorityFeePerGas: "uint256", + paymaster: "address", + // In the future, we might want to add some + // new fields to the struct. The `txData` struct + // is to be passed to account and any changes to its structure + // would mean a breaking change to these accounts. In order to prevent this, + // we should keep some fields as "reserved". + // It is also recommended that their length is fixed, since + // it would allow easier proof integration (in case we will need + // some special circuit for preprocessing transactions). + reserved: Array(6).fill("uint256"), + data: "bytes", + signature: "bytes", + factoryDeps: "bytes32[]", + paymasterInput: "bytes", + // Reserved dynamic type for the future use-case. Using it should be avoided, + // But it is still here, just in case we want to enable some additional functionality. + reservedDynamic: "bytes", +}; + +function capitalize(s: string) { + if (!s.length) { + return s; + } + return `${s[0].toUpperCase()}${s.substring(1)}`; +} + +function memPosFromOffset(offset: number) { + return offset === 0 ? "innerTxDataOffset" : `add(innerTxDataOffset, ${offset})`; +} + +function getGetterName(fieldName: string) { + return `get${capitalize(fieldName)}`; +} + +function getPtrGetterName(fieldName: string) { + return `get${capitalize(fieldName)}Ptr`; +} + +function getGetter(fieldName: string, offset: number) { + const getterName = getGetterName(fieldName); + const memPos = memPosFromOffset(offset); + return ` + function ${getterName}(innerTxDataOffset) -> ret { + ret := mload(${memPos}) + } + `; +} + +function getPtrGetter(fieldName: string, offset: number) { + const getterName = getPtrGetterName(fieldName); + const memPos = memPosFromOffset(offset); + return ` + function ${getterName}(innerTxDataOffset) -> ret { + ret := mload(${memPos}) + ret := add(innerTxDataOffset, ret) + } + `; +} + +function getTypeValidationMethodName(type: FieldType) { + if (type == "bytes32[]") { + return "validateBytes32Array"; + } else { + return `validate${capitalize(type)}`; + } +} + +function getBytesLengthGetterName(fieldName: string): string { + return `get${capitalize(fieldName)}BytesLength`; +} + +function getBytesLengthGetter(fieldName: string, type: DynamicType) { + let lengthToBytes: string; + if (type == "bytes") { + lengthToBytes = "lengthToWords(mload(ptr))"; + } else if (type == "bytes32[]") { + lengthToBytes = "mul(mload(ptr),32)"; + } else { + throw new Error(`Type ${type} is not supported`); + } + + const getterName = getBytesLengthGetterName(fieldName); + return ` + function ${getterName}(innerTxDataOffset) -> ret { + let ptr := ${getPtrGetterName(fieldName)}(innerTxDataOffset) + ret := ${lengthToBytes} + } + `; +} + +function getDataLength(baseLength: number, dynamicFields: [string, DynamicType][]) { + const ptrAdders = dynamicFields + .map(([fieldName]) => { + return ` + ret := add(ret, ${getBytesLengthGetterName(fieldName)}(innerTxDataOffset))`; + }) + .join(""); + + return ` + function getDataLength(innerTxDataOffset) -> ret { + // To get the length of the txData in bytes, we can simply + // get the number of fields * 32 + the length of the dynamic types + // in bytes. + ret := ${baseLength + dynamicFields.length * 32} + + ${ptrAdders} + } + `; +} + +function validateFixedSizeField(fieldName: string, type: FixedType): string { + if (type == "uint256") { + // There is no validation for uint256 + return ""; + } + const assertionErrorStr = getEncodingError(fieldName); + const fieldValue = `${fieldName}Value`; + return ` + let ${fieldValue} := ${getGetterName(fieldName)}(innerTxDataOffset) + if iszero(${getTypeValidationMethodName(type)}(${fieldValue})) { + assertionError("${assertionErrorStr}") + } + `; +} + +function getEncodingError(fieldName: string) { + // Unfortunately we have to keep this not-so-readable name + // because the maximum length is 32. + const assertionError = `Encoding ${fieldName}`; + + if (assertionError.length > 32) { + throw new Error(`Assertion str too long: ${assertionError}`); + } + + return assertionError; +} + +function getValidateTxStructure( + fixedFieldsChecks: string, + fixedLenPart: number, + dynamicFields: [string, DynamicType][] +): string { + const dynamicChecks = dynamicFields + .map(([fieldName, type]) => { + const lengthPos = `${fieldName}LengthPos`; + const assertionError = getEncodingError(fieldName); + const validationMethod = getTypeValidationMethodName(type); + + return ` + let ${lengthPos} := ${getPtrGetterName(fieldName)}(innerTxDataOffset) + if iszero(eq(${lengthPos}, expectedDynamicLenPtr)) { + assertionError("${assertionError}") + } + expectedDynamicLenPtr := ${validationMethod}(${lengthPos}) + `; + }) + .join("\n"); + + return ` + /// This method checks that the transaction's structure is correct + /// and tightly packed + function validateAbiEncoding(innerTxDataOffset) -> ret { + ${fixedFieldsChecks} + + let expectedDynamicLenPtr := add(innerTxDataOffset, ${fixedLenPart}) + ${dynamicChecks} + }`; +} + +export function getTransactionUtils(): string { + let result = `/// + /// TransactionData utilities + ///\n`; + + let innerOffsetBytes = 0; + let checksStr = ""; + + const dynamicFields: [string, DynamicType][] = []; + for (const [key, value] of Object.entries(TransactionFields)) { + if (Array.isArray(value)) { + // We assume that the + for (let i = 0; i < value.length; i++) { + const keyName = `${key}${i}`; + result += getGetter(keyName, innerOffsetBytes); + checksStr += validateFixedSizeField(keyName, value[i]); + innerOffsetBytes += 32; + } + } else if (isFixedType(value)) { + result += getGetter(key, innerOffsetBytes); + checksStr += validateFixedSizeField(key, value); + innerOffsetBytes += 32; + } else { + result += getPtrGetter(key, innerOffsetBytes); + result += getBytesLengthGetter(key, value); + dynamicFields.push([key, value]); + innerOffsetBytes += 32; + } + } + + result += getValidateTxStructure(checksStr, innerOffsetBytes, dynamicFields); + + result += getDataLength(innerOffsetBytes, dynamicFields); + + return result; +} + +export function getRevertSelector(): string { + return ethers.utils.keccak256(ethers.utils.toUtf8Bytes("Error(string)")).substring(0, 10); +} diff --git a/.test-node-subtree/etc/system-contracts/scripts/deploy-preimages.ts b/.test-node-subtree/etc/system-contracts/scripts/deploy-preimages.ts new file mode 100644 index 00000000..20cc8611 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/scripts/deploy-preimages.ts @@ -0,0 +1,305 @@ +import * as hre from "hardhat"; + +import { Deployer } from "@matterlabs/hardhat-zksync-deploy"; +import { Command } from "commander"; +import type { BigNumber } from "ethers"; +import { ethers } from "ethers"; +import { formatUnits, parseUnits } from "ethers/lib/utils"; +import * as fs from "fs"; +import * as path from "path"; +import { Provider, Wallet } from "zksync-web3"; +import { hashBytecode } from "zksync-web3/build/src/utils"; +import { Language, SYSTEM_CONTRACTS } from "./constants"; +import type { Dependency, DeployedDependency } from "./utils"; +import { filterPublishedFactoryDeps, publishFactoryDeps, readYulBytecode } from "./utils"; + +const testConfigPath = path.join(process.env.ZKSYNC_HOME as string, "etc/test_config/constant"); +const ethTestConfig = JSON.parse(fs.readFileSync(`${testConfigPath}/eth.json`, { encoding: "utf-8" })); + +// Maximum length of the combined length of dependencies +const MAX_COMBINED_LENGTH = 90000; + +const DEFAULT_ACCOUNT_CONTRACT_NAME = "DefaultAccount"; +const BOOTLOADER_CONTRACT_NAME = "Bootloader"; + +class ZkSyncDeployer { + deployer: Deployer; + gasPrice: BigNumber; + nonce: number; + dependenciesToUpgrade: DeployedDependency[]; + defaultAccountToUpgrade?: DeployedDependency; + bootloaderToUpgrade?: DeployedDependency; + constructor(deployer: Deployer, gasPrice: BigNumber, nonce: number) { + this.deployer = deployer; + this.gasPrice = gasPrice; + this.nonce = nonce; + this.dependenciesToUpgrade = []; + } + + async publishFactoryDeps(dependencies: Dependency[]) { + await publishFactoryDeps(dependencies, this.deployer, this.nonce, this.gasPrice); + this.nonce += 1; + } + + // Returns the current default account bytecode on zkSync + async currentDefaultAccountBytecode(): Promise { + const zkSync = await this.deployer.zkWallet.getMainContract(); + return await zkSync.getL2DefaultAccountBytecodeHash(); + } + + // If needed, appends the default account bytecode to the upgrade + async checkShouldUpgradeDefaultAA(defaultAccountBytecode: string) { + const bytecodeHash = ethers.utils.hexlify(hashBytecode(defaultAccountBytecode)); + const currentDefaultAccountBytecode = ethers.utils.hexlify(await this.currentDefaultAccountBytecode()); + + // If the bytecode is not the same as the one deployed on zkSync, we need to add it to the deployment + if (bytecodeHash.toLowerCase() !== currentDefaultAccountBytecode) { + this.defaultAccountToUpgrade = { + name: DEFAULT_ACCOUNT_CONTRACT_NAME, + bytecodeHashes: [bytecodeHash], + }; + } + } + + // Publish default account bytecode + async publishDefaultAA(defaultAccountBytecode: string) { + const [defaultAccountBytecodes] = await filterPublishedFactoryDeps( + DEFAULT_ACCOUNT_CONTRACT_NAME, + [defaultAccountBytecode], + this.deployer + ); + + if (defaultAccountBytecodes.length == 0) { + console.log("Default account bytecode is already published, skipping"); + return; + } + + await this.publishFactoryDeps([ + { + name: DEFAULT_ACCOUNT_CONTRACT_NAME, + bytecodes: defaultAccountBytecodes, + }, + ]); + this.nonce += 1; + } + + // Publishes the bytecode of default AA and appends it to the deployed bytecodes if needed. + async processDefaultAA() { + const defaultAccountBytecode = (await this.deployer.loadArtifact(DEFAULT_ACCOUNT_CONTRACT_NAME)).bytecode; + + await this.publishDefaultAA(defaultAccountBytecode); + await this.checkShouldUpgradeDefaultAA(defaultAccountBytecode); + } + + async currentBootloaderBytecode(): Promise { + const zkSync = await this.deployer.zkWallet.getMainContract(); + return await zkSync.getL2BootloaderBytecodeHash(); + } + + async checkShouldUpgradeBootloader(bootloaderCode: string) { + const bytecodeHash = ethers.utils.hexlify(hashBytecode(bootloaderCode)); + const currentBootloaderBytecode = ethers.utils.hexlify(await this.currentBootloaderBytecode()); + + // If the bytecode is not the same as the one deployed on zkSync, we need to add it to the deployment + if (bytecodeHash.toLowerCase() !== currentBootloaderBytecode) { + this.bootloaderToUpgrade = { + name: BOOTLOADER_CONTRACT_NAME, + bytecodeHashes: [bytecodeHash], + }; + } + } + + async publishBootloader(bootloaderCode: string) { + console.log("\nPublishing bootloader bytecode:"); + + const [deps] = await filterPublishedFactoryDeps(BOOTLOADER_CONTRACT_NAME, [bootloaderCode], this.deployer); + + if (deps.length == 0) { + console.log("Default bootloader bytecode is already published, skipping"); + return; + } + + await this.publishFactoryDeps([ + { + name: BOOTLOADER_CONTRACT_NAME, + bytecodes: deps, + }, + ]); + } + + async processBootloader() { + const bootloaderCode = ethers.utils.hexlify( + fs.readFileSync("./bootloader/build/artifacts/proved_batch.yul/proved_batch.yul.zbin") + ); + + await this.publishBootloader(bootloaderCode); + await this.checkShouldUpgradeBootloader(bootloaderCode); + } + + async shouldUpgradeSystemContract(contractAddress: string, expectedBytecodeHash: string): Promise { + // We could have also used the `getCode` method of the JSON-RPC, but in the context + // of system upgrades looking into account code storage is more robust + const currentBytecodeHash = await this.deployer.zkWallet.provider.getStorageAt( + SYSTEM_CONTRACTS.accountCodeStorage.address, + contractAddress + ); + + return expectedBytecodeHash.toLowerCase() !== currentBytecodeHash.toLowerCase(); + } + + // Returns the contracts to be published. + async prepareContractsForPublishing(): Promise { + const dependenciesToPublish: Dependency[] = []; + for (const contract of Object.values(SYSTEM_CONTRACTS)) { + const contractName = contract.codeName; + let factoryDeps: string[] = []; + if (contract.lang == Language.Solidity) { + const artifact = await this.deployer.loadArtifact(contractName); + factoryDeps = [...(await this.deployer.extractFactoryDeps(artifact)), artifact.bytecode]; + } else { + // Yul files have only one dependency + factoryDeps = [readYulBytecode(contract)]; + } + + const contractBytecodeHash = ethers.utils.hexlify(hashBytecode(factoryDeps[factoryDeps.length - 1])); + if (await this.shouldUpgradeSystemContract(contract.address, contractBytecodeHash)) { + this.dependenciesToUpgrade.push({ + name: contractName, + bytecodeHashes: [contractBytecodeHash], + address: contract.address, + }); + } + + const [bytecodesToPublish, currentLength] = await filterPublishedFactoryDeps( + contractName, + factoryDeps, + this.deployer + ); + if (bytecodesToPublish.length == 0) { + console.log(`All bytecodes for ${contractName} are already published, skipping`); + continue; + } + if (currentLength > MAX_COMBINED_LENGTH) { + throw new Error(`Can not publish dependencies of contract ${contractName}`); + } + + dependenciesToPublish.push({ + name: contractName, + bytecodes: bytecodesToPublish, + address: contract.address, + }); + } + + return dependenciesToPublish; + } + + async publishDependencies(dependenciesToPublish: Dependency[]) { + let currentLength = 0; + let currentDependencies: Dependency[] = []; + // We iterate over dependencies and try to batch the publishing of those in order to save up on gas as well as time. + for (const dependency of dependenciesToPublish) { + const dependencyLength = dependency.bytecodes.reduce((prev, dep) => prev + ethers.utils.arrayify(dep).length, 0); + if (currentLength + dependencyLength > MAX_COMBINED_LENGTH) { + await this.publishFactoryDeps(currentDependencies); + currentLength = dependencyLength; + currentDependencies = [dependency]; + } else { + currentLength += dependencyLength; + currentDependencies.push(dependency); + } + } + if (currentDependencies.length > 0) { + await this.publishFactoryDeps(currentDependencies); + } + } + + returnResult() { + return { + systemContracts: this.dependenciesToUpgrade, + defaultAA: this.defaultAccountToUpgrade, + bootloader: this.bootloaderToUpgrade, + }; + } +} + +export function l1RpcUrl() { + return process.env.ETH_CLIENT_WEB3_URL as string; +} + +export function l2RpcUrl() { + return process.env.API_WEB3_JSON_RPC_HTTP_URL as string; +} + +async function main() { + const program = new Command(); + + program.version("0.1.0").name("publish preimages").description("publish preimages for the L2 contracts"); + + program + .option("--private-key ") + .option("--gas-price ") + .option("--nonce ") + .option("--l1Rpc ") + .option("--l2Rpc ") + .option("--bootloader") + .option("--default-aa") + .option("--system-contracts") + .option("--file ") + .action(async (cmd) => { + const l1Rpc = cmd.l1Rpc ? cmd.l1Rpc : l1RpcUrl(); + const l2Rpc = cmd.l2Rpc ? cmd.l2Rpc : l2RpcUrl(); + const providerL1 = new ethers.providers.JsonRpcProvider(l1Rpc); + const providerL2 = new Provider(l2Rpc); + const wallet = cmd.privateKey + ? new Wallet(cmd.privateKey) + : Wallet.fromMnemonic(process.env.MNEMONIC ? process.env.MNEMONIC : ethTestConfig.mnemonic, "m/44'/60'/0'/0/1"); + wallet.connect(providerL2); + wallet.connectToL1(providerL1); + + // TODO(EVM-392): refactor to avoid `any` here. + // eslint-disable-next-line @typescript-eslint/no-explicit-any + const deployer = new Deployer(hre, wallet as any); + // eslint-disable-next-line @typescript-eslint/no-explicit-any + deployer.zkWallet = deployer.zkWallet.connect(providerL2 as any).connectToL1(providerL1); + deployer.ethWallet = deployer.ethWallet.connect(providerL1); + const ethWallet = deployer.ethWallet; + + console.log(`Using deployer wallet: ${ethWallet.address}`); + + const gasPrice = cmd.gasPrice ? parseUnits(cmd.gasPrice, "gwei") : await providerL1.getGasPrice(); + console.log(`Using gas price: ${formatUnits(gasPrice, "gwei")} gwei`); + + const nonce = cmd.nonce ? parseInt(cmd.nonce) : await ethWallet.getTransactionCount(); + console.log(`Using nonce: ${nonce}`); + + const zkSyncDeployer = new ZkSyncDeployer(deployer, gasPrice, nonce); + if (cmd.bootloader) { + await zkSyncDeployer.processBootloader(); + } + + if (cmd.defaultAa) { + await zkSyncDeployer.processDefaultAA(); + } + + if (cmd.systemContracts) { + const dependenciesToPublish = await zkSyncDeployer.prepareContractsForPublishing(); + await zkSyncDeployer.publishDependencies(dependenciesToPublish); + } + + const result = zkSyncDeployer.returnResult(); + console.log(JSON.stringify(result, null, 2)); + if (cmd.file) { + fs.writeFileSync(cmd.file, JSON.stringify(result, null, 2)); + } + console.log("\nPublishing factory dependencies complete!"); + }); + + await program.parseAsync(process.argv); +} + +main() + .then(() => process.exit(0)) + .catch((err) => { + console.error("Error:", err); + process.exit(1); + }); diff --git a/.test-node-subtree/etc/system-contracts/scripts/process.ts b/.test-node-subtree/etc/system-contracts/scripts/process.ts new file mode 100644 index 00000000..3c230f61 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/scripts/process.ts @@ -0,0 +1,274 @@ +import * as hre from "hardhat"; + +import { ethers } from "ethers"; +import { existsSync, mkdirSync, writeFileSync } from "fs"; +import { join } from "path"; +import { renderFile } from "template-file"; +import { utils } from "zksync-web3"; +import { SYSTEM_CONTRACTS, getRevertSelector, getTransactionUtils } from "./constants"; +import type { ForceDeployment } from "./utils"; + +/* eslint-disable @typescript-eslint/no-var-requires */ +const preprocess = require("preprocess"); +const SYSTEM_PARAMS = require("../SystemConfig.json"); +/* eslint-enable@typescript-eslint/no-var-requires */ + +const OUTPUT_DIR = "bootloader/build"; + +function path(...args: string[]): string { + return join(__dirname, ...args); +} + +function getSelector(contractName: string, method: string): string { + const artifact = hre.artifacts.readArtifactSync(contractName); + const contractInterface = new ethers.utils.Interface(artifact.abi); + + return contractInterface.getSighash(method); +} + +// Methods from ethers do zero pad from left, but we need to pad from the right +function padZeroRight(hexData: string, length: number): string { + while (hexData.length < length) { + hexData += "0"; + } + + return hexData; +} + +const PADDED_SELECTOR_LENGTH = 32 * 2 + 2; +function getPaddedSelector(contractName: string, method: string): string { + const result = getSelector(contractName, method); + + return padZeroRight(result, PADDED_SELECTOR_LENGTH); +} + +function getSystemContextExpectedHash() { + const artifact = hre.artifacts.readArtifactSync("SystemContext"); + return ethers.utils.hexlify(utils.hashBytecode(artifact.bytecode)); +} + +function upgradeSystemContextCalldata() { + // Here we need to encode the force deployment for the system context contract as well as transform + // it into writing of the calldata into the bootloader memory. + + const newHash = getSystemContextExpectedHash(); + const artifact = new ethers.utils.Interface(hre.artifacts.readArtifactSync("ContractDeployer").abi); + + const forceDeplyment: ForceDeployment = { + bytecodeHash: newHash, + newAddress: SYSTEM_CONTRACTS.systemContext.address, + callConstructor: false, + value: 0, + input: "0x", + }; + + let calldata = artifact.encodeFunctionData("forceDeployOnAddresses", [[forceDeplyment]]); + const originalLength = (calldata.length - 2) / 2; + + // Padding calldata from the right. We really need to do it, since Yul would "implicitly" pad it from the left and it + // it is not what we want. + while ((calldata.length - 2) % 64 != 0) { + calldata += "0"; + } + + // We will apply tabulation to make the compiled bootloader code more readable + const TABULATION = "\t\t\t\t\t"; + // In the first slot we need to store the calldata's length + let data = `mstore(0x00, ${originalLength})\n`; + + const slices = (calldata.length - 2) / 64; + + for (let slice = 0; slice < slices; slice++) { + const offset = slice * 32; + const sliceHex = calldata.slice(2 + offset * 2, 2 + offset * 2 + 64); + + data += `${TABULATION}mstore(${offset + 32}, 0x${sliceHex})\n`; + } + + return data; +} + +// Maybe in the future some of these params will be passed +// in a JSON file. For now, a simple object is ok here. +const params = { + MARK_BATCH_AS_REPUBLISHED_SELECTOR: getSelector("KnownCodesStorage", "markFactoryDeps"), + VALIDATE_TX_SELECTOR: getSelector("IAccount", "validateTransaction"), + EXECUTE_TX_SELECTOR: getSelector("DefaultAccount", "executeTransaction"), + RIGHT_PADDED_GET_ACCOUNT_VERSION_SELECTOR: getPaddedSelector("ContractDeployer", "extendedAccountVersion"), + RIGHT_PADDED_GET_RAW_CODE_HASH_SELECTOR: getPaddedSelector("AccountCodeStorage", "getRawCodeHash"), + PAY_FOR_TX_SELECTOR: getSelector("DefaultAccount", "payForTransaction"), + PRE_PAYMASTER_SELECTOR: getSelector("DefaultAccount", "prepareForPaymaster"), + VALIDATE_AND_PAY_PAYMASTER: getSelector("IPaymaster", "validateAndPayForPaymasterTransaction"), + // It doesn't used directly now but is important to keep the way to regenerate it when needed + TX_UTILITIES: getTransactionUtils(), + RIGHT_PADDED_POST_TRANSACTION_SELECTOR: getPaddedSelector("IPaymaster", "postTransaction"), + RIGHT_PADDED_SET_TX_ORIGIN: getPaddedSelector("SystemContext", "setTxOrigin"), + RIGHT_PADDED_SET_GAS_PRICE: getPaddedSelector("SystemContext", "setGasPrice"), + RIGHT_PADDED_INCREMENT_TX_NUMBER_IN_BLOCK_SELECTOR: getPaddedSelector("SystemContext", "incrementTxNumberInBatch"), + RIGHT_PADDED_RESET_TX_NUMBER_IN_BLOCK_SELECTOR: getPaddedSelector("SystemContext", "resetTxNumberInBatch"), + RIGHT_PADDED_SEND_L2_TO_L1_LOG_SELECTOR: getPaddedSelector("L1Messenger", "sendL2ToL1Log"), + PUBLISH_PUBDATA_SELECTOR: getSelector("L1Messenger", "publishPubdataAndClearState"), + RIGHT_PADDED_SET_NEW_BATCH_SELECTOR: getPaddedSelector("SystemContext", "setNewBatch"), + RIGHT_PADDED_OVERRIDE_BATCH_SELECTOR: getPaddedSelector("SystemContext", "unsafeOverrideBatch"), + // Error + REVERT_ERROR_SELECTOR: padZeroRight(getRevertSelector(), PADDED_SELECTOR_LENGTH), + RIGHT_PADDED_VALIDATE_NONCE_USAGE_SELECTOR: getPaddedSelector("INonceHolder", "validateNonceUsage"), + RIGHT_PADDED_MINT_ETHER_SELECTOR: getPaddedSelector("L2EthToken", "mint"), + GET_TX_HASHES_SELECTOR: getSelector("BootloaderUtilities", "getTransactionHashes"), + CREATE_SELECTOR: getSelector("ContractDeployer", "create"), + CREATE2_SELECTOR: getSelector("ContractDeployer", "create2"), + CREATE_ACCOUNT_SELECTOR: getSelector("ContractDeployer", "createAccount"), + CREATE2_ACCOUNT_SELECTOR: getSelector("ContractDeployer", "create2Account"), + PADDED_TRANSFER_FROM_TO_SELECTOR: getPaddedSelector("L2EthToken", "transferFromTo"), + SUCCESSFUL_ACCOUNT_VALIDATION_MAGIC_VALUE: getPaddedSelector("IAccount", "validateTransaction"), + SUCCESSFUL_PAYMASTER_VALIDATION_MAGIC_VALUE: getPaddedSelector("IPaymaster", "validateAndPayForPaymasterTransaction"), + PUBLISH_COMPRESSED_BYTECODE_SELECTOR: getSelector("Compressor", "publishCompressedBytecode"), + GET_MARKER_PADDED_SELECTOR: getPaddedSelector("KnownCodesStorage", "getMarker"), + RIGHT_PADDED_SET_L2_BLOCK_SELECTOR: getPaddedSelector("SystemContext", "setL2Block"), + RIGHT_PADDED_APPEND_TRANSACTION_TO_L2_BLOCK_SELECTOR: getPaddedSelector( + "SystemContext", + "appendTransactionToCurrentL2Block" + ), + RIGHT_PADDED_PUBLISH_TIMESTAMP_DATA_TO_L1_SELECTOR: getPaddedSelector("SystemContext", "publishTimestampDataToL1"), + COMPRESSED_BYTECODES_SLOTS: 32768, + ENSURE_RETURNED_MAGIC: 1, + FORBID_ZERO_GAS_PER_PUBDATA: 1, + SYSTEM_CONTEXT_EXPECTED_CODE_HASH: getSystemContextExpectedHash(), + UPGRADE_SYSTEM_CONTEXT_CALLDATA: upgradeSystemContextCalldata(), + // One of "worst case" scenarios for the number of state diffs in a batch is when 120kb of pubdata is spent + // on repeated writes, that are all zeroed out. In this case, the number of diffs is 120k / 5 = 24k. This means that they will have + // accoomdate 6528000 bytes of calldata for the uncompressed state diffs. Adding 120k on top leaves us with + // roughly 6650000 bytes needed for calldata. 207813 slots are needed to accomodate this amount of data. + // We round up to 208000 slots just in case. + // + // In theory though much more calldata could be used (if for instance 1 byte is used for enum index). It is the responsibility of the + // operator to ensure that it can form the correct calldata for the L1Messenger. + OPERATOR_PROVIDED_L1_MESSENGER_PUBDATA_SLOTS: 208000, + ...SYSTEM_PARAMS, +}; + +function extractTestFunctionNames(sourceCode: string): string[] { + // Remove single-line comments + sourceCode = sourceCode.replace(/\/\/[^\n]*/g, ""); + + // Remove multi-line comments + sourceCode = sourceCode.replace(/\/\*[\s\S]*?\*\//g, ""); + + const regexPatterns = [/function\s+(TEST\w+)/g]; + + const results: string[] = []; + for (const pattern of regexPatterns) { + let match; + while ((match = pattern.exec(sourceCode)) !== null) { + results.push(match[1]); + } + } + + return [...new Set(results)]; // Remove duplicates +} + +function createTestFramework(tests: string[]): string { + let testFramework = ` + let test_id:= mload(0) + + switch test_id + case 0 { + testing_totalTests(${tests.length}) + } + `; + + tests.forEach((value, index) => { + testFramework += ` + case ${index + 1} { + testing_start("${value}") + ${value}() + } + `; + }); + + testFramework += ` + default { + } + return (0, 0) + `; + + return testFramework; +} + +async function main() { + const bootloader = await renderFile("bootloader/bootloader.yul", params); + // The overhead is unknown for gas tests and so it should be zero to calculate it + const gasTestBootloaderTemplate = await renderFile("bootloader/bootloader.yul", { + ...params, + L2_TX_INTRINSIC_GAS: 0, + L2_TX_INTRINSIC_PUBDATA: 0, + L1_TX_INTRINSIC_L2_GAS: 0, + L1_TX_INTRINSIC_PUBDATA: 0, + FORBID_ZERO_GAS_PER_PUBDATA: 0, + }); + + const feeEstimationBootloaderTemplate = await renderFile("bootloader/bootloader.yul", { + ...params, + ENSURE_RETURNED_MAGIC: 0, + }); + + console.log("Preprocessing production bootloader"); + const provedBatchBootloader = preprocess.preprocess(bootloader, { BOOTLOADER_TYPE: "proved_batch" }); + console.log("Preprocessing playground block bootloader"); + const playgroundBatchBootloader = preprocess.preprocess(bootloader, { BOOTLOADER_TYPE: "playground_batch" }); + console.log("Preprocessing gas test bootloader"); + const gasTestBootloader = preprocess.preprocess(gasTestBootloaderTemplate, { BOOTLOADER_TYPE: "proved_batch" }); + console.log("Preprocessing fee estimation bootloader"); + const feeEstimationBootloader = preprocess.preprocess(feeEstimationBootloaderTemplate, { + BOOTLOADER_TYPE: "playground_batch", + }); + + // For impersonating block start + console.log('Preprocessing production impersonating bootloader'); + const provedBatchImpersonatingBootloader = preprocess.preprocess( + bootloader, + { BOOTLOADER_TYPE: 'proved_batch', ACCOUNT_IMPERSONATING: true } + ); + console.log('Preprocessing fee estimation impersonating bootloader'); + const feeEstimationImpersonatingBootloader = preprocess.preprocess( + bootloader, + { BOOTLOADER_TYPE: 'playground_batch', ACCOUNT_IMPERSONATING: true } + ); + // For impersonating block end + + console.log("Preprocessing bootloader tests"); + const bootloaderTests = await renderFile("bootloader/tests/bootloader/bootloader_test.yul", {}); + + const testMethods = extractTestFunctionNames(bootloaderTests); + + console.log("Found tests: " + testMethods); + + const testFramework = createTestFramework(testMethods); + + const bootloaderTestUtils = await renderFile("bootloader/tests/utils/test_utils.yul", {}); + + const bootloaderWithTests = await renderFile("bootloader/bootloader.yul", { + ...params, + CODE_START_PLACEHOLDER: "\n" + bootloaderTestUtils + "\n" + bootloaderTests + "\n" + testFramework, + }); + const provedBootloaderWithTests = preprocess.preprocess(bootloaderWithTests, { BOOTLOADER_TYPE: "proved_batch" }); + + if (!existsSync(OUTPUT_DIR)) { + mkdirSync(OUTPUT_DIR); + } + + writeFileSync(path(`../${OUTPUT_DIR}/bootloader_test.yul`), provedBootloaderWithTests); + writeFileSync(path(`../${OUTPUT_DIR}/proved_batch.yul`), provedBatchBootloader); + writeFileSync(path(`../${OUTPUT_DIR}/playground_batch.yul`), playgroundBatchBootloader); + writeFileSync(path(`../${OUTPUT_DIR}/gas_test.yul`), gasTestBootloader); + writeFileSync(path(`../${OUTPUT_DIR}/fee_estimate.yul`), feeEstimationBootloader); + + // For impersonating block start + writeFileSync(path(`../${OUTPUT_DIR}/proved_batch_impersonating.yul`), provedBatchImpersonatingBootloader); + writeFileSync(path(`../${OUTPUT_DIR}/fee_estimate_impersonating.yul`), feeEstimationImpersonatingBootloader); + // For impersonating block end + + console.log("Preprocessing done!"); +} + +main(); diff --git a/.test-node-subtree/etc/system-contracts/scripts/quick-setup.sh b/.test-node-subtree/etc/system-contracts/scripts/quick-setup.sh new file mode 100755 index 00000000..341d77d2 --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/scripts/quick-setup.sh @@ -0,0 +1,15 @@ +#!/bin/bash + +# install rust +curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh + +rustup toolchain install nightly + +# install era-test-node +cargo +nightly install --git https://github.com/matter-labs/era-test-node.git --locked --branch boojum-integration + +yarn +yarn build +era_test_node run > /dev/null 2>&1 & export TEST_NODE_PID=$! +yarn test +kill $TEST_NODE_PID diff --git a/.test-node-subtree/etc/system-contracts/scripts/utils.ts b/.test-node-subtree/etc/system-contracts/scripts/utils.ts new file mode 100644 index 00000000..8ef1dfff --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/scripts/utils.ts @@ -0,0 +1,183 @@ +import * as hre from "hardhat"; + +import type { Deployer } from "@matterlabs/hardhat-zksync-deploy"; +import type { BigNumberish, BytesLike } from "ethers"; +import { BigNumber, ethers } from "ethers"; +import * as fs from "fs"; +import { hashBytecode } from "zksync-web3/build/src/utils"; +import type { YulContractDescrption } from "./constants"; +import { Language, SYSTEM_CONTRACTS } from "./constants"; + +export interface Dependency { + name: string; + bytecodes: BytesLike[]; + address?: string; +} + +export interface DeployedDependency { + name: string; + bytecodeHashes: string[]; + address?: string; +} + +export function readYulBytecode(description: YulContractDescrption) { + const contractName = description.codeName; + const path = `contracts/${description.path}/artifacts/${contractName}.yul/${contractName}.yul.zbin`; + return ethers.utils.hexlify(fs.readFileSync(path)); +} + +// The struct used to represent the parameters of a forced deployment -- a deployment during upgrade +// which sets a bytecode onto an address. Typically used for updating system contracts. +export interface ForceDeployment { + // The bytecode hash to put on an address + bytecodeHash: BytesLike; + // The address on which to deploy the bytecodehash to + newAddress: string; + // Whether to call the constructor + callConstructor: boolean; + // The value with which to initialize a contract + value: BigNumberish; + // The constructor calldata + input: BytesLike; +} + +export async function outputSystemContracts(): Promise { + const upgradeParamsPromises: Promise[] = Object.values(SYSTEM_CONTRACTS).map( + async (systemContractInfo) => { + let bytecode: string; + + if (systemContractInfo.lang === Language.Yul) { + bytecode = readYulBytecode(systemContractInfo); + } else { + bytecode = (await hre.artifacts.readArtifact(systemContractInfo.codeName)).bytecode; + } + const bytecodeHash = hashBytecode(bytecode); + + return { + bytecodeHash: ethers.utils.hexlify(bytecodeHash), + newAddress: systemContractInfo.address, + value: "0", + input: "0x", + callConstructor: false, + }; + } + ); + + return await Promise.all(upgradeParamsPromises); +} + +// Script that publishes preimages for all the system contracts on zkSync +// and outputs the JSON that can be used for performing the necessary upgrade +const DEFAULT_L2_TX_GAS_LIMIT = 2097152; + +// For the given dependencies, returns an array of tuples (bytecodeHash, marker), where +// for each dependency the bytecodeHash is its versioned hash and marker is whether +// the hash has been published before. +export async function getMarkers(dependencies: BytesLike[], deployer: Deployer): Promise<[string, boolean][]> { + const contract = new ethers.Contract( + SYSTEM_CONTRACTS.knownCodesStorage.address, + (await hre.artifacts.readArtifact("KnownCodesStorage")).abi, + deployer.zkWallet + ); + + const promises = dependencies.map(async (dep) => { + const hash = ethers.utils.hexlify(hashBytecode(dep)); + const marker = BigNumber.from(await contract.getMarker(hash)); + + return [hash, marker.eq(1)] as [string, boolean]; + }); + + return await Promise.all(promises); +} + +// Checks whether the marker has been set correctly in the KnownCodesStorage +// system contract +export async function checkMarkers(dependencies: BytesLike[], deployer: Deployer) { + const markers = await getMarkers(dependencies, deployer); + + for (const [bytecodeHash, marker] of markers) { + if (!marker) { + throw new Error(`Failed to mark ${bytecodeHash}`); + } + } +} + +export function totalBytesLength(dependencies: BytesLike[]): number { + return dependencies.reduce((prev, curr) => prev + ethers.utils.arrayify(curr).length, 0); +} + +export function getBytecodes(dependencies: Dependency[]): BytesLike[] { + return dependencies.map((dep) => dep.bytecodes).flat(); +} + +export async function publishFactoryDeps( + dependencies: Dependency[], + deployer: Deployer, + nonce: number, + gasPrice: BigNumber +) { + if (dependencies.length == 0) { + return []; + } + const bytecodes = getBytecodes(dependencies); + const combinedLength = totalBytesLength(bytecodes); + + console.log( + `\nPublishing dependencies for contracts ${dependencies + .map((dep) => { + return dep.name; + }) + .join(", ")}` + ); + console.log(`Combined length ${combinedLength}`); + + const txHandle = await deployer.zkWallet.requestExecute({ + contractAddress: ethers.constants.AddressZero, + calldata: "0x", + l2GasLimit: DEFAULT_L2_TX_GAS_LIMIT, + factoryDeps: bytecodes, + overrides: { + nonce, + gasPrice, + gasLimit: 3000000, + }, + }); + console.log(`Transaction hash: ${txHandle.hash}`); + + // Waiting for the transaction to be processed by the server + await txHandle.wait(); + + console.log("Transaction complete! Checking markers on L2..."); + + // Double checking that indeed the dependencies have been marked as known + await checkMarkers(bytecodes, deployer); +} + +// Returns an array of bytecodes that should be published along with their total length in bytes +export async function filterPublishedFactoryDeps( + contractName: string, + factoryDeps: string[], + deployer: Deployer +): Promise<[string[], number]> { + console.log(`\nFactory dependencies for contract ${contractName}:`); + let currentLength = 0; + + const bytecodesToDeploy: string[] = []; + + const hashesAndMarkers = await getMarkers(factoryDeps, deployer); + + for (let i = 0; i < factoryDeps.length; i++) { + const depLength = ethers.utils.arrayify(factoryDeps[i]).length; + const [hash, marker] = hashesAndMarkers[i]; + console.log(`${hash} (length: ${depLength} bytes) (deployed: ${marker})`); + + if (!marker) { + currentLength += depLength; + bytecodesToDeploy.push(factoryDeps[i]); + } + } + + console.log(`Combined length to deploy: ${currentLength}`); + + return [bytecodesToDeploy, currentLength]; +} diff --git a/.test-node-subtree/etc/system-contracts/yarn.lock b/.test-node-subtree/etc/system-contracts/yarn.lock new file mode 100644 index 00000000..166747de --- /dev/null +++ b/.test-node-subtree/etc/system-contracts/yarn.lock @@ -0,0 +1,5353 @@ +# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. +# yarn lockfile v1 + + +"@aashutoshrathi/word-wrap@^1.2.3": + version "1.2.6" + resolved "https://registry.yarnpkg.com/@aashutoshrathi/word-wrap/-/word-wrap-1.2.6.tgz#bd9154aec9983f77b3a034ecaa015c2e4201f6cf" + integrity sha512-1Yjs2SvM8TflER/OD3cOjhWWOZb58A2t7wpE2S9XfBYTiIl+XFhQG2bjy4Pu1I+EAlCNUzRDYDdFwFYUKvXcIA== + +"@babel/code-frame@^7.0.0": + version "7.22.13" + resolved "https://registry.yarnpkg.com/@babel/code-frame/-/code-frame-7.22.13.tgz#e3c1c099402598483b7a8c46a721d1038803755e" + integrity sha512-XktuhWlJ5g+3TJXc5upd9Ks1HutSArik6jf2eAjYFyIOf4ej3RN+184cZbzDvbPnuTJIUhPKKJE3cIsYTiAT3w== + dependencies: + "@babel/highlight" "^7.22.13" + chalk "^2.4.2" + +"@babel/helper-validator-identifier@^7.22.20": + version "7.22.20" + resolved "https://registry.yarnpkg.com/@babel/helper-validator-identifier/-/helper-validator-identifier-7.22.20.tgz#c4ae002c61d2879e724581d96665583dbc1dc0e0" + integrity sha512-Y4OZ+ytlatR8AI+8KZfKuL5urKp7qey08ha31L8b3BwewJAoJamTzyvxPR/5D+KkdJCGPq/+8TukHBlY10FX9A== + +"@babel/highlight@^7.22.13": + version "7.22.20" + resolved "https://registry.yarnpkg.com/@babel/highlight/-/highlight-7.22.20.tgz#4ca92b71d80554b01427815e06f2df965b9c1f54" + integrity sha512-dkdMCN3py0+ksCgYmGG8jKeGA/8Tk+gJwSYYlFGxG5lmhfKNoAy004YpLxpS1W2J8m/EK2Ew+yOs9pVRwO89mg== + dependencies: + "@babel/helper-validator-identifier" "^7.22.20" + chalk "^2.4.2" + js-tokens "^4.0.0" + +"@balena/dockerignore@^1.0.2": + version "1.0.2" + resolved "https://registry.yarnpkg.com/@balena/dockerignore/-/dockerignore-1.0.2.tgz#9ffe4726915251e8eb69f44ef3547e0da2c03e0d" + integrity sha512-wMue2Sy4GAVTk6Ic4tJVcnfdau+gx2EnG7S+uAEe+TWJFqE4YoWN4/H8MSLj4eYJKxGg26lZwboEniNiNwZQ6Q== + +"@blakek/curry@^2.0.2": + version "2.0.2" + resolved "https://registry.yarnpkg.com/@blakek/curry/-/curry-2.0.2.tgz#979e927bcf5fa0426d2af681d7131df5791d1cd4" + integrity sha512-B/KkDnZqm9Y92LwETU80BaxbQ61bYTR2GaAY41mKisaICwBoC8lcuw7lwQLl52InMhviCTJBO39GJOA8d+BrVw== + +"@blakek/deep@^2.2.0": + version "2.2.0" + resolved "https://registry.yarnpkg.com/@blakek/deep/-/deep-2.2.0.tgz#eb97488e4a0943df4da09ad50efba4a98789f5e5" + integrity sha512-aRq/qF1yrlhCWNk2tI4epXNpo+cA8/MrxsR5oIkpKKNYtYOQKjAxRMbgnhASPx+b328MkDN+T706yFKJg8VZkQ== + dependencies: + "@blakek/curry" "^2.0.2" + pathington "^1.1.7" + +"@chainsafe/as-sha256@^0.3.1": + version "0.3.1" + resolved "https://registry.yarnpkg.com/@chainsafe/as-sha256/-/as-sha256-0.3.1.tgz#3639df0e1435cab03f4d9870cc3ac079e57a6fc9" + integrity sha512-hldFFYuf49ed7DAakWVXSJODuq3pzJEguD8tQ7h+sGkM18vja+OFoJI9krnGmgzyuZC2ETX0NOIcCTy31v2Mtg== + +"@chainsafe/persistent-merkle-tree@^0.4.2": + version "0.4.2" + resolved "https://registry.yarnpkg.com/@chainsafe/persistent-merkle-tree/-/persistent-merkle-tree-0.4.2.tgz#4c9ee80cc57cd3be7208d98c40014ad38f36f7ff" + integrity sha512-lLO3ihKPngXLTus/L7WHKaw9PnNJWizlOF1H9NNzHP6Xvh82vzg9F2bzkXhYIFshMZ2gTCEz8tq6STe7r5NDfQ== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + +"@chainsafe/persistent-merkle-tree@^0.5.0": + version "0.5.0" + resolved "https://registry.yarnpkg.com/@chainsafe/persistent-merkle-tree/-/persistent-merkle-tree-0.5.0.tgz#2b4a62c9489a5739dedd197250d8d2f5427e9f63" + integrity sha512-l0V1b5clxA3iwQLXP40zYjyZYospQLZXzBVIhhr9kDg/1qHZfzzHw0jj4VPBijfYCArZDlPkRi1wZaV2POKeuw== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + +"@chainsafe/ssz@^0.10.0": + version "0.10.2" + resolved "https://registry.yarnpkg.com/@chainsafe/ssz/-/ssz-0.10.2.tgz#c782929e1bb25fec66ba72e75934b31fd087579e" + integrity sha512-/NL3Lh8K+0q7A3LsiFq09YXS9fPE+ead2rr7vM2QK8PLzrNsw3uqrif9bpRX5UxgeRjM+vYi+boCM3+GM4ovXg== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + "@chainsafe/persistent-merkle-tree" "^0.5.0" + +"@chainsafe/ssz@^0.9.2": + version "0.9.4" + resolved "https://registry.yarnpkg.com/@chainsafe/ssz/-/ssz-0.9.4.tgz#696a8db46d6975b600f8309ad3a12f7c0e310497" + integrity sha512-77Qtg2N1ayqs4Bg/wvnWfg5Bta7iy7IRh8XqXh7oNMeP2HBbBwx8m6yTpA8p0EHItWPEBkgZd5S5/LSlp3GXuQ== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + "@chainsafe/persistent-merkle-tree" "^0.4.2" + case "^1.6.3" + +"@cspotcode/source-map-support@^0.8.0": + version "0.8.1" + resolved "https://registry.yarnpkg.com/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz#00629c35a688e05a88b1cda684fb9d5e73f000a1" + integrity sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw== + dependencies: + "@jridgewell/trace-mapping" "0.3.9" + +"@eslint-community/eslint-utils@^4.2.0", "@eslint-community/eslint-utils@^4.4.0": + version "4.4.0" + resolved "https://registry.yarnpkg.com/@eslint-community/eslint-utils/-/eslint-utils-4.4.0.tgz#a23514e8fb9af1269d5f7788aa556798d61c6b59" + integrity sha512-1/sA4dwrzBAyeUoQ6oxahHKmrZvsnLCg4RfxW3ZFGGmQkSNQPFNLV9CUEFQP1x9EYXHTo5p6xdhZM1Ne9p/AfA== + dependencies: + eslint-visitor-keys "^3.3.0" + +"@eslint-community/regexpp@^4.5.1", "@eslint-community/regexpp@^4.6.1": + version "4.10.0" + resolved "https://registry.yarnpkg.com/@eslint-community/regexpp/-/regexpp-4.10.0.tgz#548f6de556857c8bb73bbee70c35dc82a2e74d63" + integrity sha512-Cu96Sd2By9mCNTx2iyKOmq10v22jUVQv0lQnlGNy16oE9589yE+QADPbrMGCkA51cKZSg3Pu/aTJVTGfL/qjUA== + +"@eslint/eslintrc@^2.1.2": + version "2.1.2" + resolved "https://registry.yarnpkg.com/@eslint/eslintrc/-/eslintrc-2.1.2.tgz#c6936b4b328c64496692f76944e755738be62396" + integrity sha512-+wvgpDsrB1YqAMdEUCcnTlpfVBH7Vqn6A/NT3D8WVXFIaKMlErPIZT3oCIAVCOtarRpMtelZLqJeU3t7WY6X6g== + dependencies: + ajv "^6.12.4" + debug "^4.3.2" + espree "^9.6.0" + globals "^13.19.0" + ignore "^5.2.0" + import-fresh "^3.2.1" + js-yaml "^4.1.0" + minimatch "^3.1.2" + strip-json-comments "^3.1.1" + +"@eslint/js@8.52.0": + version "8.52.0" + resolved "https://registry.yarnpkg.com/@eslint/js/-/js-8.52.0.tgz#78fe5f117840f69dc4a353adf9b9cd926353378c" + integrity sha512-mjZVbpaeMZludF2fsWLD0Z9gCref1Tk4i9+wddjRvpUNqqcndPkBD09N/Mapey0b3jaXbLm2kICwFv2E64QinA== + +"@ethersproject/abi@5.7.0", "@ethersproject/abi@^5.1.2", "@ethersproject/abi@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abi/-/abi-5.7.0.tgz#b3f3e045bbbeed1af3947335c247ad625a44e449" + integrity sha512-351ktp42TiRcYB3H1OP8yajPeAQstMW/yCFokj/AthP9bLHzQFPlOrxOcwYEDkUAICmOHljvN4K39OMTMUa9RA== + dependencies: + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/abstract-provider@5.7.0", "@ethersproject/abstract-provider@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abstract-provider/-/abstract-provider-5.7.0.tgz#b0a8550f88b6bf9d51f90e4795d48294630cb9ef" + integrity sha512-R41c9UkchKCpAqStMYUpdunjo3pkEvZC3FAwZn5S5MGbXoMQOHIdHItezTETxAO5bevtMApSyEhn9+CHcDsWBw== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/networks" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/web" "^5.7.0" + +"@ethersproject/abstract-signer@5.7.0", "@ethersproject/abstract-signer@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abstract-signer/-/abstract-signer-5.7.0.tgz#13f4f32117868452191a4649723cb086d2b596b2" + integrity sha512-a16V8bq1/Cz+TGCkE2OPMTOUDLS3grCpdjoJCYNnVBbdYEMSgKrU0+B90s8b6H+ByYTBZN7a3g76jdIJi7UfKQ== + dependencies: + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + +"@ethersproject/address@5.7.0", "@ethersproject/address@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/address/-/address-5.7.0.tgz#19b56c4d74a3b0a46bfdbb6cfcc0a153fc697f37" + integrity sha512-9wYhYt7aghVGo758POM5nqcOMaE168Q6aRLJZwUmiqSrAungkG74gSSeKEIR7ukixesdRZGPgVqme6vmxs1fkA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + +"@ethersproject/base64@5.7.0", "@ethersproject/base64@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/base64/-/base64-5.7.0.tgz#ac4ee92aa36c1628173e221d0d01f53692059e1c" + integrity sha512-Dr8tcHt2mEbsZr/mwTPIQAf3Ai0Bks/7gTw9dSqk1mQvhW3XvRlmDJr/4n+wg1JmCl16NZue17CDh8xb/vZ0sQ== + dependencies: + "@ethersproject/bytes" "^5.7.0" + +"@ethersproject/basex@5.7.0", "@ethersproject/basex@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/basex/-/basex-5.7.0.tgz#97034dc7e8938a8ca943ab20f8a5e492ece4020b" + integrity sha512-ywlh43GwZLv2Voc2gQVTKBoVQ1mti3d8HK5aMxsfu/nRDnMmNqaSJ3r3n85HBByT8OpoY96SXM1FogC533T4zw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + +"@ethersproject/bignumber@5.7.0", "@ethersproject/bignumber@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/bignumber/-/bignumber-5.7.0.tgz#e2f03837f268ba655ffba03a57853e18a18dc9c2" + integrity sha512-n1CAdIHRWjSucQO3MC1zPSVgV/6dy/fjL9pMrPP9peL+QxEg9wOsVqwD4+818B6LUEtaXzVHQiuivzRoxPxUGw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + bn.js "^5.2.1" + +"@ethersproject/bytes@5.7.0", "@ethersproject/bytes@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/bytes/-/bytes-5.7.0.tgz#a00f6ea8d7e7534d6d87f47188af1148d71f155d" + integrity sha512-nsbxwgFXWh9NyYWo+U8atvmMsSdKJprTcICAkvbBffT75qDocbuggBU0SJiVK2MuTrp0q+xvLkTnGMPK1+uA9A== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/constants@5.7.0", "@ethersproject/constants@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/constants/-/constants-5.7.0.tgz#df80a9705a7e08984161f09014ea012d1c75295e" + integrity sha512-DHI+y5dBNvkpYUMiRQyxRBYBefZkJfo70VUkUAsRjcPs47muV9evftfZ0PJVCXYbAiCgght0DtcF9srFQmIgWA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + +"@ethersproject/contracts@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/contracts/-/contracts-5.7.0.tgz#c305e775abd07e48aa590e1a877ed5c316f8bd1e" + integrity sha512-5GJbzEU3X+d33CdfPhcyS+z8MzsTrBGk/sc+G+59+tPa9yFkl6HQ9D6L0QMgNTA9q8dT0XKxxkyp883XsQvbbg== + dependencies: + "@ethersproject/abi" "^5.7.0" + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + +"@ethersproject/hash@5.7.0", "@ethersproject/hash@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/hash/-/hash-5.7.0.tgz#eb7aca84a588508369562e16e514b539ba5240a7" + integrity sha512-qX5WrQfnah1EFnO5zJv1v46a8HW0+E5xuBBDTwMFZLuVTx0tbU2kkx15NqdjxecrLGatQN9FGQKpb1FKdHCt+g== + dependencies: + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/base64" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/hdnode@5.7.0", "@ethersproject/hdnode@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/hdnode/-/hdnode-5.7.0.tgz#e627ddc6b466bc77aebf1a6b9e47405ca5aef9cf" + integrity sha512-OmyYo9EENBPPf4ERhR7oj6uAtUAhYGqOnIS+jE5pTXvdKBS99ikzq1E7Iv0ZQZ5V36Lqx1qZLeak0Ra16qpeOg== + dependencies: + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/basex" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/pbkdf2" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + "@ethersproject/signing-key" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/wordlists" "^5.7.0" + +"@ethersproject/json-wallets@5.7.0", "@ethersproject/json-wallets@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/json-wallets/-/json-wallets-5.7.0.tgz#5e3355287b548c32b368d91014919ebebddd5360" + integrity sha512-8oee5Xgu6+RKgJTkvEMl2wDgSPSAQ9MB/3JYjFV9jlKvcYHUXZC+cQp0njgmxdHkYWn8s6/IqIZYm0YWCjO/0g== + dependencies: + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/hdnode" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/pbkdf2" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/random" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + aes-js "3.0.0" + scrypt-js "3.0.1" + +"@ethersproject/keccak256@5.7.0", "@ethersproject/keccak256@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/keccak256/-/keccak256-5.7.0.tgz#3186350c6e1cd6aba7940384ec7d6d9db01f335a" + integrity sha512-2UcPboeL/iW+pSg6vZ6ydF8tCnv3Iu/8tUmLLzWWGzxWKFFqOBQFLo6uLUv6BDrLgCDfN28RJ/wtByx+jZ4KBg== + dependencies: + "@ethersproject/bytes" "^5.7.0" + js-sha3 "0.8.0" + +"@ethersproject/logger@5.7.0", "@ethersproject/logger@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/logger/-/logger-5.7.0.tgz#6ce9ae168e74fecf287be17062b590852c311892" + integrity sha512-0odtFdXu/XHtjQXJYA3u9G0G8btm0ND5Cu8M7i5vhEcE8/HmF4Lbdqanwyv4uQTr2tx6b7fQRmgLrsnpQlmnig== + +"@ethersproject/networks@5.7.1", "@ethersproject/networks@^5.7.0": + version "5.7.1" + resolved "https://registry.yarnpkg.com/@ethersproject/networks/-/networks-5.7.1.tgz#118e1a981d757d45ccea6bb58d9fd3d9db14ead6" + integrity sha512-n/MufjFYv3yFcUyfhnXotyDlNdFb7onmkSy8aQERi2PjNcnWQ66xXxa3XlS8nCcA8aJKJjIIMNJTC7tu80GwpQ== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/pbkdf2@5.7.0", "@ethersproject/pbkdf2@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/pbkdf2/-/pbkdf2-5.7.0.tgz#d2267d0a1f6e123f3771007338c47cccd83d3102" + integrity sha512-oR/dBRZR6GTyaofd86DehG72hY6NpAjhabkhxgr3X2FpJtJuodEl2auADWBZfhDHgVCbu3/H/Ocq2uC6dpNjjw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + +"@ethersproject/properties@5.7.0", "@ethersproject/properties@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/properties/-/properties-5.7.0.tgz#a6e12cb0439b878aaf470f1902a176033067ed30" + integrity sha512-J87jy8suntrAkIZtecpxEPxY//szqr1mlBaYlQ0r4RCaiD2hjheqF9s1LVE8vVuJCXisjIP+JgtK/Do54ej4Sw== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/providers@5.7.2", "@ethersproject/providers@^5.7.1", "@ethersproject/providers@^5.7.2": + version "5.7.2" + resolved "https://registry.yarnpkg.com/@ethersproject/providers/-/providers-5.7.2.tgz#f8b1a4f275d7ce58cf0a2eec222269a08beb18cb" + integrity sha512-g34EWZ1WWAVgr4aptGlVBF8mhl3VWjv+8hoAnzStu8Ah22VHBsuGzP17eb6xDVRzw895G4W7vvx60lFFur/1Rg== + dependencies: + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/base64" "^5.7.0" + "@ethersproject/basex" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/networks" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/random" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/web" "^5.7.0" + bech32 "1.1.4" + ws "7.4.6" + +"@ethersproject/random@5.7.0", "@ethersproject/random@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/random/-/random-5.7.0.tgz#af19dcbc2484aae078bb03656ec05df66253280c" + integrity sha512-19WjScqRA8IIeWclFme75VMXSBvi4e6InrUNuaR4s5pTF2qNhcGdCUwdxUVGtDDqC00sDLCO93jPQoDUH4HVmQ== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/rlp@5.7.0", "@ethersproject/rlp@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/rlp/-/rlp-5.7.0.tgz#de39e4d5918b9d74d46de93af80b7685a9c21304" + integrity sha512-rBxzX2vK8mVF7b0Tol44t5Tb8gomOHkj5guL+HhzQ1yBh/ydjGnpw6at+X6Iw0Kp3OzzzkcKp8N9r0W4kYSs9w== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/sha2@5.7.0", "@ethersproject/sha2@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/sha2/-/sha2-5.7.0.tgz#9a5f7a7824ef784f7f7680984e593a800480c9fb" + integrity sha512-gKlH42riwb3KYp0reLsFTokByAKoJdgFCwI+CCiX/k+Jm2mbNs6oOaCjYQSlI1+XBVejwH2KrmCbMAT/GnRDQw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + hash.js "1.1.7" + +"@ethersproject/signing-key@5.7.0", "@ethersproject/signing-key@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/signing-key/-/signing-key-5.7.0.tgz#06b2df39411b00bc57c7c09b01d1e41cf1b16ab3" + integrity sha512-MZdy2nL3wO0u7gkB4nA/pEf8lu1TlFswPNmy8AiYkfKTdO6eXBJyUdmHO/ehm/htHw9K/qF8ujnTyUAD+Ry54Q== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + bn.js "^5.2.1" + elliptic "6.5.4" + hash.js "1.1.7" + +"@ethersproject/solidity@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/solidity/-/solidity-5.7.0.tgz#5e9c911d8a2acce2a5ebb48a5e2e0af20b631cb8" + integrity sha512-HmabMd2Dt/raavyaGukF4XxizWKhKQ24DoLtdNbBmNKUOPqwjsKQSdV9GQtj9CBEea9DlzETlVER1gYeXXBGaA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/strings@5.7.0", "@ethersproject/strings@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/strings/-/strings-5.7.0.tgz#54c9d2a7c57ae8f1205c88a9d3a56471e14d5ed2" + integrity sha512-/9nu+lj0YswRNSH0NXYqrh8775XNyEdUQAuf3f+SmOrnVewcJ5SBNAjF7lpgehKi4abvNNXyf+HX86czCdJ8Mg== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/transactions@5.7.0", "@ethersproject/transactions@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/transactions/-/transactions-5.7.0.tgz#91318fc24063e057885a6af13fdb703e1f993d3b" + integrity sha512-kmcNicCp1lp8qanMTC3RIikGgoJ80ztTyvtsFvCYpSCfkjhD0jZ2LOrnbcuxuToLIUYYf+4XwD1rP+B/erDIhQ== + dependencies: + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + "@ethersproject/signing-key" "^5.7.0" + +"@ethersproject/units@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/units/-/units-5.7.0.tgz#637b563d7e14f42deeee39245275d477aae1d8b1" + integrity sha512-pD3xLMy3SJu9kG5xDGI7+xhTEmGXlEqXU4OfNapmfnxLVY4EMSSRp7j1k7eezutBPH7RBN/7QPnwR7hzNlEFeg== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/wallet@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/wallet/-/wallet-5.7.0.tgz#4e5d0790d96fe21d61d38fb40324e6c7ef350b2d" + integrity sha512-MhmXlJXEJFBFVKrDLB4ZdDzxcBxQ3rLyCkhNqVu3CDYvR97E+8r01UgrI+TI99Le+aYm/in/0vp86guJuM7FCA== + dependencies: + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/hdnode" "^5.7.0" + "@ethersproject/json-wallets" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/random" "^5.7.0" + "@ethersproject/signing-key" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/wordlists" "^5.7.0" + +"@ethersproject/web@5.7.1", "@ethersproject/web@^5.7.0": + version "5.7.1" + resolved "https://registry.yarnpkg.com/@ethersproject/web/-/web-5.7.1.tgz#de1f285b373149bee5928f4eb7bcb87ee5fbb4ae" + integrity sha512-Gueu8lSvyjBWL4cYsWsjh6MtMwM0+H4HvqFPZfB6dV8ctbP9zFAO73VG1cMWae0FLPCtz0peKPpZY8/ugJJX2w== + dependencies: + "@ethersproject/base64" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/wordlists@5.7.0", "@ethersproject/wordlists@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/wordlists/-/wordlists-5.7.0.tgz#8fb2c07185d68c3e09eb3bfd6e779ba2774627f5" + integrity sha512-S2TFNJNfHWVHNE6cNDjbVlZ6MgE17MIxMbMg2zv3wn+3XSJGosL1m9ZVv3GXCf/2ymSsQ+hRI5IzoMJTG6aoVA== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@fastify/busboy@^2.0.0": + version "2.0.0" + resolved "https://registry.yarnpkg.com/@fastify/busboy/-/busboy-2.0.0.tgz#f22824caff3ae506b18207bad4126dbc6ccdb6b8" + integrity sha512-JUFJad5lv7jxj926GPgymrWQxxjPYuJNiNjNMzqT+HiuP6Vl3dk5xzG+8sTX96np0ZAluvaMzPsjhHZ5rNuNQQ== + +"@humanwhocodes/config-array@^0.11.13": + version "0.11.13" + resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.13.tgz#075dc9684f40a531d9b26b0822153c1e832ee297" + integrity sha512-JSBDMiDKSzQVngfRjOdFXgFfklaXI4K9nLF49Auh21lmBWRLIK3+xTErTWD4KU54pb6coM6ESE7Awz/FNU3zgQ== + dependencies: + "@humanwhocodes/object-schema" "^2.0.1" + debug "^4.1.1" + minimatch "^3.0.5" + +"@humanwhocodes/module-importer@^1.0.1": + version "1.0.1" + resolved "https://registry.yarnpkg.com/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz#af5b2691a22b44be847b0ca81641c5fb6ad0172c" + integrity sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA== + +"@humanwhocodes/object-schema@^2.0.1": + version "2.0.1" + resolved "https://registry.yarnpkg.com/@humanwhocodes/object-schema/-/object-schema-2.0.1.tgz#e5211452df060fa8522b55c7b3c0c4d1981cb044" + integrity sha512-dvuCeX5fC9dXgJn9t+X5atfmgQAzUOWqS1254Gh0m6i8wKd10ebXkfNKiRK+1GWi/yTvvLDHpoxLr0xxxeslWw== + +"@jridgewell/resolve-uri@^3.0.3": + version "3.1.1" + resolved "https://registry.yarnpkg.com/@jridgewell/resolve-uri/-/resolve-uri-3.1.1.tgz#c08679063f279615a3326583ba3a90d1d82cc721" + integrity sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA== + +"@jridgewell/sourcemap-codec@^1.4.10": + version "1.4.15" + resolved "https://registry.yarnpkg.com/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz#d7c6e6755c78567a951e04ab52ef0fd26de59f32" + integrity sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg== + +"@jridgewell/trace-mapping@0.3.9": + version "0.3.9" + resolved "https://registry.yarnpkg.com/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz#6534fd5933a53ba7cbf3a17615e273a0d1273ff9" + integrity sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ== + dependencies: + "@jridgewell/resolve-uri" "^3.0.3" + "@jridgewell/sourcemap-codec" "^1.4.10" + +"@matterlabs/eslint-config-typescript@^1.1.2": + version "1.1.2" + resolved "https://registry.yarnpkg.com/@matterlabs/eslint-config-typescript/-/eslint-config-typescript-1.1.2.tgz#a9be4e56aedf298800f247c5049fc412f8b301a7" + integrity sha512-AhiWJQr+MSE3RVfgp5XwGoMK7kNSKh6a18+T7hkNJtyycP0306I6IGmuFA5ZVbcakGb+K32fQWzepSkrNCTAGg== + +"@matterlabs/hardhat-zksync-chai-matchers@^0.1.4": + version "0.1.4" + resolved "https://registry.yarnpkg.com/@matterlabs/hardhat-zksync-chai-matchers/-/hardhat-zksync-chai-matchers-0.1.4.tgz#105cb0ec1367c8fcd3ce7e3773f747c71fff675b" + integrity sha512-eGQWiImg51fmayoQ7smIK/T6QZkSu38PK7xjp1RIrewGzw2ZgqFWGp40jb5oomkf8yOQPk52Hu4TwE3Ntp8CtA== + +"@matterlabs/hardhat-zksync-deploy@^0.6.5": + version "0.6.5" + resolved "https://registry.yarnpkg.com/@matterlabs/hardhat-zksync-deploy/-/hardhat-zksync-deploy-0.6.5.tgz#fe56bf30850e71c8d328ac1a06a100c1a0af6e3e" + integrity sha512-EZpvn8pDslfO3UA2obT8FOi5jsHhxYS5ndIR7tjL2zXKbvkbpoJR5rgKoGTJJm0riaCud674sQcxMOybVQ+2gg== + dependencies: + "@matterlabs/hardhat-zksync-solc" "0.4.2" + chalk "4.1.2" + ts-morph "^19.0.0" + +"@matterlabs/hardhat-zksync-solc@0.4.2", "@matterlabs/hardhat-zksync-solc@^0.4.2": + version "0.4.2" + resolved "https://registry.yarnpkg.com/@matterlabs/hardhat-zksync-solc/-/hardhat-zksync-solc-0.4.2.tgz#64121082e88c5ab22eb4e9594d120e504f6af499" + integrity sha512-6NFWPSZiOAoo7wNuhMg4ztj7mMEH+tLrx09WuCbcURrHPijj/KxYNsJD6Uw5lapKr7G8H7SQISGid1/MTXVmXQ== + dependencies: + "@nomiclabs/hardhat-docker" "^2.0.0" + chalk "4.1.2" + dockerode "^3.3.4" + fs-extra "^11.1.1" + proper-lockfile "^4.1.2" + semver "^7.5.1" + +"@matterlabs/prettier-config@^1.0.3": + version "1.0.3" + resolved "https://registry.yarnpkg.com/@matterlabs/prettier-config/-/prettier-config-1.0.3.tgz#3e2eb559c0112bbe9671895f935700dad2a15d38" + integrity sha512-JW7nHREPqEtjBWz3EfxLarkmJBD8vi7Kx/1AQ6eBZnz12eHc1VkOyrc6mpR5ogTf0dOUNXFAfZut+cDe2dn4kQ== + +"@metamask/eth-sig-util@^4.0.0": + version "4.0.1" + resolved "https://registry.yarnpkg.com/@metamask/eth-sig-util/-/eth-sig-util-4.0.1.tgz#3ad61f6ea9ad73ba5b19db780d40d9aae5157088" + integrity sha512-tghyZKLHZjcdlDqCA3gNZmLeR0XvOE9U1qoQO9ohyAZT6Pya+H9vkBPcsyXytmYLNgVoin7CKCmweo/R43V+tQ== + dependencies: + ethereumjs-abi "^0.6.8" + ethereumjs-util "^6.2.1" + ethjs-util "^0.1.6" + tweetnacl "^1.0.3" + tweetnacl-util "^0.15.1" + +"@noble/hashes@1.2.0", "@noble/hashes@~1.2.0": + version "1.2.0" + resolved "https://registry.yarnpkg.com/@noble/hashes/-/hashes-1.2.0.tgz#a3150eeb09cc7ab207ebf6d7b9ad311a9bdbed12" + integrity sha512-FZfhjEDbT5GRswV3C6uvLPHMiVD6lQBmpoX5+eSiPaMTXte/IKqI5dykDxzZB/WBeK/CDuQRBWarPdi3FNY2zQ== + +"@noble/secp256k1@1.7.1", "@noble/secp256k1@~1.7.0": + version "1.7.1" + resolved "https://registry.yarnpkg.com/@noble/secp256k1/-/secp256k1-1.7.1.tgz#b251c70f824ce3ca7f8dc3df08d58f005cc0507c" + integrity sha512-hOUk6AyBFmqVrv7k5WAw/LpszxVbj9gGN4JRkIX52fdFAj1UA61KXmZDvqVEm+pOyec3+fIeZB02LYa/pWOArw== + +"@nodelib/fs.scandir@2.1.5": + version "2.1.5" + resolved "https://registry.yarnpkg.com/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz#7619c2eb21b25483f6d167548b4cfd5a7488c3d5" + integrity sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g== + dependencies: + "@nodelib/fs.stat" "2.0.5" + run-parallel "^1.1.9" + +"@nodelib/fs.stat@2.0.5", "@nodelib/fs.stat@^2.0.2": + version "2.0.5" + resolved "https://registry.yarnpkg.com/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz#5bd262af94e9d25bd1e71b05deed44876a222e8b" + integrity sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A== + +"@nodelib/fs.walk@^1.2.3", "@nodelib/fs.walk@^1.2.8": + version "1.2.8" + resolved "https://registry.yarnpkg.com/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz#e95737e8bb6746ddedf69c556953494f196fe69a" + integrity sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg== + dependencies: + "@nodelib/fs.scandir" "2.1.5" + fastq "^1.6.0" + +"@nomicfoundation/ethereumjs-block@5.0.1": + version "5.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-block/-/ethereumjs-block-5.0.1.tgz#6f89664f55febbd723195b6d0974773d29ee133d" + integrity sha512-u1Yioemi6Ckj3xspygu/SfFvm8vZEO8/Yx5a1QLzi6nVU0jz3Pg2OmHKJ5w+D9Ogk1vhwRiqEBAqcb0GVhCyHw== + dependencies: + "@nomicfoundation/ethereumjs-common" "4.0.1" + "@nomicfoundation/ethereumjs-rlp" "5.0.1" + "@nomicfoundation/ethereumjs-trie" "6.0.1" + "@nomicfoundation/ethereumjs-tx" "5.0.1" + "@nomicfoundation/ethereumjs-util" "9.0.1" + ethereum-cryptography "0.1.3" + ethers "^5.7.1" + +"@nomicfoundation/ethereumjs-blockchain@7.0.1": + version "7.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-blockchain/-/ethereumjs-blockchain-7.0.1.tgz#80e0bd3535bfeb9baa29836b6f25123dab06a726" + integrity sha512-NhzndlGg829XXbqJEYrF1VeZhAwSPgsK/OB7TVrdzft3y918hW5KNd7gIZ85sn6peDZOdjBsAXIpXZ38oBYE5A== + dependencies: + "@nomicfoundation/ethereumjs-block" "5.0.1" + "@nomicfoundation/ethereumjs-common" "4.0.1" + "@nomicfoundation/ethereumjs-ethash" "3.0.1" + "@nomicfoundation/ethereumjs-rlp" "5.0.1" + "@nomicfoundation/ethereumjs-trie" "6.0.1" + "@nomicfoundation/ethereumjs-tx" "5.0.1" + "@nomicfoundation/ethereumjs-util" "9.0.1" + abstract-level "^1.0.3" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + level "^8.0.0" + lru-cache "^5.1.1" + memory-level "^1.0.0" + +"@nomicfoundation/ethereumjs-common@4.0.1": + version "4.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-common/-/ethereumjs-common-4.0.1.tgz#4702d82df35b07b5407583b54a45bf728e46a2f0" + integrity sha512-OBErlkfp54GpeiE06brBW/TTbtbuBJV5YI5Nz/aB2evTDo+KawyEzPjBlSr84z/8MFfj8wS2wxzQX1o32cev5g== + dependencies: + "@nomicfoundation/ethereumjs-util" "9.0.1" + crc-32 "^1.2.0" + +"@nomicfoundation/ethereumjs-ethash@3.0.1": + version "3.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-ethash/-/ethereumjs-ethash-3.0.1.tgz#65ca494d53e71e8415c9a49ef48bc921c538fc41" + integrity sha512-KDjGIB5igzWOp8Ik5I6QiRH5DH+XgILlplsHR7TEuWANZA759G6krQ6o8bvj+tRUz08YygMQu/sGd9mJ1DYT8w== + dependencies: + "@nomicfoundation/ethereumjs-block" "5.0.1" + "@nomicfoundation/ethereumjs-rlp" "5.0.1" + "@nomicfoundation/ethereumjs-util" "9.0.1" + abstract-level "^1.0.3" + bigint-crypto-utils "^3.0.23" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-evm@2.0.1": + version "2.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-evm/-/ethereumjs-evm-2.0.1.tgz#f35681e203363f69ce2b3d3bf9f44d4e883ca1f1" + integrity sha512-oL8vJcnk0Bx/onl+TgQOQ1t/534GKFaEG17fZmwtPFeH8S5soiBYPCLUrvANOl4sCp9elYxIMzIiTtMtNNN8EQ== + dependencies: + "@ethersproject/providers" "^5.7.1" + "@nomicfoundation/ethereumjs-common" "4.0.1" + "@nomicfoundation/ethereumjs-tx" "5.0.1" + "@nomicfoundation/ethereumjs-util" "9.0.1" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + mcl-wasm "^0.7.1" + rustbn.js "~0.2.0" + +"@nomicfoundation/ethereumjs-rlp@5.0.1": + version "5.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-rlp/-/ethereumjs-rlp-5.0.1.tgz#0b30c1cf77d125d390408e391c4bb5291ef43c28" + integrity sha512-xtxrMGa8kP4zF5ApBQBtjlSbN5E2HI8m8FYgVSYAnO6ssUoY5pVPGy2H8+xdf/bmMa22Ce8nWMH3aEW8CcqMeQ== + +"@nomicfoundation/ethereumjs-statemanager@2.0.1": + version "2.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-statemanager/-/ethereumjs-statemanager-2.0.1.tgz#8824a97938db4471911e2d2f140f79195def5935" + integrity sha512-B5ApMOnlruVOR7gisBaYwFX+L/AP7i/2oAahatssjPIBVDF6wTX1K7Qpa39E/nzsH8iYuL3krkYeUFIdO3EMUQ== + dependencies: + "@nomicfoundation/ethereumjs-common" "4.0.1" + "@nomicfoundation/ethereumjs-rlp" "5.0.1" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + ethers "^5.7.1" + js-sdsl "^4.1.4" + +"@nomicfoundation/ethereumjs-trie@6.0.1": + version "6.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-trie/-/ethereumjs-trie-6.0.1.tgz#662c55f6b50659fd4b22ea9f806a7401cafb7717" + integrity sha512-A64It/IMpDVODzCgxDgAAla8jNjNtsoQZIzZUfIV5AY6Coi4nvn7+VReBn5itlxMiL2yaTlQr9TRWp3CSI6VoA== + dependencies: + "@nomicfoundation/ethereumjs-rlp" "5.0.1" + "@nomicfoundation/ethereumjs-util" "9.0.1" + "@types/readable-stream" "^2.3.13" + ethereum-cryptography "0.1.3" + readable-stream "^3.6.0" + +"@nomicfoundation/ethereumjs-tx@5.0.1": + version "5.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-tx/-/ethereumjs-tx-5.0.1.tgz#7629dc2036b4a33c34e9f0a592b43227ef4f0c7d" + integrity sha512-0HwxUF2u2hrsIM1fsasjXvlbDOq1ZHFV2dd1yGq8CA+MEYhaxZr8OTScpVkkxqMwBcc5y83FyPl0J9MZn3kY0w== + dependencies: + "@chainsafe/ssz" "^0.9.2" + "@ethersproject/providers" "^5.7.2" + "@nomicfoundation/ethereumjs-common" "4.0.1" + "@nomicfoundation/ethereumjs-rlp" "5.0.1" + "@nomicfoundation/ethereumjs-util" "9.0.1" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-util@9.0.1": + version "9.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-util/-/ethereumjs-util-9.0.1.tgz#530cda8bae33f8b5020a8f199ed1d0a2ce48ec89" + integrity sha512-TwbhOWQ8QoSCFhV/DDfSmyfFIHjPjFBj957219+V3jTZYZ2rf9PmDtNOeZWAE3p3vlp8xb02XGpd0v6nTUPbsA== + dependencies: + "@chainsafe/ssz" "^0.10.0" + "@nomicfoundation/ethereumjs-rlp" "5.0.1" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-vm@7.0.1": + version "7.0.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-vm/-/ethereumjs-vm-7.0.1.tgz#7d035e0993bcad10716c8b36e61dfb87fa3ca05f" + integrity sha512-rArhyn0jPsS/D+ApFsz3yVJMQ29+pVzNZ0VJgkzAZ+7FqXSRtThl1C1prhmlVr3YNUlfpZ69Ak+RUT4g7VoOuQ== + dependencies: + "@nomicfoundation/ethereumjs-block" "5.0.1" + "@nomicfoundation/ethereumjs-blockchain" "7.0.1" + "@nomicfoundation/ethereumjs-common" "4.0.1" + "@nomicfoundation/ethereumjs-evm" "2.0.1" + "@nomicfoundation/ethereumjs-rlp" "5.0.1" + "@nomicfoundation/ethereumjs-statemanager" "2.0.1" + "@nomicfoundation/ethereumjs-trie" "6.0.1" + "@nomicfoundation/ethereumjs-tx" "5.0.1" + "@nomicfoundation/ethereumjs-util" "9.0.1" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + mcl-wasm "^0.7.1" + rustbn.js "~0.2.0" + +"@nomicfoundation/hardhat-chai-matchers@^1.0.3": + version "1.0.6" + resolved "https://registry.yarnpkg.com/@nomicfoundation/hardhat-chai-matchers/-/hardhat-chai-matchers-1.0.6.tgz#72a2e312e1504ee5dd73fe302932736432ba96bc" + integrity sha512-f5ZMNmabZeZegEfuxn/0kW+mm7+yV7VNDxLpMOMGXWFJ2l/Ct3QShujzDRF9cOkK9Ui/hbDeOWGZqyQALDXVCQ== + dependencies: + "@ethersproject/abi" "^5.1.2" + "@types/chai-as-promised" "^7.1.3" + chai-as-promised "^7.1.1" + deep-eql "^4.0.1" + ordinal "^1.0.3" + +"@nomicfoundation/solidity-analyzer-darwin-arm64@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-darwin-arm64/-/solidity-analyzer-darwin-arm64-0.1.1.tgz#4c858096b1c17fe58a474fe81b46815f93645c15" + integrity sha512-KcTodaQw8ivDZyF+D76FokN/HdpgGpfjc/gFCImdLUyqB6eSWVaZPazMbeAjmfhx3R0zm/NYVzxwAokFKgrc0w== + +"@nomicfoundation/solidity-analyzer-darwin-x64@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-darwin-x64/-/solidity-analyzer-darwin-x64-0.1.1.tgz#6e25ccdf6e2d22389c35553b64fe6f3fdaec432c" + integrity sha512-XhQG4BaJE6cIbjAVtzGOGbK3sn1BO9W29uhk9J8y8fZF1DYz0Doj8QDMfpMu+A6TjPDs61lbsmeYodIDnfveSA== + +"@nomicfoundation/solidity-analyzer-freebsd-x64@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-freebsd-x64/-/solidity-analyzer-freebsd-x64-0.1.1.tgz#0a224ea50317139caeebcdedd435c28a039d169c" + integrity sha512-GHF1VKRdHW3G8CndkwdaeLkVBi5A9u2jwtlS7SLhBc8b5U/GcoL39Q+1CSO3hYqePNP+eV5YI7Zgm0ea6kMHoA== + +"@nomicfoundation/solidity-analyzer-linux-arm64-gnu@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-arm64-gnu/-/solidity-analyzer-linux-arm64-gnu-0.1.1.tgz#dfa085d9ffab9efb2e7b383aed3f557f7687ac2b" + integrity sha512-g4Cv2fO37ZsUENQ2vwPnZc2zRenHyAxHcyBjKcjaSmmkKrFr64yvzeNO8S3GBFCo90rfochLs99wFVGT/0owpg== + +"@nomicfoundation/solidity-analyzer-linux-arm64-musl@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-arm64-musl/-/solidity-analyzer-linux-arm64-musl-0.1.1.tgz#c9e06b5d513dd3ab02a7ac069c160051675889a4" + integrity sha512-WJ3CE5Oek25OGE3WwzK7oaopY8xMw9Lhb0mlYuJl/maZVo+WtP36XoQTb7bW/i8aAdHW5Z+BqrHMux23pvxG3w== + +"@nomicfoundation/solidity-analyzer-linux-x64-gnu@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-x64-gnu/-/solidity-analyzer-linux-x64-gnu-0.1.1.tgz#8d328d16839e52571f72f2998c81e46bf320f893" + integrity sha512-5WN7leSr5fkUBBjE4f3wKENUy9HQStu7HmWqbtknfXkkil+eNWiBV275IOlpXku7v3uLsXTOKpnnGHJYI2qsdA== + +"@nomicfoundation/solidity-analyzer-linux-x64-musl@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-x64-musl/-/solidity-analyzer-linux-x64-musl-0.1.1.tgz#9b49d0634b5976bb5ed1604a1e1b736f390959bb" + integrity sha512-KdYMkJOq0SYPQMmErv/63CwGwMm5XHenEna9X9aB8mQmhDBrYrlAOSsIPgFCUSL0hjxE3xHP65/EPXR/InD2+w== + +"@nomicfoundation/solidity-analyzer-win32-arm64-msvc@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-arm64-msvc/-/solidity-analyzer-win32-arm64-msvc-0.1.1.tgz#e2867af7264ebbcc3131ef837878955dd6a3676f" + integrity sha512-VFZASBfl4qiBYwW5xeY20exWhmv6ww9sWu/krWSesv3q5hA0o1JuzmPHR4LPN6SUZj5vcqci0O6JOL8BPw+APg== + +"@nomicfoundation/solidity-analyzer-win32-ia32-msvc@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-ia32-msvc/-/solidity-analyzer-win32-ia32-msvc-0.1.1.tgz#0685f78608dd516c8cdfb4896ed451317e559585" + integrity sha512-JnFkYuyCSA70j6Si6cS1A9Gh1aHTEb8kOTBApp/c7NRTFGNMH8eaInKlyuuiIbvYFhlXW4LicqyYuWNNq9hkpQ== + +"@nomicfoundation/solidity-analyzer-win32-x64-msvc@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-x64-msvc/-/solidity-analyzer-win32-x64-msvc-0.1.1.tgz#c9a44f7108646f083b82e851486e0f6aeb785836" + integrity sha512-HrVJr6+WjIXGnw3Q9u6KQcbZCtk0caVWhCdFADySvRyUxJ8PnzlaP+MhwNE8oyT8OZ6ejHBRrrgjSqDCFXGirw== + +"@nomicfoundation/solidity-analyzer@^0.1.0": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer/-/solidity-analyzer-0.1.1.tgz#f5f4d36d3f66752f59a57e7208cd856f3ddf6f2d" + integrity sha512-1LMtXj1puAxyFusBgUIy5pZk3073cNXYnXUpuNKFghHbIit/xZgbk0AokpUADbNm3gyD6bFWl3LRFh3dhVdREg== + optionalDependencies: + "@nomicfoundation/solidity-analyzer-darwin-arm64" "0.1.1" + "@nomicfoundation/solidity-analyzer-darwin-x64" "0.1.1" + "@nomicfoundation/solidity-analyzer-freebsd-x64" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-arm64-gnu" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-arm64-musl" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-x64-gnu" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-x64-musl" "0.1.1" + "@nomicfoundation/solidity-analyzer-win32-arm64-msvc" "0.1.1" + "@nomicfoundation/solidity-analyzer-win32-ia32-msvc" "0.1.1" + "@nomicfoundation/solidity-analyzer-win32-x64-msvc" "0.1.1" + +"@nomiclabs/hardhat-docker@^2.0.0": + version "2.0.2" + resolved "https://registry.yarnpkg.com/@nomiclabs/hardhat-docker/-/hardhat-docker-2.0.2.tgz#ae964be17951275a55859ff7358e9e7c77448846" + integrity sha512-XgGEpRT3wlA1VslyB57zyAHV+oll8KnV1TjwnxxC1tpAL04/lbdwpdO5KxInVN8irMSepqFpsiSkqlcnvbE7Ng== + dependencies: + dockerode "^2.5.8" + fs-extra "^7.0.1" + node-fetch "^2.6.0" + +"@nomiclabs/hardhat-ethers@^2.0.6": + version "2.2.3" + resolved "https://registry.yarnpkg.com/@nomiclabs/hardhat-ethers/-/hardhat-ethers-2.2.3.tgz#b41053e360c31a32c2640c9a45ee981a7e603fe0" + integrity sha512-YhzPdzb612X591FOe68q+qXVXGG2ANZRvDo0RRUtimev85rCrAlv/TLMEZw5c+kq9AbzocLTVX/h2jVIFPL9Xg== + +"@nomiclabs/hardhat-solpp@^2.0.1": + version "2.0.1" + resolved "https://registry.yarnpkg.com/@nomiclabs/hardhat-solpp/-/hardhat-solpp-2.0.1.tgz#04039b3745b8d2b48c9b8bec6509e9785631aaba" + integrity sha512-aWYvB91GPJcnye4Ph26Jd9BfBNNisI1iRNSbHB2i09OpxucSHAPMvvqTfWDN1HE5EMjqlTJ2rQLdlDcYqQxPJw== + dependencies: + fs-extra "^7.0.1" + solpp "^0.11.5" + +"@pkgr/utils@^2.3.1": + version "2.4.2" + resolved "https://registry.yarnpkg.com/@pkgr/utils/-/utils-2.4.2.tgz#9e638bbe9a6a6f165580dc943f138fd3309a2cbc" + integrity sha512-POgTXhjrTfbTV63DiFXav4lBHiICLKKwDeaKn9Nphwj7WH6m0hMMCaJkMyRWjgtPFyRKRVoMXXjczsTQRDEhYw== + dependencies: + cross-spawn "^7.0.3" + fast-glob "^3.3.0" + is-glob "^4.0.3" + open "^9.1.0" + picocolors "^1.0.0" + tslib "^2.6.0" + +"@scure/base@~1.1.0": + version "1.1.3" + resolved "https://registry.yarnpkg.com/@scure/base/-/base-1.1.3.tgz#8584115565228290a6c6c4961973e0903bb3df2f" + integrity sha512-/+SgoRjLq7Xlf0CWuLHq2LUZeL/w65kfzAPG5NH9pcmBhs+nunQTn4gvdwgMTIXnt9b2C/1SeL2XiysZEyIC9Q== + +"@scure/bip32@1.1.5": + version "1.1.5" + resolved "https://registry.yarnpkg.com/@scure/bip32/-/bip32-1.1.5.tgz#d2ccae16dcc2e75bc1d75f5ef3c66a338d1ba300" + integrity sha512-XyNh1rB0SkEqd3tXcXMi+Xe1fvg+kUIcoRIEujP1Jgv7DqW2r9lg3Ah0NkFaCs9sTkQAQA8kw7xiRXzENi9Rtw== + dependencies: + "@noble/hashes" "~1.2.0" + "@noble/secp256k1" "~1.7.0" + "@scure/base" "~1.1.0" + +"@scure/bip39@1.1.1": + version "1.1.1" + resolved "https://registry.yarnpkg.com/@scure/bip39/-/bip39-1.1.1.tgz#b54557b2e86214319405db819c4b6a370cf340c5" + integrity sha512-t+wDck2rVkh65Hmv280fYdVdY25J9YeEUIgn2LG1WM6gxFkGzcksoDiUkWVpVp3Oex9xGC68JU2dSbUfwZ2jPg== + dependencies: + "@noble/hashes" "~1.2.0" + "@scure/base" "~1.1.0" + +"@sentry/core@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/core/-/core-5.30.0.tgz#6b203664f69e75106ee8b5a2fe1d717379b331f3" + integrity sha512-TmfrII8w1PQZSZgPpUESqjB+jC6MvZJZdLtE/0hZ+SrnKhW3x5WlYLvTXZpcWePYBku7rl2wn1RZu6uT0qCTeg== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/minimal" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/hub@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/hub/-/hub-5.30.0.tgz#2453be9b9cb903404366e198bd30c7ca74cdc100" + integrity sha512-2tYrGnzb1gKz2EkMDQcfLrDTvmGcQPuWxLnJKXJvYTQDGLlEvi2tWz1VIHjunmOvJrB5aIQLhm+dcMRwFZDCqQ== + dependencies: + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/minimal@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/minimal/-/minimal-5.30.0.tgz#ce3d3a6a273428e0084adcb800bc12e72d34637b" + integrity sha512-BwWb/owZKtkDX+Sc4zCSTNcvZUq7YcH3uAVlmh/gtR9rmUvbzAA3ewLuB3myi4wWRAMEtny6+J/FN/x+2wn9Xw== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/types" "5.30.0" + tslib "^1.9.3" + +"@sentry/node@^5.18.1": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/node/-/node-5.30.0.tgz#4ca479e799b1021285d7fe12ac0858951c11cd48" + integrity sha512-Br5oyVBF0fZo6ZS9bxbJZG4ApAjRqAnqFFurMVJJdunNb80brh7a5Qva2kjhm+U6r9NJAB5OmDyPkA1Qnt+QVg== + dependencies: + "@sentry/core" "5.30.0" + "@sentry/hub" "5.30.0" + "@sentry/tracing" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + cookie "^0.4.1" + https-proxy-agent "^5.0.0" + lru_map "^0.3.3" + tslib "^1.9.3" + +"@sentry/tracing@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/tracing/-/tracing-5.30.0.tgz#501d21f00c3f3be7f7635d8710da70d9419d4e1f" + integrity sha512-dUFowCr0AIMwiLD7Fs314Mdzcug+gBVo/+NCMyDw8tFxJkwWAKl7Qa2OZxLQ0ZHjakcj1hNKfCQJ9rhyfOl4Aw== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/minimal" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/types@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/types/-/types-5.30.0.tgz#19709bbe12a1a0115bc790b8942917da5636f402" + integrity sha512-R8xOqlSTZ+htqrfteCWU5Nk0CDN5ApUTvrlvBuiH1DyP6czDZ4ktbZB0hAgBlVcK0U+qpD3ag3Tqqpa5Q67rPw== + +"@sentry/utils@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/utils/-/utils-5.30.0.tgz#9a5bd7ccff85ccfe7856d493bffa64cabc41e980" + integrity sha512-zaYmoH0NWWtvnJjC9/CBseXMtKHm/tm40sz3YfJRxeQjyzRqNQPgivpd9R/oDJCYj999mzdW382p/qi2ypjLww== + dependencies: + "@sentry/types" "5.30.0" + tslib "^1.9.3" + +"@solidity-parser/parser@^0.16.0": + version "0.16.1" + resolved "https://registry.yarnpkg.com/@solidity-parser/parser/-/parser-0.16.1.tgz#f7c8a686974e1536da0105466c4db6727311253c" + integrity sha512-PdhRFNhbTtu3x8Axm0uYpqOy/lODYQK+MlYSgqIsq2L8SFYEHJPHNUiOTAJbDGzNjjr1/n9AcIayxafR/fWmYw== + dependencies: + antlr4ts "^0.5.0-alpha.4" + +"@ts-morph/common@~0.20.0": + version "0.20.0" + resolved "https://registry.yarnpkg.com/@ts-morph/common/-/common-0.20.0.tgz#3f161996b085ba4519731e4d24c35f6cba5b80af" + integrity sha512-7uKjByfbPpwuzkstL3L5MQyuXPSKdoNG93Fmi2JoDcTf3pEP731JdRFAduRVkOs8oqxPsXKA+ScrWkdQ8t/I+Q== + dependencies: + fast-glob "^3.2.12" + minimatch "^7.4.3" + mkdirp "^2.1.6" + path-browserify "^1.0.1" + +"@tsconfig/node10@^1.0.7": + version "1.0.9" + resolved "https://registry.yarnpkg.com/@tsconfig/node10/-/node10-1.0.9.tgz#df4907fc07a886922637b15e02d4cebc4c0021b2" + integrity sha512-jNsYVVxU8v5g43Erja32laIDHXeoNvFEpX33OK4d6hljo3jDhCBDhx5dhCCTMWUojscpAagGiRkBKxpdl9fxqA== + +"@tsconfig/node12@^1.0.7": + version "1.0.11" + resolved "https://registry.yarnpkg.com/@tsconfig/node12/-/node12-1.0.11.tgz#ee3def1f27d9ed66dac6e46a295cffb0152e058d" + integrity sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag== + +"@tsconfig/node14@^1.0.0": + version "1.0.3" + resolved "https://registry.yarnpkg.com/@tsconfig/node14/-/node14-1.0.3.tgz#e4386316284f00b98435bf40f72f75a09dabf6c1" + integrity sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow== + +"@tsconfig/node16@^1.0.2": + version "1.0.4" + resolved "https://registry.yarnpkg.com/@tsconfig/node16/-/node16-1.0.4.tgz#0b92dcc0cc1c81f6f306a381f28e31b1a56536e9" + integrity sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA== + +"@typechain/ethers-v5@^10.0.0": + version "10.2.1" + resolved "https://registry.yarnpkg.com/@typechain/ethers-v5/-/ethers-v5-10.2.1.tgz#50241e6957683281ecfa03fb5a6724d8a3ce2391" + integrity sha512-n3tQmCZjRE6IU4h6lqUGiQ1j866n5MTCBJreNEHHVWXa2u9GJTaeYyU1/k+1qLutkyw+sS6VAN+AbeiTqsxd/A== + dependencies: + lodash "^4.17.15" + ts-essentials "^7.0.1" + +"@typechain/hardhat@^7.0.0": + version "7.0.0" + resolved "https://registry.yarnpkg.com/@typechain/hardhat/-/hardhat-7.0.0.tgz#ffa7465328150e793007fee616ae7b76ed20784d" + integrity sha512-XB79i5ewg9Met7gMVGfgVkmypicbnI25T5clJBEooMoW2161p4zvKFpoS2O+lBppQyMrPIZkdvl2M3LMDayVcA== + dependencies: + fs-extra "^9.1.0" + +"@types/bn.js@^4.11.3": + version "4.11.6" + resolved "https://registry.yarnpkg.com/@types/bn.js/-/bn.js-4.11.6.tgz#c306c70d9358aaea33cd4eda092a742b9505967c" + integrity sha512-pqr857jrp2kPuO9uRjZ3PwnJTjoQy+fcdxvBTvHm6dkmEL9q+hDD/2j/0ELOBPtPnS8LjCX0gI9nbl8lVkadpg== + dependencies: + "@types/node" "*" + +"@types/bn.js@^5.1.0": + version "5.1.1" + resolved "https://registry.yarnpkg.com/@types/bn.js/-/bn.js-5.1.1.tgz#b51e1b55920a4ca26e9285ff79936bbdec910682" + integrity sha512-qNrYbZqMx0uJAfKnKclPh+dTwK33KfLHYqtyODwd5HnXOjnkhc4qgn3BrK6RWyGZm5+sIFE7Q7Vz6QQtJB7w7g== + dependencies: + "@types/node" "*" + +"@types/chai-as-promised@^7.1.3": + version "7.1.6" + resolved "https://registry.yarnpkg.com/@types/chai-as-promised/-/chai-as-promised-7.1.6.tgz#3b08cbe1e7206567a480dc6538bade374b19e4e1" + integrity sha512-cQLhk8fFarRVZAXUQV1xEnZgMoPxqKojBvRkqPCKPQCzEhpbbSKl1Uu75kDng7k5Ln6LQLUmNBjLlFthCgm1NA== + dependencies: + "@types/chai" "*" + +"@types/chai@*": + version "4.3.6" + resolved "https://registry.yarnpkg.com/@types/chai/-/chai-4.3.6.tgz#7b489e8baf393d5dd1266fb203ddd4ea941259e6" + integrity sha512-VOVRLM1mBxIRxydiViqPcKn6MIxZytrbMpd6RJLIWKxUNr3zux8no0Oc7kJx0WAPIitgZ0gkrDS+btlqQpubpw== + +"@types/chai@^4.3.1": + version "4.3.3" + resolved "https://registry.yarnpkg.com/@types/chai/-/chai-4.3.3.tgz#3c90752792660c4b562ad73b3fbd68bf3bc7ae07" + integrity sha512-hC7OMnszpxhZPduX+m+nrx+uFoLkWOMiR4oa/AZF3MuSETYTZmFfJAHqZEM8MVlvfG7BEUcgvtwoCTxBp6hm3g== + +"@types/json-schema@^7.0.12": + version "7.0.14" + resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.14.tgz#74a97a5573980802f32c8e47b663530ab3b6b7d1" + integrity sha512-U3PUjAudAdJBeC2pgN8uTIKgxrb4nlDF3SF0++EldXQvQBGkpFZMSnwQiIoDU77tv45VgNkl/L4ouD+rEomujw== + +"@types/json5@^0.0.29": + version "0.0.29" + resolved "https://registry.yarnpkg.com/@types/json5/-/json5-0.0.29.tgz#ee28707ae94e11d2b827bcbe5270bcea7f3e71ee" + integrity sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ== + +"@types/lodash@^4.14.199": + version "4.14.199" + resolved "https://registry.yarnpkg.com/@types/lodash/-/lodash-4.14.199.tgz#c3edb5650149d847a277a8961a7ad360c474e9bf" + integrity sha512-Vrjz5N5Ia4SEzWWgIVwnHNEnb1UE1XMkvY5DGXrAeOGE9imk0hgTHh5GyDjLDJi9OTCn9oo9dXH1uToK1VRfrg== + +"@types/lru-cache@^5.1.0": + version "5.1.1" + resolved "https://registry.yarnpkg.com/@types/lru-cache/-/lru-cache-5.1.1.tgz#c48c2e27b65d2a153b19bfc1a317e30872e01eef" + integrity sha512-ssE3Vlrys7sdIzs5LOxCzTVMsU7i9oa/IaW92wF32JFb3CVczqOkru2xspuKczHEbG3nvmPY7IFqVmGGHdNbYw== + +"@types/mkdirp@^0.5.2": + version "0.5.2" + resolved "https://registry.yarnpkg.com/@types/mkdirp/-/mkdirp-0.5.2.tgz#503aacfe5cc2703d5484326b1b27efa67a339c1f" + integrity sha512-U5icWpv7YnZYGsN4/cmh3WD2onMY0aJIiTE6+51TwJCttdHvtCYmkBNOobHlXwrJRL0nkH9jH4kD+1FAdMN4Tg== + dependencies: + "@types/node" "*" + +"@types/mocha@^9.1.1": + version "9.1.1" + resolved "https://registry.yarnpkg.com/@types/mocha/-/mocha-9.1.1.tgz#e7c4f1001eefa4b8afbd1eee27a237fee3bf29c4" + integrity sha512-Z61JK7DKDtdKTWwLeElSEBcWGRLY8g95ic5FoQqI9CMx0ns/Ghep3B4DfcEimiKMvtamNVULVNKEsiwV3aQmXw== + +"@types/node@*": + version "20.6.0" + resolved "https://registry.yarnpkg.com/@types/node/-/node-20.6.0.tgz#9d7daa855d33d4efec8aea88cd66db1c2f0ebe16" + integrity sha512-najjVq5KN2vsH2U/xyh2opaSEz6cZMR2SetLIlxlj08nOcmPOemJmUK2o4kUzfLqfrWE0PIrNeE16XhYDd3nqg== + +"@types/node@^17.0.34": + version "17.0.45" + resolved "https://registry.yarnpkg.com/@types/node/-/node-17.0.45.tgz#2c0fafd78705e7a18b7906b5201a522719dc5190" + integrity sha512-w+tIMs3rq2afQdsPJlODhoUEKzFP1ayaoyl1CcnwtIlsVe7K7bA1NGm4s3PraqTLlXnbIN84zuBlxBWo1u9BLw== + +"@types/pbkdf2@^3.0.0": + version "3.1.0" + resolved "https://registry.yarnpkg.com/@types/pbkdf2/-/pbkdf2-3.1.0.tgz#039a0e9b67da0cdc4ee5dab865caa6b267bb66b1" + integrity sha512-Cf63Rv7jCQ0LaL8tNXmEyqTHuIJxRdlS5vMh1mj5voN4+QFhVZnlZruezqpWYDiJ8UTzhP0VmeLXCmBk66YrMQ== + dependencies: + "@types/node" "*" + +"@types/prettier@^2.1.1": + version "2.7.3" + resolved "https://registry.yarnpkg.com/@types/prettier/-/prettier-2.7.3.tgz#3e51a17e291d01d17d3fc61422015a933af7a08f" + integrity sha512-+68kP9yzs4LMp7VNh8gdzMSPZFL44MLGqiHWvttYJe+6qnuVr4Ek9wSBQoveqY/r+LwjCcU29kNVkidwim+kYA== + +"@types/readable-stream@^2.3.13": + version "2.3.15" + resolved "https://registry.yarnpkg.com/@types/readable-stream/-/readable-stream-2.3.15.tgz#3d79c9ceb1b6a57d5f6e6976f489b9b5384321ae" + integrity sha512-oM5JSKQCcICF1wvGgmecmHldZ48OZamtMxcGGVICOJA8o8cahXC1zEVAif8iwoc5j8etxFaRFnf095+CDsuoFQ== + dependencies: + "@types/node" "*" + safe-buffer "~5.1.1" + +"@types/resolve@^0.0.8": + version "0.0.8" + resolved "https://registry.yarnpkg.com/@types/resolve/-/resolve-0.0.8.tgz#f26074d238e02659e323ce1a13d041eee280e194" + integrity sha512-auApPaJf3NPfe18hSoJkp8EbZzer2ISk7o8mCC3M9he/a04+gbMF97NkpD2S8riMGvm4BMRI59/SZQSaLTKpsQ== + dependencies: + "@types/node" "*" + +"@types/secp256k1@^4.0.1": + version "4.0.3" + resolved "https://registry.yarnpkg.com/@types/secp256k1/-/secp256k1-4.0.3.tgz#1b8e55d8e00f08ee7220b4d59a6abe89c37a901c" + integrity sha512-Da66lEIFeIz9ltsdMZcpQvmrmmoqrfju8pm1BH8WbYjZSwUgCwXLb9C+9XYogwBITnbsSaMdVPb2ekf7TV+03w== + dependencies: + "@types/node" "*" + +"@types/semver@^7.5.0": + version "7.5.4" + resolved "https://registry.yarnpkg.com/@types/semver/-/semver-7.5.4.tgz#0a41252ad431c473158b22f9bfb9a63df7541cff" + integrity sha512-MMzuxN3GdFwskAnb6fz0orFvhfqi752yjaXylr0Rp4oDg5H0Zn1IuyRhDVvYOwAXoJirx2xuS16I3WjxnAIHiQ== + +"@typescript-eslint/eslint-plugin@^6.7.4": + version "6.9.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-6.9.0.tgz#fdb6f3821c0167e3356e9d89c80e8230b2e401f4" + integrity sha512-lgX7F0azQwRPB7t7WAyeHWVfW1YJ9NIgd9mvGhfQpRY56X6AVf8mwM8Wol+0z4liE7XX3QOt8MN1rUKCfSjRIA== + dependencies: + "@eslint-community/regexpp" "^4.5.1" + "@typescript-eslint/scope-manager" "6.9.0" + "@typescript-eslint/type-utils" "6.9.0" + "@typescript-eslint/utils" "6.9.0" + "@typescript-eslint/visitor-keys" "6.9.0" + debug "^4.3.4" + graphemer "^1.4.0" + ignore "^5.2.4" + natural-compare "^1.4.0" + semver "^7.5.4" + ts-api-utils "^1.0.1" + +"@typescript-eslint/parser@^6.7.4": + version "6.9.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/parser/-/parser-6.9.0.tgz#2b402cadeadd3f211c25820e5433413347b27391" + integrity sha512-GZmjMh4AJ/5gaH4XF2eXA8tMnHWP+Pm1mjQR2QN4Iz+j/zO04b9TOvJYOX2sCNIQHtRStKTxRY1FX7LhpJT4Gw== + dependencies: + "@typescript-eslint/scope-manager" "6.9.0" + "@typescript-eslint/types" "6.9.0" + "@typescript-eslint/typescript-estree" "6.9.0" + "@typescript-eslint/visitor-keys" "6.9.0" + debug "^4.3.4" + +"@typescript-eslint/scope-manager@6.9.0": + version "6.9.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/scope-manager/-/scope-manager-6.9.0.tgz#2626e9a7fe0e004c3e25f3b986c75f584431134e" + integrity sha512-1R8A9Mc39n4pCCz9o79qRO31HGNDvC7UhPhv26TovDsWPBDx+Sg3rOZdCELIA3ZmNoWAuxaMOT7aWtGRSYkQxw== + dependencies: + "@typescript-eslint/types" "6.9.0" + "@typescript-eslint/visitor-keys" "6.9.0" + +"@typescript-eslint/type-utils@6.9.0": + version "6.9.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/type-utils/-/type-utils-6.9.0.tgz#23923c8c9677c2ad41457cf8e10a5f2946be1b04" + integrity sha512-XXeahmfbpuhVbhSOROIzJ+b13krFmgtc4GlEuu1WBT+RpyGPIA4Y/eGnXzjbDj5gZLzpAXO/sj+IF/x2GtTMjQ== + dependencies: + "@typescript-eslint/typescript-estree" "6.9.0" + "@typescript-eslint/utils" "6.9.0" + debug "^4.3.4" + ts-api-utils "^1.0.1" + +"@typescript-eslint/types@6.9.0": + version "6.9.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/types/-/types-6.9.0.tgz#86a0cbe7ac46c0761429f928467ff3d92f841098" + integrity sha512-+KB0lbkpxBkBSiVCuQvduqMJy+I1FyDbdwSpM3IoBS7APl4Bu15lStPjgBIdykdRqQNYqYNMa8Kuidax6phaEw== + +"@typescript-eslint/typescript-estree@6.9.0": + version "6.9.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/typescript-estree/-/typescript-estree-6.9.0.tgz#d0601b245be873d8fe49f3737f93f8662c8693d4" + integrity sha512-NJM2BnJFZBEAbCfBP00zONKXvMqihZCrmwCaik0UhLr0vAgb6oguXxLX1k00oQyD+vZZ+CJn3kocvv2yxm4awQ== + dependencies: + "@typescript-eslint/types" "6.9.0" + "@typescript-eslint/visitor-keys" "6.9.0" + debug "^4.3.4" + globby "^11.1.0" + is-glob "^4.0.3" + semver "^7.5.4" + ts-api-utils "^1.0.1" + +"@typescript-eslint/utils@6.9.0": + version "6.9.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-6.9.0.tgz#5bdac8604fca4823f090e4268e681c84d3597c9f" + integrity sha512-5Wf+Jsqya7WcCO8me504FBigeQKVLAMPmUzYgDbWchINNh1KJbxCgVya3EQ2MjvJMVeXl3pofRmprqX6mfQkjQ== + dependencies: + "@eslint-community/eslint-utils" "^4.4.0" + "@types/json-schema" "^7.0.12" + "@types/semver" "^7.5.0" + "@typescript-eslint/scope-manager" "6.9.0" + "@typescript-eslint/types" "6.9.0" + "@typescript-eslint/typescript-estree" "6.9.0" + semver "^7.5.4" + +"@typescript-eslint/visitor-keys@6.9.0": + version "6.9.0" + resolved "https://registry.yarnpkg.com/@typescript-eslint/visitor-keys/-/visitor-keys-6.9.0.tgz#cc69421c10c4ac997ed34f453027245988164e80" + integrity sha512-dGtAfqjV6RFOtIP8I0B4ZTBRrlTT8NHHlZZSchQx3qReaoDeXhYM++M4So2AgFK9ZB0emRPA6JI1HkafzA2Ibg== + dependencies: + "@typescript-eslint/types" "6.9.0" + eslint-visitor-keys "^3.4.1" + +"@ungap/structured-clone@^1.2.0": + version "1.2.0" + resolved "https://registry.yarnpkg.com/@ungap/structured-clone/-/structured-clone-1.2.0.tgz#756641adb587851b5ccb3e095daf27ae581c8406" + integrity sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ== + +JSONStream@1.3.2: + version "1.3.2" + resolved "https://registry.yarnpkg.com/JSONStream/-/JSONStream-1.3.2.tgz#c102371b6ec3a7cf3b847ca00c20bb0fce4c6dea" + integrity sha512-mn0KSip7N4e0UDPZHnqDsHECo5uGQrixQKnAskOM1BIB8hd7QKbd6il8IPRPudPHOeHiECoCFqhyMaRO9+nWyA== + dependencies: + jsonparse "^1.2.0" + through ">=2.2.7 <3" + +abort-controller@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/abort-controller/-/abort-controller-3.0.0.tgz#eaf54d53b62bae4138e809ca225c8439a6efb392" + integrity sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg== + dependencies: + event-target-shim "^5.0.0" + +abstract-level@^1.0.0, abstract-level@^1.0.2, abstract-level@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/abstract-level/-/abstract-level-1.0.3.tgz#78a67d3d84da55ee15201486ab44c09560070741" + integrity sha512-t6jv+xHy+VYwc4xqZMn2Pa9DjcdzvzZmQGRjTFc8spIbRGHgBrEKbPq+rYXc7CCo0lxgYvSgKVg9qZAhpVQSjA== + dependencies: + buffer "^6.0.3" + catering "^2.1.0" + is-buffer "^2.0.5" + level-supports "^4.0.0" + level-transcoder "^1.0.1" + module-error "^1.0.1" + queue-microtask "^1.2.3" + +acorn-jsx@^5.3.2: + version "5.3.2" + resolved "https://registry.yarnpkg.com/acorn-jsx/-/acorn-jsx-5.3.2.tgz#7ed5bb55908b3b2f1bc55c6af1653bada7f07937" + integrity sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ== + +acorn-walk@^8.1.1: + version "8.2.0" + resolved "https://registry.yarnpkg.com/acorn-walk/-/acorn-walk-8.2.0.tgz#741210f2e2426454508853a2f44d0ab83b7f69c1" + integrity sha512-k+iyHEuPgSw6SbuDpGQM+06HQUa04DZ3o+F6CSzXMvvI5KMvnaEqXe+YVe555R9nn6GPt404fos4wcgpw12SDA== + +acorn@^8.4.1: + version "8.10.0" + resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.10.0.tgz#8be5b3907a67221a81ab23c7889c4c5526b62ec5" + integrity sha512-F0SAmZ8iUtS//m8DmCTA0jlh6TDKkHQyK6xc6V4KDTyZKA9dnvX9/3sRTVQrWm79glUAZbnmmNcdYwUIHWVybw== + +acorn@^8.9.0: + version "8.11.2" + resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.11.2.tgz#ca0d78b51895be5390a5903c5b3bdcdaf78ae40b" + integrity sha512-nc0Axzp/0FILLEVsm4fNwLCwMttvhEI263QtVPQcbpfZZ3ts0hLsZGOpE6czNlid7CJ9MlyH8reXkpsf3YUY4w== + +adm-zip@^0.4.16: + version "0.4.16" + resolved "https://registry.yarnpkg.com/adm-zip/-/adm-zip-0.4.16.tgz#cf4c508fdffab02c269cbc7f471a875f05570365" + integrity sha512-TFi4HBKSGfIKsK5YCkKaaFG2m4PEDyViZmEwof3MTIgzimHLto6muaHVpbrljdIvIrFZzEq/p4nafOeLcYegrg== + +aes-js@3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/aes-js/-/aes-js-3.0.0.tgz#e21df10ad6c2053295bcbb8dab40b09dbea87e4d" + integrity sha512-H7wUZRn8WpTq9jocdxQ2c8x2sKo9ZVmzfRE13GiNJXfp7NcKYEdvl3vspKjXox6RIG2VtaRe4JFvxG4rqp2Zuw== + +agent-base@6: + version "6.0.2" + resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-6.0.2.tgz#49fff58577cfee3f37176feab4c22e00f86d7f77" + integrity sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ== + dependencies: + debug "4" + +aggregate-error@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/aggregate-error/-/aggregate-error-3.1.0.tgz#92670ff50f5359bdb7a3e0d40d0ec30c5737687a" + integrity sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA== + dependencies: + clean-stack "^2.0.0" + indent-string "^4.0.0" + +ajv@^6.12.4, ajv@^6.12.6: + version "6.12.6" + resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.12.6.tgz#baf5a62e802b07d977034586f8c3baf5adf26df4" + integrity sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g== + dependencies: + fast-deep-equal "^3.1.1" + fast-json-stable-stringify "^2.0.0" + json-schema-traverse "^0.4.1" + uri-js "^4.2.2" + +ajv@^8.0.1: + version "8.12.0" + resolved "https://registry.yarnpkg.com/ajv/-/ajv-8.12.0.tgz#d1a0527323e22f53562c567c00991577dfbe19d1" + integrity sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA== + dependencies: + fast-deep-equal "^3.1.1" + json-schema-traverse "^1.0.0" + require-from-string "^2.0.2" + uri-js "^4.2.2" + +ansi-colors@4.1.1: + version "4.1.1" + resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-4.1.1.tgz#cbb9ae256bf750af1eab344f229aa27fe94ba348" + integrity sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA== + +ansi-colors@^4.1.1: + version "4.1.3" + resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-4.1.3.tgz#37611340eb2243e70cc604cad35d63270d48781b" + integrity sha512-/6w/C21Pm1A7aZitlI5Ni/2J6FFQN8i1Cvz3kHABAAbw93v/NlvKdVOqz7CCWz/3iv/JplRSEEZ83XION15ovw== + +ansi-escapes@^4.3.0: + version "4.3.2" + resolved "https://registry.yarnpkg.com/ansi-escapes/-/ansi-escapes-4.3.2.tgz#6b2291d1db7d98b6521d5f1efa42d0f3a9feb65e" + integrity sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ== + dependencies: + type-fest "^0.21.3" + +ansi-regex@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-5.0.1.tgz#082cb2c89c9fe8659a311a53bd6a4dc5301db304" + integrity sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ== + +ansi-styles@^3.2.1: + version "3.2.1" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-3.2.1.tgz#41fbb20243e50b12be0f04b8dedbf07520ce841d" + integrity sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA== + dependencies: + color-convert "^1.9.0" + +ansi-styles@^4.0.0, ansi-styles@^4.1.0: + version "4.3.0" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-4.3.0.tgz#edd803628ae71c04c85ae7a0906edad34b648937" + integrity sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg== + dependencies: + color-convert "^2.0.1" + +antlr4@^4.11.0: + version "4.13.1" + resolved "https://registry.yarnpkg.com/antlr4/-/antlr4-4.13.1.tgz#1e0a1830a08faeb86217cb2e6c34716004e4253d" + integrity sha512-kiXTspaRYvnIArgE97z5YVVf/cDVQABr3abFRR6mE7yesLMkgu4ujuyV/sgxafQ8wgve0DJQUJ38Z8tkgA2izA== + +antlr4@~4.8.0: + version "4.8.0" + resolved "https://registry.yarnpkg.com/antlr4/-/antlr4-4.8.0.tgz#f938ec171be7fc2855cd3a533e87647185b32b6a" + integrity sha512-en/MxQ4OkPgGJQ3wD/muzj1uDnFSzdFIhc2+c6bHZokWkuBb6RRvFjpWhPxWLbgQvaEzldJZ0GSQpfSAaE3hqg== + +antlr4ts@^0.5.0-alpha.4: + version "0.5.0-alpha.4" + resolved "https://registry.yarnpkg.com/antlr4ts/-/antlr4ts-0.5.0-alpha.4.tgz#71702865a87478ed0b40c0709f422cf14d51652a" + integrity sha512-WPQDt1B74OfPv/IMS2ekXAKkTZIHl88uMetg6q3OTqgFxZ/dxDXI0EWLyZid/1Pe6hTftyg5N7gel5wNAGxXyQ== + +any-promise@^1.0.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/any-promise/-/any-promise-1.3.0.tgz#abc6afeedcea52e809cdc0376aed3ce39635d17f" + integrity sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A== + +anymatch@~3.1.2: + version "3.1.3" + resolved "https://registry.yarnpkg.com/anymatch/-/anymatch-3.1.3.tgz#790c58b19ba1720a84205b57c618d5ad8524973e" + integrity sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw== + dependencies: + normalize-path "^3.0.0" + picomatch "^2.0.4" + +arg@^4.1.0: + version "4.1.3" + resolved "https://registry.yarnpkg.com/arg/-/arg-4.1.3.tgz#269fc7ad5b8e42cb63c896d5666017261c144089" + integrity sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA== + +argparse@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/argparse/-/argparse-2.0.1.tgz#246f50f3ca78a3240f6c997e8a9bd1eac49e4b38" + integrity sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q== + +array-back@^3.0.1, array-back@^3.1.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/array-back/-/array-back-3.1.0.tgz#b8859d7a508871c9a7b2cf42f99428f65e96bfb0" + integrity sha512-TkuxA4UCOvxuDK6NZYXCalszEzj+TLszyASooky+i742l9TqsOdYCMJJupxRic61hwquNtppB3hgcuq9SVSH1Q== + +array-back@^4.0.1, array-back@^4.0.2: + version "4.0.2" + resolved "https://registry.yarnpkg.com/array-back/-/array-back-4.0.2.tgz#8004e999a6274586beeb27342168652fdb89fa1e" + integrity sha512-NbdMezxqf94cnNfWLL7V/im0Ub+Anbb0IoZhvzie8+4HJ4nMQuzHuy49FkGYCJK2yAloZ3meiB6AVMClbrI1vg== + +array-buffer-byte-length@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/array-buffer-byte-length/-/array-buffer-byte-length-1.0.0.tgz#fabe8bc193fea865f317fe7807085ee0dee5aead" + integrity sha512-LPuwb2P+NrQw3XhxGc36+XSvuBPopovXYTR9Ew++Du9Yb/bx5AzBfrIsBoj0EZUifjQU+sHL21sseZ3jerWO/A== + dependencies: + call-bind "^1.0.2" + is-array-buffer "^3.0.1" + +array-includes@^3.1.7: + version "3.1.7" + resolved "https://registry.yarnpkg.com/array-includes/-/array-includes-3.1.7.tgz#8cd2e01b26f7a3086cbc87271593fe921c62abda" + integrity sha512-dlcsNBIiWhPkHdOEEKnehA+RNUWDc4UqFtnIXU4uuYDPtA4LDkr7qip2p0VvFAEXNDr0yWZ9PJyIRiGjRLQzwQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + get-intrinsic "^1.2.1" + is-string "^1.0.7" + +array-union@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/array-union/-/array-union-2.1.0.tgz#b798420adbeb1de828d84acd8a2e23d3efe85e8d" + integrity sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw== + +array.prototype.findlastindex@^1.2.3: + version "1.2.3" + resolved "https://registry.yarnpkg.com/array.prototype.findlastindex/-/array.prototype.findlastindex-1.2.3.tgz#b37598438f97b579166940814e2c0493a4f50207" + integrity sha512-LzLoiOMAxvy+Gd3BAq3B7VeIgPdo+Q8hthvKtXybMvRV0jrXfJM/t8mw7nNlpEcVlVUnCnM2KSX4XU5HmpodOA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + es-shim-unscopables "^1.0.0" + get-intrinsic "^1.2.1" + +array.prototype.flat@^1.3.2: + version "1.3.2" + resolved "https://registry.yarnpkg.com/array.prototype.flat/-/array.prototype.flat-1.3.2.tgz#1476217df8cff17d72ee8f3ba06738db5b387d18" + integrity sha512-djYB+Zx2vLewY8RWlNCUdHjDXs2XOgm602S9E7P/UpHgfeHL00cRiIF+IN/G/aUJ7kGPb6yO/ErDI5V2s8iycA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + es-shim-unscopables "^1.0.0" + +array.prototype.flatmap@^1.3.2: + version "1.3.2" + resolved "https://registry.yarnpkg.com/array.prototype.flatmap/-/array.prototype.flatmap-1.3.2.tgz#c9a7c6831db8e719d6ce639190146c24bbd3e527" + integrity sha512-Ewyx0c9PmpcsByhSW4r+9zDU7sGjFc86qf/kKtuSCRdhfbk0SNLLkaT5qvcHnRGgc5NP/ly/y+qkXkqONX54CQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + es-shim-unscopables "^1.0.0" + +arraybuffer.prototype.slice@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/arraybuffer.prototype.slice/-/arraybuffer.prototype.slice-1.0.2.tgz#98bd561953e3e74bb34938e77647179dfe6e9f12" + integrity sha512-yMBKppFur/fbHu9/6USUe03bZ4knMYiwFBcyiaXB8Go0qNehwX6inYPzK9U0NeQvGxKthcmHcaR8P5MStSRBAw== + dependencies: + array-buffer-byte-length "^1.0.0" + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + get-intrinsic "^1.2.1" + is-array-buffer "^3.0.2" + is-shared-array-buffer "^1.0.2" + +asn1@^0.2.6: + version "0.2.6" + resolved "https://registry.yarnpkg.com/asn1/-/asn1-0.2.6.tgz#0d3a7bb6e64e02a90c0303b31f292868ea09a08d" + integrity sha512-ix/FxPn0MDjeyJ7i/yoHGFt/EX6LyNbxSEhPPXODPL+KB0VPk86UYfL0lMdy+KCnv+fmvIzySwaK5COwqVbWTQ== + dependencies: + safer-buffer "~2.1.0" + +assertion-error@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/assertion-error/-/assertion-error-1.1.0.tgz#e60b6b0e8f301bd97e5375215bda406c85118c0b" + integrity sha512-jgsaNduz+ndvGyFt3uSuWqvy4lCnIJiovtouQN5JZHOKCS2QuhEdbcQHFhVksz2N2U9hXJo8odG7ETyWlEeuDw== + +ast-parents@^0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/ast-parents/-/ast-parents-0.0.1.tgz#508fd0f05d0c48775d9eccda2e174423261e8dd3" + integrity sha512-XHusKxKz3zoYk1ic8Un640joHbFMhbqneyoZfoKnEGtf2ey9Uh/IdpcQplODdO/kENaMIWsD0nJm4+wX3UNLHA== + +astral-regex@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/astral-regex/-/astral-regex-2.0.0.tgz#483143c567aeed4785759c0865786dc77d7d2e31" + integrity sha512-Z7tMw1ytTXt5jqMcOP+OQteU1VuNK9Y02uuJtKQ1Sv69jXQKKg5cibLwGJow8yzZP+eAc18EmLGPal0bp36rvQ== + +at-least-node@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/at-least-node/-/at-least-node-1.0.0.tgz#602cd4b46e844ad4effc92a8011a3c46e0238dc2" + integrity sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg== + +available-typed-arrays@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/available-typed-arrays/-/available-typed-arrays-1.0.5.tgz#92f95616501069d07d10edb2fc37d3e1c65123b7" + integrity sha512-DMD0KiN46eipeziST1LPP/STfDU0sufISXmjSgvVsoU2tqxctQeASejWcfNtxYKqETM1UxQ8sp2OrSBWpHY6sw== + +axios@^0.21.1: + version "0.21.4" + resolved "https://registry.yarnpkg.com/axios/-/axios-0.21.4.tgz#c67b90dc0568e5c1cf2b0b858c43ba28e2eda575" + integrity sha512-ut5vewkiu8jjGBdqpM44XxjuCjq9LAKeHVmoVfHVzy8eHgxxq8SbAVQNovDA8mVi05kP0Ea/n/UzcSHcTJQfNg== + dependencies: + follow-redirects "^1.14.0" + +balanced-match@^1.0.0: + version "1.0.2" + resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.2.tgz#e83e3a7e3f300b34cb9d87f615fa0cbf357690ee" + integrity sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw== + +base-x@^3.0.2: + version "3.0.9" + resolved "https://registry.yarnpkg.com/base-x/-/base-x-3.0.9.tgz#6349aaabb58526332de9f60995e548a53fe21320" + integrity sha512-H7JU6iBHTal1gp56aKoaa//YUxEaAOUiydvrV/pILqIHXTtqxSkATOnDA2u+jZ/61sD+L/412+7kzXRtWukhpQ== + dependencies: + safe-buffer "^5.0.1" + +base64-js@^1.3.1: + version "1.5.1" + resolved "https://registry.yarnpkg.com/base64-js/-/base64-js-1.5.1.tgz#1b1b440160a5bf7ad40b650f095963481903930a" + integrity sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA== + +bcrypt-pbkdf@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz#a4301d389b6a43f9b67ff3ca11a3f6637e360e9e" + integrity sha512-qeFIXtP4MSoi6NLqO12WfqARWWuCKi2Rn/9hJLEmtB5yTNr9DqFWkJRCf2qShWzPeAMRnOgCrq0sg/KLv5ES9w== + dependencies: + tweetnacl "^0.14.3" + +bech32@1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/bech32/-/bech32-1.1.4.tgz#e38c9f37bf179b8eb16ae3a772b40c356d4832e9" + integrity sha512-s0IrSOzLlbvX7yp4WBfPITzpAU8sqQcpsmwXDiKwrG4r491vwCO/XpejasRNl0piBMe/DvP4Tz0mIS/X1DPJBQ== + +big-integer@^1.6.44: + version "1.6.51" + resolved "https://registry.yarnpkg.com/big-integer/-/big-integer-1.6.51.tgz#0df92a5d9880560d3ff2d5fd20245c889d130686" + integrity sha512-GPEid2Y9QU1Exl1rpO9B2IPJGHPSupF5GnVIP0blYvNOMer2bTvSWs1jGOUg04hTmu67nmLsQ9TBo1puaotBHg== + +bigint-crypto-utils@^3.0.23: + version "3.3.0" + resolved "https://registry.yarnpkg.com/bigint-crypto-utils/-/bigint-crypto-utils-3.3.0.tgz#72ad00ae91062cf07f2b1def9594006c279c1d77" + integrity sha512-jOTSb+drvEDxEq6OuUybOAv/xxoh3cuYRUIPyu8sSHQNKM303UQ2R1DAo45o1AkcIXw6fzbaFI1+xGGdaXs2lg== + +binary-extensions@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/binary-extensions/-/binary-extensions-2.2.0.tgz#75f502eeaf9ffde42fc98829645be4ea76bd9e2d" + integrity sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA== + +bl@^1.0.0: + version "1.2.3" + resolved "https://registry.yarnpkg.com/bl/-/bl-1.2.3.tgz#1e8dd80142eac80d7158c9dccc047fb620e035e7" + integrity sha512-pvcNpa0UU69UT341rO6AYy4FVAIkUHuZXRIWbq+zHnsVcRzDDjIAhGuuYoi0d//cwIwtt4pkpKycWEfjdV+vww== + dependencies: + readable-stream "^2.3.5" + safe-buffer "^5.1.1" + +bl@^4.0.3: + version "4.1.0" + resolved "https://registry.yarnpkg.com/bl/-/bl-4.1.0.tgz#451535264182bec2fbbc83a62ab98cf11d9f7b3a" + integrity sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w== + dependencies: + buffer "^5.5.0" + inherits "^2.0.4" + readable-stream "^3.4.0" + +blakejs@^1.1.0: + version "1.2.1" + resolved "https://registry.yarnpkg.com/blakejs/-/blakejs-1.2.1.tgz#5057e4206eadb4a97f7c0b6e197a505042fc3814" + integrity sha512-QXUSXI3QVc/gJME0dBpXrag1kbzOqCjCX8/b54ntNyW6sjtoqxqRk3LTmXzaJoh71zMsDCjM+47jS7XiwN/+fQ== + +bn-str-256@^1.9.1: + version "1.9.1" + resolved "https://registry.yarnpkg.com/bn-str-256/-/bn-str-256-1.9.1.tgz#898cebee70a3edc3968f97b4cebbc4771025aa82" + integrity sha512-u3muv3WO5sYv9nUQsPnDGLg731yNt/MOlKPK5pmBVqClcl7tY97tyfKxw8ed44HVrpi+7dkgJgQpbXP47a3GoQ== + dependencies: + decimal.js-light "^2.5.0" + lodash "^4.17.11" + +bn.js@^4.11.0, bn.js@^4.11.8, bn.js@^4.11.9: + version "4.12.0" + resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-4.12.0.tgz#775b3f278efbb9718eec7361f483fb36fbbfea88" + integrity sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA== + +bn.js@^5.2.0, bn.js@^5.2.1: + version "5.2.1" + resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-5.2.1.tgz#0bc527a6a0d18d0aa8d5b0538ce4a77dccfa7b70" + integrity sha512-eXRvHzWyYPBuB4NBy0cmYQjGitUrtqwbvlzP3G6VFnNRbsZQIxQ10PbKKHt8gZ/HW/D/747aDl+QkDqg3KQLMQ== + +bplist-parser@^0.2.0: + version "0.2.0" + resolved "https://registry.yarnpkg.com/bplist-parser/-/bplist-parser-0.2.0.tgz#43a9d183e5bf9d545200ceac3e712f79ebbe8d0e" + integrity sha512-z0M+byMThzQmD9NILRniCUXYsYpjwnlO8N5uCFaCqIOpqRsJCrQL9NK3JsD67CN5a08nF5oIL2bD6loTdHOuKw== + dependencies: + big-integer "^1.6.44" + +brace-expansion@^1.1.7: + version "1.1.11" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd" + integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA== + dependencies: + balanced-match "^1.0.0" + concat-map "0.0.1" + +brace-expansion@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-2.0.1.tgz#1edc459e0f0c548486ecf9fc99f2221364b9a0ae" + integrity sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA== + dependencies: + balanced-match "^1.0.0" + +braces@^3.0.2, braces@~3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/braces/-/braces-3.0.2.tgz#3454e1a462ee8d599e236df336cd9ea4f8afe107" + integrity sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A== + dependencies: + fill-range "^7.0.1" + +brorand@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/brorand/-/brorand-1.1.0.tgz#12c25efe40a45e3c323eb8675a0a0ce57b22371f" + integrity sha512-cKV8tMCEpQs4hK/ik71d6LrPOnpkpGBR0wzxqr68g2m/LB2GxVYQroAjMJZRVM1Y4BCjCKc3vAamxSzOY2RP+w== + +browser-level@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/browser-level/-/browser-level-1.0.1.tgz#36e8c3183d0fe1c405239792faaab5f315871011" + integrity sha512-XECYKJ+Dbzw0lbydyQuJzwNXtOpbMSq737qxJN11sIRTErOMShvDpbzTlgju7orJKvx4epULolZAuJGLzCmWRQ== + dependencies: + abstract-level "^1.0.2" + catering "^2.1.1" + module-error "^1.0.2" + run-parallel-limit "^1.1.0" + +browser-stdout@1.3.1: + version "1.3.1" + resolved "https://registry.yarnpkg.com/browser-stdout/-/browser-stdout-1.3.1.tgz#baa559ee14ced73452229bad7326467c61fabd60" + integrity sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw== + +browserify-aes@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/browserify-aes/-/browserify-aes-1.2.0.tgz#326734642f403dabc3003209853bb70ad428ef48" + integrity sha512-+7CHXqGuspUn/Sl5aO7Ea0xWGAtETPXNSAjHo48JfLdPWcMng33Xe4znFvQweqc/uzk5zSOI3H52CYnjCfb5hA== + dependencies: + buffer-xor "^1.0.3" + cipher-base "^1.0.0" + create-hash "^1.1.0" + evp_bytestokey "^1.0.3" + inherits "^2.0.1" + safe-buffer "^5.0.1" + +bs58@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/bs58/-/bs58-4.0.1.tgz#be161e76c354f6f788ae4071f63f34e8c4f0a42a" + integrity sha512-Ok3Wdf5vOIlBrgCvTq96gBkJw+JUEzdBgyaza5HLtPm7yTHkjRy8+JzNyHF7BHa0bNWOQIp3m5YF0nnFcOIKLw== + dependencies: + base-x "^3.0.2" + +bs58check@^2.1.2: + version "2.1.2" + resolved "https://registry.yarnpkg.com/bs58check/-/bs58check-2.1.2.tgz#53b018291228d82a5aa08e7d796fdafda54aebfc" + integrity sha512-0TS1jicxdU09dwJMNZtVAfzPi6Q6QeN0pM1Fkzrjn+XYHvzMKPU3pHVpva+769iNVSfIYWf7LJ6WR+BuuMf8cA== + dependencies: + bs58 "^4.0.0" + create-hash "^1.1.0" + safe-buffer "^5.1.2" + +buffer-alloc-unsafe@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/buffer-alloc-unsafe/-/buffer-alloc-unsafe-1.1.0.tgz#bd7dc26ae2972d0eda253be061dba992349c19f0" + integrity sha512-TEM2iMIEQdJ2yjPJoSIsldnleVaAk1oW3DBVUykyOLsEsFmEc9kn+SFFPz+gl54KQNxlDnAwCXosOS9Okx2xAg== + +buffer-alloc@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/buffer-alloc/-/buffer-alloc-1.2.0.tgz#890dd90d923a873e08e10e5fd51a57e5b7cce0ec" + integrity sha512-CFsHQgjtW1UChdXgbyJGtnm+O/uLQeZdtbDo8mfUgYXCHSM1wgrVxXm6bSyrUuErEb+4sYVGCzASBRot7zyrow== + dependencies: + buffer-alloc-unsafe "^1.1.0" + buffer-fill "^1.0.0" + +buffer-fill@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/buffer-fill/-/buffer-fill-1.0.0.tgz#f8f78b76789888ef39f205cd637f68e702122b2c" + integrity sha512-T7zexNBwiiaCOGDg9xNX9PBmjrubblRkENuptryuI64URkXDFum9il/JGL8Lm8wYfAXpredVXXZz7eMHilimiQ== + +buffer-from@^1.0.0: + version "1.1.2" + resolved "https://registry.yarnpkg.com/buffer-from/-/buffer-from-1.1.2.tgz#2b146a6fd72e80b4f55d255f35ed59a3a9a41bd5" + integrity sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ== + +buffer-xor@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/buffer-xor/-/buffer-xor-1.0.3.tgz#26e61ed1422fb70dd42e6e36729ed51d855fe8d9" + integrity sha512-571s0T7nZWK6vB67HI5dyUF7wXiNcfaPPPTl6zYCNApANjIvYJTg7hlud/+cJpdAhS7dVzqMLmfhfHR3rAcOjQ== + +buffer@^5.5.0: + version "5.7.1" + resolved "https://registry.yarnpkg.com/buffer/-/buffer-5.7.1.tgz#ba62e7c13133053582197160851a8f648e99eed0" + integrity sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ== + dependencies: + base64-js "^1.3.1" + ieee754 "^1.1.13" + +buffer@^6.0.3: + version "6.0.3" + resolved "https://registry.yarnpkg.com/buffer/-/buffer-6.0.3.tgz#2ace578459cc8fbe2a70aaa8f52ee63b6a74c6c6" + integrity sha512-FTiCpNxtwiZZHEZbcbTIcZjERVICn9yq/pDFkTl95/AxzD1naBctN7YO68riM/gLSDY7sdrMby8hofADYuuqOA== + dependencies: + base64-js "^1.3.1" + ieee754 "^1.2.1" + +buildcheck@~0.0.6: + version "0.0.6" + resolved "https://registry.yarnpkg.com/buildcheck/-/buildcheck-0.0.6.tgz#89aa6e417cfd1e2196e3f8fe915eb709d2fe4238" + integrity sha512-8f9ZJCUXyT1M35Jx7MkBgmBMo3oHTTBIPLiY9xyL0pl3T5RwcPEY8cUHr5LBNfu/fk6c2T4DJZuVM/8ZZT2D2A== + +bundle-name@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/bundle-name/-/bundle-name-3.0.0.tgz#ba59bcc9ac785fb67ccdbf104a2bf60c099f0e1a" + integrity sha512-PKA4BeSvBpQKQ8iPOGCSiell+N8P+Tf1DlwqmYhpe2gAhKPHn8EYOxVT+ShuGmhg8lN8XiSlS80yiExKXrURlw== + dependencies: + run-applescript "^5.0.0" + +bytes@3.1.2: + version "3.1.2" + resolved "https://registry.yarnpkg.com/bytes/-/bytes-3.1.2.tgz#8b0beeb98605adf1b128fa4386403c009e0221a5" + integrity sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg== + +call-bind@^1.0.0, call-bind@^1.0.2, call-bind@^1.0.4, call-bind@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/call-bind/-/call-bind-1.0.5.tgz#6fa2b7845ce0ea49bf4d8b9ef64727a2c2e2e513" + integrity sha512-C3nQxfFZxFRVoJoGKKI8y3MOEo129NQ+FgQ08iye+Mk4zNZZGdjfs06bVTr+DBSlA66Q2VEcMki/cUCP4SercQ== + dependencies: + function-bind "^1.1.2" + get-intrinsic "^1.2.1" + set-function-length "^1.1.1" + +callsites@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/callsites/-/callsites-3.1.0.tgz#b3630abd8943432f54b3f0519238e33cd7df2f73" + integrity sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ== + +camelcase@^6.0.0: + version "6.3.0" + resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-6.3.0.tgz#5685b95eb209ac9c0c177467778c9c84df58ba9a" + integrity sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA== + +case@^1.6.3: + version "1.6.3" + resolved "https://registry.yarnpkg.com/case/-/case-1.6.3.tgz#0a4386e3e9825351ca2e6216c60467ff5f1ea1c9" + integrity sha512-mzDSXIPaFwVDvZAHqZ9VlbyF4yyXRuX6IvB06WvPYkqJVO24kX1PPhv9bfpKNFZyxYFmmgo03HUiD8iklmJYRQ== + +catering@^2.1.0, catering@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/catering/-/catering-2.1.1.tgz#66acba06ed5ee28d5286133982a927de9a04b510" + integrity sha512-K7Qy8O9p76sL3/3m7/zLKbRkyOlSZAgzEaLhyj2mXS8PsCud2Eo4hAb8aLtZqHh0QGqLcb9dlJSu6lHRVENm1w== + +chai-as-promised@^7.1.1: + version "7.1.1" + resolved "https://registry.yarnpkg.com/chai-as-promised/-/chai-as-promised-7.1.1.tgz#08645d825deb8696ee61725dbf590c012eb00ca0" + integrity sha512-azL6xMoi+uxu6z4rhWQ1jbdUhOMhis2PvscD/xjLqNMkv3BPPp2JyyuTHOrf9BOosGpNQ11v6BKv/g57RXbiaA== + dependencies: + check-error "^1.0.2" + +chai@^4.3.6: + version "4.3.8" + resolved "https://registry.yarnpkg.com/chai/-/chai-4.3.8.tgz#40c59718ad6928da6629c70496fe990b2bb5b17c" + integrity sha512-vX4YvVVtxlfSZ2VecZgFUTU5qPCYsobVI2O9FmwEXBhDigYGQA6jRXCycIs1yJnnWbZ6/+a2zNIF5DfVCcJBFQ== + dependencies: + assertion-error "^1.1.0" + check-error "^1.0.2" + deep-eql "^4.1.2" + get-func-name "^2.0.0" + loupe "^2.3.1" + pathval "^1.1.1" + type-detect "^4.0.5" + +chalk@4.1.2, chalk@^4.0.0, chalk@^4.1.0, chalk@^4.1.2: + version "4.1.2" + resolved "https://registry.yarnpkg.com/chalk/-/chalk-4.1.2.tgz#aac4e2b7734a740867aeb16bf02aad556a1e7a01" + integrity sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA== + dependencies: + ansi-styles "^4.1.0" + supports-color "^7.1.0" + +chalk@^2.4.1, chalk@^2.4.2: + version "2.4.2" + resolved "https://registry.yarnpkg.com/chalk/-/chalk-2.4.2.tgz#cd42541677a54333cf541a49108c1432b44c9424" + integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ== + dependencies: + ansi-styles "^3.2.1" + escape-string-regexp "^1.0.5" + supports-color "^5.3.0" + +check-error@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/check-error/-/check-error-1.0.2.tgz#574d312edd88bb5dd8912e9286dd6c0aed4aac82" + integrity sha512-BrgHpW9NURQgzoNyjfq0Wu6VFO6D7IZEmJNdtgNqpzGG8RuNFHt2jQxWlAs4HMe119chBnv+34syEZtc6IhLtA== + +chokidar@3.5.3, chokidar@^3.4.0: + version "3.5.3" + resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-3.5.3.tgz#1cf37c8707b932bd1af1ae22c0432e2acd1903bd" + integrity sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw== + dependencies: + anymatch "~3.1.2" + braces "~3.0.2" + glob-parent "~5.1.2" + is-binary-path "~2.1.0" + is-glob "~4.0.1" + normalize-path "~3.0.0" + readdirp "~3.6.0" + optionalDependencies: + fsevents "~2.3.2" + +chownr@^1.0.1, chownr@^1.1.1: + version "1.1.4" + resolved "https://registry.yarnpkg.com/chownr/-/chownr-1.1.4.tgz#6fc9d7b42d32a583596337666e7d08084da2cc6b" + integrity sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg== + +ci-info@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/ci-info/-/ci-info-2.0.0.tgz#67a9e964be31a51e15e5010d58e6f12834002f46" + integrity sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ== + +cipher-base@^1.0.0, cipher-base@^1.0.1, cipher-base@^1.0.3: + version "1.0.4" + resolved "https://registry.yarnpkg.com/cipher-base/-/cipher-base-1.0.4.tgz#8760e4ecc272f4c363532f926d874aae2c1397de" + integrity sha512-Kkht5ye6ZGmwv40uUDZztayT2ThLQGfnj/T71N/XzeZeo3nf8foyW7zGTsPYkEya3m5f3cAypH+qe7YOrM1U2Q== + dependencies: + inherits "^2.0.1" + safe-buffer "^5.0.1" + +classic-level@^1.2.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/classic-level/-/classic-level-1.3.0.tgz#5e36680e01dc6b271775c093f2150844c5edd5c8" + integrity sha512-iwFAJQYtqRTRM0F6L8h4JCt00ZSGdOyqh7yVrhhjrOpFhmBjNlRUey64MCiyo6UmQHMJ+No3c81nujPv+n9yrg== + dependencies: + abstract-level "^1.0.2" + catering "^2.1.0" + module-error "^1.0.1" + napi-macros "^2.2.2" + node-gyp-build "^4.3.0" + +clean-stack@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/clean-stack/-/clean-stack-2.2.0.tgz#ee8472dbb129e727b31e8a10a427dee9dfe4008b" + integrity sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A== + +cliui@^7.0.2: + version "7.0.4" + resolved "https://registry.yarnpkg.com/cliui/-/cliui-7.0.4.tgz#a0265ee655476fc807aea9df3df8df7783808b4f" + integrity sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ== + dependencies: + string-width "^4.2.0" + strip-ansi "^6.0.0" + wrap-ansi "^7.0.0" + +code-block-writer@^12.0.0: + version "12.0.0" + resolved "https://registry.yarnpkg.com/code-block-writer/-/code-block-writer-12.0.0.tgz#4dd58946eb4234105aff7f0035977b2afdc2a770" + integrity sha512-q4dMFMlXtKR3XNBHyMHt/3pwYNA69EDk00lloMOaaUMKPUXBw6lpXtbu3MMVG6/uOihGnRDOlkyqsONEUj60+w== + +color-convert@^1.9.0: + version "1.9.3" + resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-1.9.3.tgz#bb71850690e1f136567de629d2d5471deda4c1e8" + integrity sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg== + dependencies: + color-name "1.1.3" + +color-convert@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-2.0.1.tgz#72d3a68d598c9bdb3af2ad1e84f21d896abd4de3" + integrity sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ== + dependencies: + color-name "~1.1.4" + +color-name@1.1.3: + version "1.1.3" + resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.3.tgz#a7d0558bd89c42f795dd42328f740831ca53bc25" + integrity sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw== + +color-name@~1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.4.tgz#c2a09a87acbde69543de6f63fa3995c826c536a2" + integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA== + +command-exists@^1.2.8: + version "1.2.9" + resolved "https://registry.yarnpkg.com/command-exists/-/command-exists-1.2.9.tgz#c50725af3808c8ab0260fd60b01fbfa25b954f69" + integrity sha512-LTQ/SGc+s0Xc0Fu5WaKnR0YiygZkm9eKFvyS+fRsU7/ZWFF8ykFM6Pc9aCVf1+xasOOZpO3BAVgVrKvsqKHV7w== + +command-line-args@^5.1.1: + version "5.2.1" + resolved "https://registry.yarnpkg.com/command-line-args/-/command-line-args-5.2.1.tgz#c44c32e437a57d7c51157696893c5909e9cec42e" + integrity sha512-H4UfQhZyakIjC74I9d34fGYDwk3XpSr17QhEd0Q3I9Xq1CETHo4Hcuo87WyWHpAF1aSLjLRf5lD9ZGX2qStUvg== + dependencies: + array-back "^3.1.0" + find-replace "^3.0.0" + lodash.camelcase "^4.3.0" + typical "^4.0.0" + +command-line-usage@^6.1.0: + version "6.1.3" + resolved "https://registry.yarnpkg.com/command-line-usage/-/command-line-usage-6.1.3.tgz#428fa5acde6a838779dfa30e44686f4b6761d957" + integrity sha512-sH5ZSPr+7UStsloltmDh7Ce5fb8XPlHyoPzTpyyMuYCtervL65+ubVZ6Q61cFtFl62UyJlc8/JwERRbAFPUqgw== + dependencies: + array-back "^4.0.2" + chalk "^2.4.2" + table-layout "^1.0.2" + typical "^5.2.0" + +commander@3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/commander/-/commander-3.0.2.tgz#6837c3fb677ad9933d1cfba42dd14d5117d6b39e" + integrity sha512-Gar0ASD4BDyKC4hl4DwHqDrmvjoxWKZigVnAbn5H1owvm4CxCPdb0HQDehwNYMJpla5+M2tPmPARzhtYuwpHow== + +commander@^10.0.0: + version "10.0.1" + resolved "https://registry.yarnpkg.com/commander/-/commander-10.0.1.tgz#881ee46b4f77d1c1dccc5823433aa39b022cbe06" + integrity sha512-y4Mg2tXshplEbSGzx7amzPwKKOCGuoSRP/CjEdwwk0FOGlUbq6lKuoyDZTNZkmxHdJtp54hdfY/JUrdL7Xfdug== + +commander@^2.19.0: + version "2.20.3" + resolved "https://registry.yarnpkg.com/commander/-/commander-2.20.3.tgz#fd485e84c03eb4881c20722ba48035e8531aeb33" + integrity sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ== + +commander@^9.4.1: + version "9.5.0" + resolved "https://registry.yarnpkg.com/commander/-/commander-9.5.0.tgz#bc08d1eb5cedf7ccb797a96199d41c7bc3e60d30" + integrity sha512-KRs7WVDKg86PWiuAqhDrAQnTXZKraVcCc6vFdL14qrZ/DcWwuRo7VoiYXalXO7S5GKpqYiVEwCbgFDfxNHKJBQ== + +commander@~9.4.1: + version "9.4.1" + resolved "https://registry.yarnpkg.com/commander/-/commander-9.4.1.tgz#d1dd8f2ce6faf93147295c0df13c7c21141cfbdd" + integrity sha512-5EEkTNyHNGFPD2H+c/dXXfQZYa/scCKasxWcXJaWnNJ99pnQN9Vnmqow+p+PlFPE63Q6mThaZws1T+HxfpgtPw== + +concat-map@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" + integrity sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg== + +concat-stream@~1.6.2: + version "1.6.2" + resolved "https://registry.yarnpkg.com/concat-stream/-/concat-stream-1.6.2.tgz#904bdf194cd3122fc675c77fc4ac3d4ff0fd1a34" + integrity sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw== + dependencies: + buffer-from "^1.0.0" + inherits "^2.0.3" + readable-stream "^2.2.2" + typedarray "^0.0.6" + +cookie@^0.4.1: + version "0.4.2" + resolved "https://registry.yarnpkg.com/cookie/-/cookie-0.4.2.tgz#0e41f24de5ecf317947c82fc789e06a884824432" + integrity sha512-aSWTXFzaKWkvHO1Ny/s+ePFpvKsPnjc551iI41v3ny/ow6tBG5Vd+FuqGNhh1LxOmVzOlGUriIlOaokOvhaStA== + +core-util-is@~1.0.0: + version "1.0.3" + resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.3.tgz#a6042d3634c2b27e9328f837b965fac83808db85" + integrity sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ== + +cosmiconfig@^8.0.0: + version "8.3.6" + resolved "https://registry.yarnpkg.com/cosmiconfig/-/cosmiconfig-8.3.6.tgz#060a2b871d66dba6c8538ea1118ba1ac16f5fae3" + integrity sha512-kcZ6+W5QzcJ3P1Mt+83OUv/oHFqZHIx8DuxG6eZ5RGMERoLqp4BuGjhHLYGK+Kf5XVkQvqBSmAy/nGWN3qDgEA== + dependencies: + import-fresh "^3.3.0" + js-yaml "^4.1.0" + parse-json "^5.2.0" + path-type "^4.0.0" + +cpu-features@~0.0.8: + version "0.0.9" + resolved "https://registry.yarnpkg.com/cpu-features/-/cpu-features-0.0.9.tgz#5226b92f0f1c63122b0a3eb84cb8335a4de499fc" + integrity sha512-AKjgn2rP2yJyfbepsmLfiYcmtNn/2eUvocUyM/09yB0YDiz39HteK/5/T4Onf0pmdYDMgkBoGvRLvEguzyL7wQ== + dependencies: + buildcheck "~0.0.6" + nan "^2.17.0" + +crc-32@^1.2.0: + version "1.2.2" + resolved "https://registry.yarnpkg.com/crc-32/-/crc-32-1.2.2.tgz#3cad35a934b8bf71f25ca524b6da51fb7eace2ff" + integrity sha512-ROmzCKrTnOwybPcJApAA6WBWij23HVfGVNKqqrZpuyZOHqK2CwHSvpGuyt/UNNvaIjEd8X5IFGp4Mh+Ie1IHJQ== + +create-hash@^1.1.0, create-hash@^1.1.2, create-hash@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/create-hash/-/create-hash-1.2.0.tgz#889078af11a63756bcfb59bd221996be3a9ef196" + integrity sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg== + dependencies: + cipher-base "^1.0.1" + inherits "^2.0.1" + md5.js "^1.3.4" + ripemd160 "^2.0.1" + sha.js "^2.4.0" + +create-hmac@^1.1.4, create-hmac@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/create-hmac/-/create-hmac-1.1.7.tgz#69170c78b3ab957147b2b8b04572e47ead2243ff" + integrity sha512-MJG9liiZ+ogc4TzUwuvbER1JRdgvUFSB5+VR/g5h82fGaIRWMWddtKBHi7/sVhfjQZ6SehlyhvQYrcYkaUIpLg== + dependencies: + cipher-base "^1.0.3" + create-hash "^1.1.0" + inherits "^2.0.1" + ripemd160 "^2.0.0" + safe-buffer "^5.0.1" + sha.js "^2.4.8" + +create-require@^1.1.0: + version "1.1.1" + resolved "https://registry.yarnpkg.com/create-require/-/create-require-1.1.1.tgz#c1d7e8f1e5f6cfc9ff65f9cd352d37348756c333" + integrity sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ== + +cross-spawn@^7.0.2, cross-spawn@^7.0.3: + version "7.0.3" + resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.3.tgz#f73a85b9d5d41d045551c177e2882d4ac85728a6" + integrity sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w== + dependencies: + path-key "^3.1.0" + shebang-command "^2.0.0" + which "^2.0.1" + +debug@4, debug@4.3.4, debug@^4.1.1, debug@^4.3.1, debug@^4.3.2, debug@^4.3.3, debug@^4.3.4: + version "4.3.4" + resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.4.tgz#1319f6579357f2338d3337d2cdd4914bb5dcc865" + integrity sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ== + dependencies: + ms "2.1.2" + +debug@^3.2.6, debug@^3.2.7: + version "3.2.7" + resolved "https://registry.yarnpkg.com/debug/-/debug-3.2.7.tgz#72580b7e9145fb39b6676f9c5e5fb100b934179a" + integrity sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ== + dependencies: + ms "^2.1.1" + +decamelize@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-4.0.0.tgz#aa472d7bf660eb15f3494efd531cab7f2a709837" + integrity sha512-9iE1PgSik9HeIIw2JO94IidnE3eBoQrFJ3w7sFuzSX4DpmZ3v5sZpUiV5Swcf6mQEF+Y0ru8Neo+p+nyh2J+hQ== + +decimal.js-light@^2.5.0: + version "2.5.1" + resolved "https://registry.yarnpkg.com/decimal.js-light/-/decimal.js-light-2.5.1.tgz#134fd32508f19e208f4fb2f8dac0d2626a867934" + integrity sha512-qIMFpTMZmny+MMIitAB6D7iVPEorVw6YQRWkvarTkT4tBeSLLiHzcwj6q0MmYSFCiVpiqPJTJEYIrpcPzVEIvg== + +deep-eql@^4.0.1, deep-eql@^4.1.2: + version "4.1.3" + resolved "https://registry.yarnpkg.com/deep-eql/-/deep-eql-4.1.3.tgz#7c7775513092f7df98d8df9996dd085eb668cc6d" + integrity sha512-WaEtAOpRA1MQ0eohqZjpGD8zdI0Ovsm8mmFhaDN8dvDZzyoUMcYDnf5Y6iu7HTXxf8JDS23qWa4a+hKCDyOPzw== + dependencies: + type-detect "^4.0.0" + +deep-extend@^0.6.0, deep-extend@~0.6.0: + version "0.6.0" + resolved "https://registry.yarnpkg.com/deep-extend/-/deep-extend-0.6.0.tgz#c4fa7c95404a17a9c3e8ca7e1537312b736330ac" + integrity sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA== + +deep-is@^0.1.3: + version "0.1.4" + resolved "https://registry.yarnpkg.com/deep-is/-/deep-is-0.1.4.tgz#a6f2dce612fadd2ef1f519b73551f17e85199831" + integrity sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ== + +default-browser-id@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/default-browser-id/-/default-browser-id-3.0.0.tgz#bee7bbbef1f4e75d31f98f4d3f1556a14cea790c" + integrity sha512-OZ1y3y0SqSICtE8DE4S8YOE9UZOJ8wO16fKWVP5J1Qz42kV9jcnMVFrEE/noXb/ss3Q4pZIH79kxofzyNNtUNA== + dependencies: + bplist-parser "^0.2.0" + untildify "^4.0.0" + +default-browser@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/default-browser/-/default-browser-4.0.0.tgz#53c9894f8810bf86696de117a6ce9085a3cbc7da" + integrity sha512-wX5pXO1+BrhMkSbROFsyxUm0i/cJEScyNhA4PPxc41ICuv05ZZB/MX28s8aZx6xjmatvebIapF6hLEKEcpneUA== + dependencies: + bundle-name "^3.0.0" + default-browser-id "^3.0.0" + execa "^7.1.1" + titleize "^3.0.0" + +define-data-property@^1.0.1, define-data-property@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/define-data-property/-/define-data-property-1.1.1.tgz#c35f7cd0ab09883480d12ac5cb213715587800b3" + integrity sha512-E7uGkTzkk1d0ByLeSc6ZsFS79Axg+m1P/VsgYsxHgiuc3tFSj+MjMIwe90FC4lOAZzNBdY7kkO2P2wKdsQ1vgQ== + dependencies: + get-intrinsic "^1.2.1" + gopd "^1.0.1" + has-property-descriptors "^1.0.0" + +define-lazy-prop@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/define-lazy-prop/-/define-lazy-prop-3.0.0.tgz#dbb19adfb746d7fc6d734a06b72f4a00d021255f" + integrity sha512-N+MeXYoqr3pOgn8xfyRPREN7gHakLYjhsHhWGT3fWAiL4IkAt0iDw14QiiEm2bE30c5XX5q0FtAA3CK5f9/BUg== + +define-properties@^1.1.3, define-properties@^1.1.4, define-properties@^1.2.0: + version "1.2.1" + resolved "https://registry.yarnpkg.com/define-properties/-/define-properties-1.2.1.tgz#10781cc616eb951a80a034bafcaa7377f6af2b6c" + integrity sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg== + dependencies: + define-data-property "^1.0.1" + has-property-descriptors "^1.0.0" + object-keys "^1.1.1" + +depd@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/depd/-/depd-2.0.0.tgz#b696163cc757560d09cf22cc8fad1571b79e76df" + integrity sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw== + +diff@5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/diff/-/diff-5.0.0.tgz#7ed6ad76d859d030787ec35855f5b1daf31d852b" + integrity sha512-/VTCrvm5Z0JGty/BWHljh+BAiw3IK+2j87NGMu8Nwc/f48WoDAC395uomO9ZD117ZOBaHmkX1oyLvkVM/aIT3w== + +diff@^4.0.1: + version "4.0.2" + resolved "https://registry.yarnpkg.com/diff/-/diff-4.0.2.tgz#60f3aecb89d5fae520c11aa19efc2bb982aade7d" + integrity sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A== + +dir-glob@^3.0.1: + version "3.0.1" + resolved "https://registry.yarnpkg.com/dir-glob/-/dir-glob-3.0.1.tgz#56dbf73d992a4a93ba1584f4534063fd2e41717f" + integrity sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA== + dependencies: + path-type "^4.0.0" + +docker-modem@^1.0.8: + version "1.0.9" + resolved "https://registry.yarnpkg.com/docker-modem/-/docker-modem-1.0.9.tgz#a1f13e50e6afb6cf3431b2d5e7aac589db6aaba8" + integrity sha512-lVjqCSCIAUDZPAZIeyM125HXfNvOmYYInciphNrLrylUtKyW66meAjSPXWchKVzoIYZx69TPnAepVSSkeawoIw== + dependencies: + JSONStream "1.3.2" + debug "^3.2.6" + readable-stream "~1.0.26-4" + split-ca "^1.0.0" + +docker-modem@^3.0.0: + version "3.0.8" + resolved "https://registry.yarnpkg.com/docker-modem/-/docker-modem-3.0.8.tgz#ef62c8bdff6e8a7d12f0160988c295ea8705e77a" + integrity sha512-f0ReSURdM3pcKPNS30mxOHSbaFLcknGmQjwSfmbcdOw1XWKXVhukM3NJHhr7NpY9BIyyWQb0EBo3KQvvuU5egQ== + dependencies: + debug "^4.1.1" + readable-stream "^3.5.0" + split-ca "^1.0.1" + ssh2 "^1.11.0" + +dockerode@^2.5.8: + version "2.5.8" + resolved "https://registry.yarnpkg.com/dockerode/-/dockerode-2.5.8.tgz#1b661e36e1e4f860e25f56e0deabe9f87f1d0acc" + integrity sha512-+7iOUYBeDTScmOmQqpUYQaE7F4vvIt6+gIZNHWhqAQEI887tiPFB9OvXI/HzQYqfUNvukMK+9myLW63oTJPZpw== + dependencies: + concat-stream "~1.6.2" + docker-modem "^1.0.8" + tar-fs "~1.16.3" + +dockerode@^3.3.4: + version "3.3.5" + resolved "https://registry.yarnpkg.com/dockerode/-/dockerode-3.3.5.tgz#7ae3f40f2bec53ae5e9a741ce655fff459745629" + integrity sha512-/0YNa3ZDNeLr/tSckmD69+Gq+qVNhvKfAHNeZJBnp7EOP6RGKV8ORrJHkUn20So5wU+xxT7+1n5u8PjHbfjbSA== + dependencies: + "@balena/dockerignore" "^1.0.2" + docker-modem "^3.0.0" + tar-fs "~2.0.1" + +doctrine@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-2.1.0.tgz#5cd01fc101621b42c4cd7f5d1a66243716d3f39d" + integrity sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw== + dependencies: + esutils "^2.0.2" + +doctrine@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-3.0.0.tgz#addebead72a6574db783639dc87a121773973961" + integrity sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w== + dependencies: + esutils "^2.0.2" + +elliptic@6.5.4, elliptic@^6.5.2, elliptic@^6.5.4: + version "6.5.4" + resolved "https://registry.yarnpkg.com/elliptic/-/elliptic-6.5.4.tgz#da37cebd31e79a1367e941b592ed1fbebd58abbb" + integrity sha512-iLhC6ULemrljPZb+QutR5TQGB+pdW6KGD5RSegS+8sorOZT+rdQFbsQFJgvN3eRqNALqJer4oQ16YvJHlU8hzQ== + dependencies: + bn.js "^4.11.9" + brorand "^1.1.0" + hash.js "^1.0.0" + hmac-drbg "^1.0.1" + inherits "^2.0.4" + minimalistic-assert "^1.0.1" + minimalistic-crypto-utils "^1.0.1" + +emoji-regex@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-8.0.0.tgz#e818fd69ce5ccfcb404594f842963bf53164cc37" + integrity sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A== + +end-of-stream@^1.0.0, end-of-stream@^1.1.0, end-of-stream@^1.4.1: + version "1.4.4" + resolved "https://registry.yarnpkg.com/end-of-stream/-/end-of-stream-1.4.4.tgz#5ae64a5f45057baf3626ec14da0ca5e4b2431eb0" + integrity sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q== + dependencies: + once "^1.4.0" + +enhanced-resolve@^5.12.0: + version "5.15.0" + resolved "https://registry.yarnpkg.com/enhanced-resolve/-/enhanced-resolve-5.15.0.tgz#1af946c7d93603eb88e9896cee4904dc012e9c35" + integrity sha512-LXYT42KJ7lpIKECr2mAXIaMldcNCh/7E0KBKOu4KSfkHmP+mZmSs+8V5gBAqisWBy0OO4W5Oyys0GO1Y8KtdKg== + dependencies: + graceful-fs "^4.2.4" + tapable "^2.2.0" + +enquirer@^2.3.0: + version "2.4.1" + resolved "https://registry.yarnpkg.com/enquirer/-/enquirer-2.4.1.tgz#93334b3fbd74fc7097b224ab4a8fb7e40bf4ae56" + integrity sha512-rRqJg/6gd538VHvR3PSrdRBb/1Vy2YfzHqzvbhGIQpDRKIa4FgV/54b5Q1xYSxOOwKvjXweS26E0Q+nAMwp2pQ== + dependencies: + ansi-colors "^4.1.1" + strip-ansi "^6.0.1" + +entities@~3.0.1: + version "3.0.1" + resolved "https://registry.yarnpkg.com/entities/-/entities-3.0.1.tgz#2b887ca62585e96db3903482d336c1006c3001d4" + integrity sha512-WiyBqoomrwMdFG1e0kqvASYfnlb0lp8M5o5Fw2OFq1hNZxxcNk8Ik0Xm7LxzBhuidnZB/UtBqVCgUz3kBOP51Q== + +env-paths@^2.2.0: + version "2.2.1" + resolved "https://registry.yarnpkg.com/env-paths/-/env-paths-2.2.1.tgz#420399d416ce1fbe9bc0a07c62fa68d67fd0f8f2" + integrity sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A== + +error-ex@^1.3.1: + version "1.3.2" + resolved "https://registry.yarnpkg.com/error-ex/-/error-ex-1.3.2.tgz#b4ac40648107fdcdcfae242f428bea8a14d4f1bf" + integrity sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g== + dependencies: + is-arrayish "^0.2.1" + +es-abstract@^1.22.1: + version "1.22.3" + resolved "https://registry.yarnpkg.com/es-abstract/-/es-abstract-1.22.3.tgz#48e79f5573198de6dee3589195727f4f74bc4f32" + integrity sha512-eiiY8HQeYfYH2Con2berK+To6GrK2RxbPawDkGq4UiCQQfZHb6wX9qQqkbpPqaxQFcl8d9QzZqo0tGE0VcrdwA== + dependencies: + array-buffer-byte-length "^1.0.0" + arraybuffer.prototype.slice "^1.0.2" + available-typed-arrays "^1.0.5" + call-bind "^1.0.5" + es-set-tostringtag "^2.0.1" + es-to-primitive "^1.2.1" + function.prototype.name "^1.1.6" + get-intrinsic "^1.2.2" + get-symbol-description "^1.0.0" + globalthis "^1.0.3" + gopd "^1.0.1" + has-property-descriptors "^1.0.0" + has-proto "^1.0.1" + has-symbols "^1.0.3" + hasown "^2.0.0" + internal-slot "^1.0.5" + is-array-buffer "^3.0.2" + is-callable "^1.2.7" + is-negative-zero "^2.0.2" + is-regex "^1.1.4" + is-shared-array-buffer "^1.0.2" + is-string "^1.0.7" + is-typed-array "^1.1.12" + is-weakref "^1.0.2" + object-inspect "^1.13.1" + object-keys "^1.1.1" + object.assign "^4.1.4" + regexp.prototype.flags "^1.5.1" + safe-array-concat "^1.0.1" + safe-regex-test "^1.0.0" + string.prototype.trim "^1.2.8" + string.prototype.trimend "^1.0.7" + string.prototype.trimstart "^1.0.7" + typed-array-buffer "^1.0.0" + typed-array-byte-length "^1.0.0" + typed-array-byte-offset "^1.0.0" + typed-array-length "^1.0.4" + unbox-primitive "^1.0.2" + which-typed-array "^1.1.13" + +es-set-tostringtag@^2.0.1: + version "2.0.2" + resolved "https://registry.yarnpkg.com/es-set-tostringtag/-/es-set-tostringtag-2.0.2.tgz#11f7cc9f63376930a5f20be4915834f4bc74f9c9" + integrity sha512-BuDyupZt65P9D2D2vA/zqcI3G5xRsklm5N3xCwuiy+/vKy8i0ifdsQP1sLgO4tZDSCaQUSnmC48khknGMV3D2Q== + dependencies: + get-intrinsic "^1.2.2" + has-tostringtag "^1.0.0" + hasown "^2.0.0" + +es-shim-unscopables@^1.0.0: + version "1.0.2" + resolved "https://registry.yarnpkg.com/es-shim-unscopables/-/es-shim-unscopables-1.0.2.tgz#1f6942e71ecc7835ed1c8a83006d8771a63a3763" + integrity sha512-J3yBRXCzDu4ULnQwxyToo/OjdMx6akgVC7K6few0a7F/0wLtmKKN7I73AH5T2836UuXRqN7Qg+IIUw/+YJksRw== + dependencies: + hasown "^2.0.0" + +es-to-primitive@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/es-to-primitive/-/es-to-primitive-1.2.1.tgz#e55cd4c9cdc188bcefb03b366c736323fc5c898a" + integrity sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA== + dependencies: + is-callable "^1.1.4" + is-date-object "^1.0.1" + is-symbol "^1.0.2" + +escalade@^3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/escalade/-/escalade-3.1.1.tgz#d8cfdc7000965c5a0174b4a82eaa5c0552742e40" + integrity sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw== + +escape-string-regexp@4.0.0, escape-string-regexp@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz#14ba83a5d373e3d311e5afca29cf5bfad965bf34" + integrity sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA== + +escape-string-regexp@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4" + integrity sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg== + +eslint-import-resolver-node@^0.3.9: + version "0.3.9" + resolved "https://registry.yarnpkg.com/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.9.tgz#d4eaac52b8a2e7c3cd1903eb00f7e053356118ac" + integrity sha512-WFj2isz22JahUv+B788TlO3N6zL3nNJGU8CcZbPZvVEkBPaJdCV4vy5wyghty5ROFbCRnm132v8BScu5/1BQ8g== + dependencies: + debug "^3.2.7" + is-core-module "^2.13.0" + resolve "^1.22.4" + +eslint-import-resolver-typescript@^3.6.1: + version "3.6.1" + resolved "https://registry.yarnpkg.com/eslint-import-resolver-typescript/-/eslint-import-resolver-typescript-3.6.1.tgz#7b983680edd3f1c5bce1a5829ae0bc2d57fe9efa" + integrity sha512-xgdptdoi5W3niYeuQxKmzVDTATvLYqhpwmykwsh7f6HIOStGWEIL9iqZgQDF9u9OEzrRwR8no5q2VT+bjAujTg== + dependencies: + debug "^4.3.4" + enhanced-resolve "^5.12.0" + eslint-module-utils "^2.7.4" + fast-glob "^3.3.1" + get-tsconfig "^4.5.0" + is-core-module "^2.11.0" + is-glob "^4.0.3" + +eslint-module-utils@^2.7.4, eslint-module-utils@^2.8.0: + version "2.8.0" + resolved "https://registry.yarnpkg.com/eslint-module-utils/-/eslint-module-utils-2.8.0.tgz#e439fee65fc33f6bba630ff621efc38ec0375c49" + integrity sha512-aWajIYfsqCKRDgUfjEXNN/JlrzauMuSEy5sbd7WXbtW3EH6A6MpwEh42c7qD+MqQo9QMJ6fWLAeIJynx0g6OAw== + dependencies: + debug "^3.2.7" + +eslint-plugin-import@^2.29.0: + version "2.29.0" + resolved "https://registry.yarnpkg.com/eslint-plugin-import/-/eslint-plugin-import-2.29.0.tgz#8133232e4329ee344f2f612885ac3073b0b7e155" + integrity sha512-QPOO5NO6Odv5lpoTkddtutccQjysJuFxoPS7fAHO+9m9udNHvTCPSAMW9zGAYj8lAIdr40I8yPCdUYrncXtrwg== + dependencies: + array-includes "^3.1.7" + array.prototype.findlastindex "^1.2.3" + array.prototype.flat "^1.3.2" + array.prototype.flatmap "^1.3.2" + debug "^3.2.7" + doctrine "^2.1.0" + eslint-import-resolver-node "^0.3.9" + eslint-module-utils "^2.8.0" + hasown "^2.0.0" + is-core-module "^2.13.1" + is-glob "^4.0.3" + minimatch "^3.1.2" + object.fromentries "^2.0.7" + object.groupby "^1.0.1" + object.values "^1.1.7" + semver "^6.3.1" + tsconfig-paths "^3.14.2" + +eslint-plugin-prettier@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/eslint-plugin-prettier/-/eslint-plugin-prettier-5.0.1.tgz#a3b399f04378f79f066379f544e42d6b73f11515" + integrity sha512-m3u5RnR56asrwV/lDC4GHorlW75DsFfmUcjfCYylTUs85dBRnB7VM6xG8eCMJdeDRnppzmxZVf1GEPJvl1JmNg== + dependencies: + prettier-linter-helpers "^1.0.0" + synckit "^0.8.5" + +eslint-scope@^7.2.2: + version "7.2.2" + resolved "https://registry.yarnpkg.com/eslint-scope/-/eslint-scope-7.2.2.tgz#deb4f92563390f32006894af62a22dba1c46423f" + integrity sha512-dOt21O7lTMhDM+X9mB4GX+DZrZtCUJPL/wlcTqxyrx5IvO0IYtILdtrQGQp+8n5S0gwSVmOf9NQrjMOgfQZlIg== + dependencies: + esrecurse "^4.3.0" + estraverse "^5.2.0" + +eslint-visitor-keys@^3.3.0, eslint-visitor-keys@^3.4.1, eslint-visitor-keys@^3.4.3: + version "3.4.3" + resolved "https://registry.yarnpkg.com/eslint-visitor-keys/-/eslint-visitor-keys-3.4.3.tgz#0cd72fe8550e3c2eae156a96a4dddcd1c8ac5800" + integrity sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag== + +eslint@^8.51.0: + version "8.52.0" + resolved "https://registry.yarnpkg.com/eslint/-/eslint-8.52.0.tgz#d0cd4a1fac06427a61ef9242b9353f36ea7062fc" + integrity sha512-zh/JHnaixqHZsolRB/w9/02akBk9EPrOs9JwcTP2ek7yL5bVvXuRariiaAjjoJ5DvuwQ1WAE/HsMz+w17YgBCg== + dependencies: + "@eslint-community/eslint-utils" "^4.2.0" + "@eslint-community/regexpp" "^4.6.1" + "@eslint/eslintrc" "^2.1.2" + "@eslint/js" "8.52.0" + "@humanwhocodes/config-array" "^0.11.13" + "@humanwhocodes/module-importer" "^1.0.1" + "@nodelib/fs.walk" "^1.2.8" + "@ungap/structured-clone" "^1.2.0" + ajv "^6.12.4" + chalk "^4.0.0" + cross-spawn "^7.0.2" + debug "^4.3.2" + doctrine "^3.0.0" + escape-string-regexp "^4.0.0" + eslint-scope "^7.2.2" + eslint-visitor-keys "^3.4.3" + espree "^9.6.1" + esquery "^1.4.2" + esutils "^2.0.2" + fast-deep-equal "^3.1.3" + file-entry-cache "^6.0.1" + find-up "^5.0.0" + glob-parent "^6.0.2" + globals "^13.19.0" + graphemer "^1.4.0" + ignore "^5.2.0" + imurmurhash "^0.1.4" + is-glob "^4.0.0" + is-path-inside "^3.0.3" + js-yaml "^4.1.0" + json-stable-stringify-without-jsonify "^1.0.1" + levn "^0.4.1" + lodash.merge "^4.6.2" + minimatch "^3.1.2" + natural-compare "^1.4.0" + optionator "^0.9.3" + strip-ansi "^6.0.1" + text-table "^0.2.0" + +espree@^9.6.0, espree@^9.6.1: + version "9.6.1" + resolved "https://registry.yarnpkg.com/espree/-/espree-9.6.1.tgz#a2a17b8e434690a5432f2f8018ce71d331a48c6f" + integrity sha512-oruZaFkjorTpF32kDSI5/75ViwGeZginGGy2NoOSg3Q9bnwlnmDm4HLnkl0RE3n+njDXR037aY1+x58Z/zFdwQ== + dependencies: + acorn "^8.9.0" + acorn-jsx "^5.3.2" + eslint-visitor-keys "^3.4.1" + +esquery@^1.4.2: + version "1.5.0" + resolved "https://registry.yarnpkg.com/esquery/-/esquery-1.5.0.tgz#6ce17738de8577694edd7361c57182ac8cb0db0b" + integrity sha512-YQLXUplAwJgCydQ78IMJywZCceoqk1oH01OERdSAJc/7U2AylwjhSCLDEtqwg811idIS/9fIU5GjG73IgjKMVg== + dependencies: + estraverse "^5.1.0" + +esrecurse@^4.3.0: + version "4.3.0" + resolved "https://registry.yarnpkg.com/esrecurse/-/esrecurse-4.3.0.tgz#7ad7964d679abb28bee72cec63758b1c5d2c9921" + integrity sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag== + dependencies: + estraverse "^5.2.0" + +estraverse@^5.1.0, estraverse@^5.2.0: + version "5.3.0" + resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-5.3.0.tgz#2eea5290702f26ab8fe5370370ff86c965d21123" + integrity sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA== + +esutils@^2.0.2: + version "2.0.3" + resolved "https://registry.yarnpkg.com/esutils/-/esutils-2.0.3.tgz#74d2eb4de0b8da1293711910d50775b9b710ef64" + integrity sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g== + +ethereum-cryptography@0.1.3, ethereum-cryptography@^0.1.3: + version "0.1.3" + resolved "https://registry.yarnpkg.com/ethereum-cryptography/-/ethereum-cryptography-0.1.3.tgz#8d6143cfc3d74bf79bbd8edecdf29e4ae20dd191" + integrity sha512-w8/4x1SGGzc+tO97TASLja6SLd3fRIK2tLVcV2Gx4IB21hE19atll5Cq9o3d0ZmAYC/8aw0ipieTSiekAea4SQ== + dependencies: + "@types/pbkdf2" "^3.0.0" + "@types/secp256k1" "^4.0.1" + blakejs "^1.1.0" + browserify-aes "^1.2.0" + bs58check "^2.1.2" + create-hash "^1.2.0" + create-hmac "^1.1.7" + hash.js "^1.1.7" + keccak "^3.0.0" + pbkdf2 "^3.0.17" + randombytes "^2.1.0" + safe-buffer "^5.1.2" + scrypt-js "^3.0.0" + secp256k1 "^4.0.1" + setimmediate "^1.0.5" + +ethereum-cryptography@^1.0.3: + version "1.2.0" + resolved "https://registry.yarnpkg.com/ethereum-cryptography/-/ethereum-cryptography-1.2.0.tgz#5ccfa183e85fdaf9f9b299a79430c044268c9b3a" + integrity sha512-6yFQC9b5ug6/17CQpCyE3k9eKBMdhyVjzUy1WkiuY/E4vj/SXDBbCw8QEIaXqf0Mf2SnY6RmpDcwlUmBSS0EJw== + dependencies: + "@noble/hashes" "1.2.0" + "@noble/secp256k1" "1.7.1" + "@scure/bip32" "1.1.5" + "@scure/bip39" "1.1.1" + +ethereumjs-abi@^0.6.8: + version "0.6.8" + resolved "https://registry.yarnpkg.com/ethereumjs-abi/-/ethereumjs-abi-0.6.8.tgz#71bc152db099f70e62f108b7cdfca1b362c6fcae" + integrity sha512-Tx0r/iXI6r+lRsdvkFDlut0N08jWMnKRZ6Gkq+Nmw75lZe4e6o3EkSnkaBP5NF6+m5PTGAr9JP43N3LyeoglsA== + dependencies: + bn.js "^4.11.8" + ethereumjs-util "^6.0.0" + +ethereumjs-util@^6.0.0, ethereumjs-util@^6.2.1: + version "6.2.1" + resolved "https://registry.yarnpkg.com/ethereumjs-util/-/ethereumjs-util-6.2.1.tgz#fcb4e4dd5ceacb9d2305426ab1a5cd93e3163b69" + integrity sha512-W2Ktez4L01Vexijrm5EB6w7dg4n/TgpoYU4avuT5T3Vmnw/eCRtiBrJfQYS/DCSvDIOLn2k57GcHdeBcgVxAqw== + dependencies: + "@types/bn.js" "^4.11.3" + bn.js "^4.11.0" + create-hash "^1.1.2" + elliptic "^6.5.2" + ethereum-cryptography "^0.1.3" + ethjs-util "0.1.6" + rlp "^2.2.3" + +ethers@^5.7.0, ethers@^5.7.1: + version "5.7.2" + resolved "https://registry.yarnpkg.com/ethers/-/ethers-5.7.2.tgz#3a7deeabbb8c030d4126b24f84e525466145872e" + integrity sha512-wswUsmWo1aOK8rR7DIKiWSw9DbLWe6x98Jrn8wcTflTVvaXhAMaB5zGAXy0GYQEQp9iO1iSHWVyARQm11zUtyg== + dependencies: + "@ethersproject/abi" "5.7.0" + "@ethersproject/abstract-provider" "5.7.0" + "@ethersproject/abstract-signer" "5.7.0" + "@ethersproject/address" "5.7.0" + "@ethersproject/base64" "5.7.0" + "@ethersproject/basex" "5.7.0" + "@ethersproject/bignumber" "5.7.0" + "@ethersproject/bytes" "5.7.0" + "@ethersproject/constants" "5.7.0" + "@ethersproject/contracts" "5.7.0" + "@ethersproject/hash" "5.7.0" + "@ethersproject/hdnode" "5.7.0" + "@ethersproject/json-wallets" "5.7.0" + "@ethersproject/keccak256" "5.7.0" + "@ethersproject/logger" "5.7.0" + "@ethersproject/networks" "5.7.1" + "@ethersproject/pbkdf2" "5.7.0" + "@ethersproject/properties" "5.7.0" + "@ethersproject/providers" "5.7.2" + "@ethersproject/random" "5.7.0" + "@ethersproject/rlp" "5.7.0" + "@ethersproject/sha2" "5.7.0" + "@ethersproject/signing-key" "5.7.0" + "@ethersproject/solidity" "5.7.0" + "@ethersproject/strings" "5.7.0" + "@ethersproject/transactions" "5.7.0" + "@ethersproject/units" "5.7.0" + "@ethersproject/wallet" "5.7.0" + "@ethersproject/web" "5.7.1" + "@ethersproject/wordlists" "5.7.0" + +ethjs-util@0.1.6, ethjs-util@^0.1.6: + version "0.1.6" + resolved "https://registry.yarnpkg.com/ethjs-util/-/ethjs-util-0.1.6.tgz#f308b62f185f9fe6237132fb2a9818866a5cd536" + integrity sha512-CUnVOQq7gSpDHZVVrQW8ExxUETWrnrvXYvYz55wOU8Uj4VCgw56XC2B/fVqQN+f7gmrnRHSLVnFAwsCuNwji8w== + dependencies: + is-hex-prefixed "1.0.0" + strip-hex-prefix "1.0.0" + +event-target-shim@^5.0.0: + version "5.0.1" + resolved "https://registry.yarnpkg.com/event-target-shim/-/event-target-shim-5.0.1.tgz#5d4d3ebdf9583d63a5333ce2deb7480ab2b05789" + integrity sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ== + +evp_bytestokey@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/evp_bytestokey/-/evp_bytestokey-1.0.3.tgz#7fcbdb198dc71959432efe13842684e0525acb02" + integrity sha512-/f2Go4TognH/KvCISP7OUsHn85hT9nUkxxA9BEWxFn+Oj9o8ZNLm/40hdlgSLyuOimsrTKLUMEorQexp/aPQeA== + dependencies: + md5.js "^1.3.4" + safe-buffer "^5.1.1" + +execa@^5.0.0: + version "5.1.1" + resolved "https://registry.yarnpkg.com/execa/-/execa-5.1.1.tgz#f80ad9cbf4298f7bd1d4c9555c21e93741c411dd" + integrity sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg== + dependencies: + cross-spawn "^7.0.3" + get-stream "^6.0.0" + human-signals "^2.1.0" + is-stream "^2.0.0" + merge-stream "^2.0.0" + npm-run-path "^4.0.1" + onetime "^5.1.2" + signal-exit "^3.0.3" + strip-final-newline "^2.0.0" + +execa@^7.1.1: + version "7.2.0" + resolved "https://registry.yarnpkg.com/execa/-/execa-7.2.0.tgz#657e75ba984f42a70f38928cedc87d6f2d4fe4e9" + integrity sha512-UduyVP7TLB5IcAQl+OzLyLcS/l32W/GLg+AhHJ+ow40FOk2U3SAllPwR44v4vmdFwIWqpdwxxpQbF1n5ta9seA== + dependencies: + cross-spawn "^7.0.3" + get-stream "^6.0.1" + human-signals "^4.3.0" + is-stream "^3.0.0" + merge-stream "^2.0.0" + npm-run-path "^5.1.0" + onetime "^6.0.0" + signal-exit "^3.0.7" + strip-final-newline "^3.0.0" + +fast-deep-equal@^3.1.1, fast-deep-equal@^3.1.3: + version "3.1.3" + resolved "https://registry.yarnpkg.com/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz#3a7d56b559d6cbc3eb512325244e619a65c6c525" + integrity sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q== + +fast-diff@^1.1.2, fast-diff@^1.2.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/fast-diff/-/fast-diff-1.3.0.tgz#ece407fa550a64d638536cd727e129c61616e0f0" + integrity sha512-VxPP4NqbUjj6MaAOafWeUn2cXWLcCtljklUtZf0Ind4XQ+QPtmA0b18zZy0jIQx+ExRVCR/ZQpBmik5lXshNsw== + +fast-glob@^3.2.12, fast-glob@^3.2.9, fast-glob@^3.3.0, fast-glob@^3.3.1: + version "3.3.1" + resolved "https://registry.yarnpkg.com/fast-glob/-/fast-glob-3.3.1.tgz#784b4e897340f3dbbef17413b3f11acf03c874c4" + integrity sha512-kNFPyjhh5cKjrUltxs+wFx+ZkbRaxxmZ+X0ZU31SOsxCEtP9VPgtq2teZw1DebupL5GmDaNQ6yKMMVcM41iqDg== + dependencies: + "@nodelib/fs.stat" "^2.0.2" + "@nodelib/fs.walk" "^1.2.3" + glob-parent "^5.1.2" + merge2 "^1.3.0" + micromatch "^4.0.4" + +fast-json-stable-stringify@^2.0.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz#874bf69c6f404c2b5d99c481341399fd55892633" + integrity sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw== + +fast-levenshtein@^2.0.6: + version "2.0.6" + resolved "https://registry.yarnpkg.com/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz#3d8a5c66883a16a30ca8643e851f19baa7797917" + integrity sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw== + +fastq@^1.6.0: + version "1.15.0" + resolved "https://registry.yarnpkg.com/fastq/-/fastq-1.15.0.tgz#d04d07c6a2a68fe4599fea8d2e103a937fae6b3a" + integrity sha512-wBrocU2LCXXa+lWBt8RoIRD89Fi8OdABODa/kEnyeyjS5aZO5/GNvI5sEINADqP/h8M29UHTHUb53sUu5Ihqdw== + dependencies: + reusify "^1.0.4" + +file-entry-cache@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/file-entry-cache/-/file-entry-cache-6.0.1.tgz#211b2dd9659cb0394b073e7323ac3c933d522027" + integrity sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg== + dependencies: + flat-cache "^3.0.4" + +fill-range@^7.0.1: + version "7.0.1" + resolved "https://registry.yarnpkg.com/fill-range/-/fill-range-7.0.1.tgz#1919a6a7c75fe38b2c7c77e5198535da9acdda40" + integrity sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ== + dependencies: + to-regex-range "^5.0.1" + +find-replace@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/find-replace/-/find-replace-3.0.0.tgz#3e7e23d3b05167a76f770c9fbd5258b0def68c38" + integrity sha512-6Tb2myMioCAgv5kfvP5/PkZZ/ntTpVK39fHY7WkWBgvbeE+VHd/tZuZ4mrC+bxh4cfOZeYKVPaJIZtZXV7GNCQ== + dependencies: + array-back "^3.0.1" + +find-up@5.0.0, find-up@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-5.0.0.tgz#4c92819ecb7083561e4f4a240a86be5198f536fc" + integrity sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng== + dependencies: + locate-path "^6.0.0" + path-exists "^4.0.0" + +find-up@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-2.1.0.tgz#45d1b7e506c717ddd482775a2b77920a3c0c57a7" + integrity sha512-NWzkk0jSJtTt08+FBFMvXoeZnOJD+jTtsRmBYbAIzJdX6l7dLgR7CTubCM5/eDdPUBvLCeVasP1brfVR/9/EZQ== + dependencies: + locate-path "^2.0.0" + +flat-cache@^3.0.4: + version "3.1.1" + resolved "https://registry.yarnpkg.com/flat-cache/-/flat-cache-3.1.1.tgz#a02a15fdec25a8f844ff7cc658f03dd99eb4609b" + integrity sha512-/qM2b3LUIaIgviBQovTLvijfyOQXPtSRnRK26ksj2J7rzPIecePUIpJsZ4T02Qg+xiAEKIs5K8dsHEd+VaKa/Q== + dependencies: + flatted "^3.2.9" + keyv "^4.5.3" + rimraf "^3.0.2" + +flat@^5.0.2: + version "5.0.2" + resolved "https://registry.yarnpkg.com/flat/-/flat-5.0.2.tgz#8ca6fe332069ffa9d324c327198c598259ceb241" + integrity sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ== + +flatted@^3.2.9: + version "3.2.9" + resolved "https://registry.yarnpkg.com/flatted/-/flatted-3.2.9.tgz#7eb4c67ca1ba34232ca9d2d93e9886e611ad7daf" + integrity sha512-36yxDn5H7OFZQla0/jFJmbIKTdZAQHngCedGxiMmpNfEZM0sdEeT+WczLQrjK6D7o2aiyLYDnkw0R3JK0Qv1RQ== + +follow-redirects@^1.12.1, follow-redirects@^1.14.0: + version "1.15.2" + resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.15.2.tgz#b460864144ba63f2681096f274c4e57026da2c13" + integrity sha512-VQLG33o04KaQ8uYi2tVNbdrWp1QWxNNea+nmIB4EVM28v0hmP17z7aG1+wAkNzVq4KeXTq3221ye5qTJP91JwA== + +for-each@^0.3.3: + version "0.3.3" + resolved "https://registry.yarnpkg.com/for-each/-/for-each-0.3.3.tgz#69b447e88a0a5d32c3e7084f3f1710034b21376e" + integrity sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw== + dependencies: + is-callable "^1.1.3" + +fp-ts@1.19.3: + version "1.19.3" + resolved "https://registry.yarnpkg.com/fp-ts/-/fp-ts-1.19.3.tgz#261a60d1088fbff01f91256f91d21d0caaaaa96f" + integrity sha512-H5KQDspykdHuztLTg+ajGN0Z2qUjcEf3Ybxc6hLt0k7/zPkn29XnKnxlBPyW2XIddWrGaJBzBl4VLYOtk39yZg== + +fp-ts@^1.0.0: + version "1.19.5" + resolved "https://registry.yarnpkg.com/fp-ts/-/fp-ts-1.19.5.tgz#3da865e585dfa1fdfd51785417357ac50afc520a" + integrity sha512-wDNqTimnzs8QqpldiId9OavWK2NptormjXnRJTQecNjzwfyp6P/8s/zG8e4h3ja3oqkKaY72UlTjQYt/1yXf9A== + +fs-constants@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/fs-constants/-/fs-constants-1.0.0.tgz#6be0de9be998ce16af8afc24497b9ee9b7ccd9ad" + integrity sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow== + +fs-extra@^0.30.0: + version "0.30.0" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-0.30.0.tgz#f233ffcc08d4da7d432daa449776989db1df93f0" + integrity sha512-UvSPKyhMn6LEd/WpUaV9C9t3zATuqoqfWc3QdPhPLb58prN9tqYPlPWi8Krxi44loBoUzlobqZ3+8tGpxxSzwA== + dependencies: + graceful-fs "^4.1.2" + jsonfile "^2.1.0" + klaw "^1.0.0" + path-is-absolute "^1.0.0" + rimraf "^2.2.8" + +fs-extra@^11.1.1: + version "11.1.1" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-11.1.1.tgz#da69f7c39f3b002378b0954bb6ae7efdc0876e2d" + integrity sha512-MGIE4HOvQCeUCzmlHs0vXpih4ysz4wg9qiSAu6cd42lVwPbTM1TjV7RusoyQqMmk/95gdQZX72u+YW+c3eEpFQ== + dependencies: + graceful-fs "^4.2.0" + jsonfile "^6.0.1" + universalify "^2.0.0" + +fs-extra@^7.0.0, fs-extra@^7.0.1: + version "7.0.1" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-7.0.1.tgz#4f189c44aa123b895f722804f55ea23eadc348e9" + integrity sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw== + dependencies: + graceful-fs "^4.1.2" + jsonfile "^4.0.0" + universalify "^0.1.0" + +fs-extra@^9.1.0: + version "9.1.0" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-9.1.0.tgz#5954460c764a8da2094ba3554bf839e6b9a7c86d" + integrity sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ== + dependencies: + at-least-node "^1.0.0" + graceful-fs "^4.2.0" + jsonfile "^6.0.1" + universalify "^2.0.0" + +fs.realpath@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f" + integrity sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw== + +fsevents@~2.3.2: + version "2.3.3" + resolved "https://registry.yarnpkg.com/fsevents/-/fsevents-2.3.3.tgz#cac6407785d03675a2a5e1a5305c697b347d90d6" + integrity sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw== + +function-bind@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/function-bind/-/function-bind-1.1.1.tgz#a56899d3ea3c9bab874bb9773b7c5ede92f4895d" + integrity sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A== + +function-bind@^1.1.2: + version "1.1.2" + resolved "https://registry.yarnpkg.com/function-bind/-/function-bind-1.1.2.tgz#2c02d864d97f3ea6c8830c464cbd11ab6eab7a1c" + integrity sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA== + +function.prototype.name@^1.1.6: + version "1.1.6" + resolved "https://registry.yarnpkg.com/function.prototype.name/-/function.prototype.name-1.1.6.tgz#cdf315b7d90ee77a4c6ee216c3c3362da07533fd" + integrity sha512-Z5kx79swU5P27WEayXM1tBi5Ze/lbIyiNgU3qyXUOf9b2rgXYyF9Dy9Cx+IQv/Lc8WCG6L82zwUPpSS9hGehIg== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + functions-have-names "^1.2.3" + +functional-red-black-tree@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz#1b0ab3bd553b2a0d6399d29c0e3ea0b252078327" + integrity sha512-dsKNQNdj6xA3T+QlADDA7mOSlX0qiMINjn0cgr+eGHGsbSHzTabcIogz2+p/iqP1Xs6EP/sS2SbqH+brGTbq0g== + +functions-have-names@^1.2.3: + version "1.2.3" + resolved "https://registry.yarnpkg.com/functions-have-names/-/functions-have-names-1.2.3.tgz#0404fe4ee2ba2f607f0e0ec3c80bae994133b834" + integrity sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ== + +get-caller-file@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/get-caller-file/-/get-caller-file-2.0.5.tgz#4f94412a82db32f36e3b0b9741f8a97feb031f7e" + integrity sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg== + +get-func-name@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/get-func-name/-/get-func-name-2.0.0.tgz#ead774abee72e20409433a066366023dd6887a41" + integrity sha512-Hm0ixYtaSZ/V7C8FJrtZIuBBI+iSgL+1Aq82zSu8VQNB4S3Gk8e7Qs3VwBDJAhmRZcFqkl3tQu36g/Foh5I5ig== + +get-intrinsic@^1.0.2, get-intrinsic@^1.1.1, get-intrinsic@^1.1.3, get-intrinsic@^1.2.0, get-intrinsic@^1.2.1, get-intrinsic@^1.2.2: + version "1.2.2" + resolved "https://registry.yarnpkg.com/get-intrinsic/-/get-intrinsic-1.2.2.tgz#281b7622971123e1ef4b3c90fd7539306da93f3b" + integrity sha512-0gSo4ml/0j98Y3lngkFEot/zhiCeWsbYIlZ+uZOVgzLyLaUw7wxUL+nCTP0XJvJg1AXulJRI3UJi8GsbDuxdGA== + dependencies: + function-bind "^1.1.2" + has-proto "^1.0.1" + has-symbols "^1.0.3" + hasown "^2.0.0" + +get-stdin@~9.0.0: + version "9.0.0" + resolved "https://registry.yarnpkg.com/get-stdin/-/get-stdin-9.0.0.tgz#3983ff82e03d56f1b2ea0d3e60325f39d703a575" + integrity sha512-dVKBjfWisLAicarI2Sf+JuBE/DghV4UzNAVe9yhEJuzeREd3JhOTE9cUaJTeSa77fsbQUK3pcOpJfM59+VKZaA== + +get-stream@^6.0.0, get-stream@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/get-stream/-/get-stream-6.0.1.tgz#a262d8eef67aced57c2852ad6167526a43cbf7b7" + integrity sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg== + +get-symbol-description@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/get-symbol-description/-/get-symbol-description-1.0.0.tgz#7fdb81c900101fbd564dd5f1a30af5aadc1e58d6" + integrity sha512-2EmdH1YvIQiZpltCNgkuiUnyukzxM/R6NDJX31Ke3BG1Nq5b0S2PhX59UKi9vZpPDQVdqn+1IcaAwnzTT5vCjw== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.1.1" + +get-tsconfig@^4.5.0: + version "4.7.2" + resolved "https://registry.yarnpkg.com/get-tsconfig/-/get-tsconfig-4.7.2.tgz#0dcd6fb330391d46332f4c6c1bf89a6514c2ddce" + integrity sha512-wuMsz4leaj5hbGgg4IvDU0bqJagpftG5l5cXIAvo8uZrqn0NJqwtfupTN00VnkQJPcIRrxYrm1Ue24btpCha2A== + dependencies: + resolve-pkg-maps "^1.0.0" + +glob-parent@^5.1.2, glob-parent@~5.1.2: + version "5.1.2" + resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-5.1.2.tgz#869832c58034fe68a4093c17dc15e8340d8401c4" + integrity sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow== + dependencies: + is-glob "^4.0.1" + +glob-parent@^6.0.2: + version "6.0.2" + resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-6.0.2.tgz#6d237d99083950c79290f24c7642a3de9a28f9e3" + integrity sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A== + dependencies: + is-glob "^4.0.3" + +glob@7.1.7: + version "7.1.7" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.7.tgz#3b193e9233f01d42d0b3f78294bbeeb418f94a90" + integrity sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.0.4" + once "^1.3.0" + path-is-absolute "^1.0.0" + +glob@7.2.0: + version "7.2.0" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.0.tgz#d15535af7732e02e948f4c41628bd910293f6023" + integrity sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.0.4" + once "^1.3.0" + path-is-absolute "^1.0.0" + +glob@^7.1.2, glob@^7.1.3, glob@^7.1.6: + version "7.2.3" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.3.tgz#b8df0fb802bbfa8e89bd1d938b4e16578ed44f2b" + integrity sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.1.1" + once "^1.3.0" + path-is-absolute "^1.0.0" + +glob@^8.0.3: + version "8.1.0" + resolved "https://registry.yarnpkg.com/glob/-/glob-8.1.0.tgz#d388f656593ef708ee3e34640fdfb99a9fd1c33e" + integrity sha512-r8hpEjiQEYlF2QU0df3dS+nxxSIreXQS1qRhMJM0Q5NDdR386C7jb7Hwwod8Fgiuex+k0GFjgft18yvxm5XoCQ== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^5.0.1" + once "^1.3.0" + +glob@~8.0.3: + version "8.0.3" + resolved "https://registry.yarnpkg.com/glob/-/glob-8.0.3.tgz#415c6eb2deed9e502c68fa44a272e6da6eeca42e" + integrity sha512-ull455NHSHI/Y1FqGaaYFaLGkNMMJbavMrEGFXG/PGrg6y7sutWHUHrz6gy6WEBH6akM1M414dWKCNs+IhKdiQ== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^5.0.1" + once "^1.3.0" + +globals@^13.19.0: + version "13.23.0" + resolved "https://registry.yarnpkg.com/globals/-/globals-13.23.0.tgz#ef31673c926a0976e1f61dab4dca57e0c0a8af02" + integrity sha512-XAmF0RjlrjY23MA51q3HltdlGxUpXPvg0GioKiD9X6HD28iMjo2dKC8Vqwm7lne4GNr78+RHTfliktR6ZH09wA== + dependencies: + type-fest "^0.20.2" + +globalthis@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/globalthis/-/globalthis-1.0.3.tgz#5852882a52b80dc301b0660273e1ed082f0b6ccf" + integrity sha512-sFdI5LyBiNTHjRd7cGPWapiHWMOXKyuBNX/cWJ3NfzrZQVa8GI/8cofCl74AOVqq9W5kNmguTIzJ/1s2gyI9wA== + dependencies: + define-properties "^1.1.3" + +globby@^11.1.0: + version "11.1.0" + resolved "https://registry.yarnpkg.com/globby/-/globby-11.1.0.tgz#bd4be98bb042f83d796f7e3811991fbe82a0d34b" + integrity sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g== + dependencies: + array-union "^2.1.0" + dir-glob "^3.0.1" + fast-glob "^3.2.9" + ignore "^5.2.0" + merge2 "^1.4.1" + slash "^3.0.0" + +gopd@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/gopd/-/gopd-1.0.1.tgz#29ff76de69dac7489b7c0918a5788e56477c332c" + integrity sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA== + dependencies: + get-intrinsic "^1.1.3" + +graceful-fs@^4.1.2, graceful-fs@^4.1.6, graceful-fs@^4.1.9: + version "4.2.10" + resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.10.tgz#147d3a006da4ca3ce14728c7aefc287c367d7a6c" + integrity sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA== + +graceful-fs@^4.2.0, graceful-fs@^4.2.4: + version "4.2.11" + resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.11.tgz#4183e4e8bf08bb6e05bbb2f7d2e0c8f712ca40e3" + integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ== + +graphemer@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/graphemer/-/graphemer-1.4.0.tgz#fb2f1d55e0e3a1849aeffc90c4fa0dd53a0e66c6" + integrity sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag== + +hardhat@=2.16.0: + version "2.16.0" + resolved "https://registry.yarnpkg.com/hardhat/-/hardhat-2.16.0.tgz#c5611d433416b31f6ce92f733b1f1b5236ad6230" + integrity sha512-7VQEJPQRAZdtrYUZaU9GgCpP3MBNy/pTdscARNJQMWKj5C+R7V32G5uIZKIqZ4QiqXa6CBfxxe+G+ahxUbHZHA== + dependencies: + "@ethersproject/abi" "^5.1.2" + "@metamask/eth-sig-util" "^4.0.0" + "@nomicfoundation/ethereumjs-block" "5.0.1" + "@nomicfoundation/ethereumjs-blockchain" "7.0.1" + "@nomicfoundation/ethereumjs-common" "4.0.1" + "@nomicfoundation/ethereumjs-evm" "2.0.1" + "@nomicfoundation/ethereumjs-rlp" "5.0.1" + "@nomicfoundation/ethereumjs-statemanager" "2.0.1" + "@nomicfoundation/ethereumjs-trie" "6.0.1" + "@nomicfoundation/ethereumjs-tx" "5.0.1" + "@nomicfoundation/ethereumjs-util" "9.0.1" + "@nomicfoundation/ethereumjs-vm" "7.0.1" + "@nomicfoundation/solidity-analyzer" "^0.1.0" + "@sentry/node" "^5.18.1" + "@types/bn.js" "^5.1.0" + "@types/lru-cache" "^5.1.0" + abort-controller "^3.0.0" + adm-zip "^0.4.16" + aggregate-error "^3.0.0" + ansi-escapes "^4.3.0" + chalk "^2.4.2" + chokidar "^3.4.0" + ci-info "^2.0.0" + debug "^4.1.1" + enquirer "^2.3.0" + env-paths "^2.2.0" + ethereum-cryptography "^1.0.3" + ethereumjs-abi "^0.6.8" + find-up "^2.1.0" + fp-ts "1.19.3" + fs-extra "^7.0.1" + glob "7.2.0" + immutable "^4.0.0-rc.12" + io-ts "1.10.4" + keccak "^3.0.2" + lodash "^4.17.11" + mnemonist "^0.38.0" + mocha "^10.0.0" + p-map "^4.0.0" + raw-body "^2.4.1" + resolve "1.17.0" + semver "^6.3.0" + solc "0.7.3" + source-map-support "^0.5.13" + stacktrace-parser "^0.1.10" + tsort "0.0.1" + undici "^5.14.0" + uuid "^8.3.2" + ws "^7.4.6" + +has-bigints@^1.0.1, has-bigints@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/has-bigints/-/has-bigints-1.0.2.tgz#0871bd3e3d51626f6ca0966668ba35d5602d6eaa" + integrity sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ== + +has-flag@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd" + integrity sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw== + +has-flag@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-4.0.0.tgz#944771fd9c81c81265c4d6941860da06bb59479b" + integrity sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ== + +has-property-descriptors@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/has-property-descriptors/-/has-property-descriptors-1.0.1.tgz#52ba30b6c5ec87fd89fa574bc1c39125c6f65340" + integrity sha512-VsX8eaIewvas0xnvinAe9bw4WfIeODpGYikiWYLH+dma0Jw6KHYqWiWfhQlgOVK8D6PvjubK5Uc4P0iIhIcNVg== + dependencies: + get-intrinsic "^1.2.2" + +has-proto@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/has-proto/-/has-proto-1.0.1.tgz#1885c1305538958aff469fef37937c22795408e0" + integrity sha512-7qE+iP+O+bgF9clE5+UoBFzE65mlBiVj3tKCrlNQ0Ogwm0BjpT/gK4SlLYDMybDh5I3TCTKnPPa0oMG7JDYrhg== + +has-symbols@^1.0.2, has-symbols@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/has-symbols/-/has-symbols-1.0.3.tgz#bb7b2c4349251dce87b125f7bdf874aa7c8b39f8" + integrity sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A== + +has-tostringtag@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/has-tostringtag/-/has-tostringtag-1.0.0.tgz#7e133818a7d394734f941e73c3d3f9291e658b25" + integrity sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ== + dependencies: + has-symbols "^1.0.2" + +has@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/has/-/has-1.0.3.tgz#722d7cbfc1f6aa8241f16dd814e011e1f41e8796" + integrity sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw== + dependencies: + function-bind "^1.1.1" + +hash-base@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/hash-base/-/hash-base-3.1.0.tgz#55c381d9e06e1d2997a883b4a3fddfe7f0d3af33" + integrity sha512-1nmYp/rhMDiE7AYkDw+lLwlAzz0AntGIe51F3RfFfEqyQ3feY2eI/NcwC6umIQVOASPMsWJLJScWKSSvzL9IVA== + dependencies: + inherits "^2.0.4" + readable-stream "^3.6.0" + safe-buffer "^5.2.0" + +hash.js@1.1.7, hash.js@^1.0.0, hash.js@^1.0.3, hash.js@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/hash.js/-/hash.js-1.1.7.tgz#0babca538e8d4ee4a0f8988d68866537a003cf42" + integrity sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA== + dependencies: + inherits "^2.0.3" + minimalistic-assert "^1.0.1" + +hasown@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/hasown/-/hasown-2.0.0.tgz#f4c513d454a57b7c7e1650778de226b11700546c" + integrity sha512-vUptKVTpIJhcczKBbgnS+RtcuYMB8+oNzPK2/Hp3hanz8JmpATdmmgLgSaadVREkDm+e2giHwY3ZRkyjSIDDFA== + dependencies: + function-bind "^1.1.2" + +he@1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/he/-/he-1.2.0.tgz#84ae65fa7eafb165fddb61566ae14baf05664f0f" + integrity sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw== + +hmac-drbg@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/hmac-drbg/-/hmac-drbg-1.0.1.tgz#d2745701025a6c775a6c545793ed502fc0c649a1" + integrity sha512-Tti3gMqLdZfhOQY1Mzf/AanLiqh1WTiJgEj26ZuYQ9fbkLomzGchCws4FyrSd4VkpBfiNhaE1On+lOz894jvXg== + dependencies: + hash.js "^1.0.3" + minimalistic-assert "^1.0.0" + minimalistic-crypto-utils "^1.0.1" + +http-errors@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/http-errors/-/http-errors-2.0.0.tgz#b7774a1486ef73cf7667ac9ae0858c012c57b9d3" + integrity sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ== + dependencies: + depd "2.0.0" + inherits "2.0.4" + setprototypeof "1.2.0" + statuses "2.0.1" + toidentifier "1.0.1" + +https-proxy-agent@^5.0.0: + version "5.0.1" + resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz#c59ef224a04fe8b754f3db0063a25ea30d0005d6" + integrity sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA== + dependencies: + agent-base "6" + debug "4" + +human-signals@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/human-signals/-/human-signals-2.1.0.tgz#dc91fcba42e4d06e4abaed33b3e7a3c02f514ea0" + integrity sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw== + +human-signals@^4.3.0: + version "4.3.1" + resolved "https://registry.yarnpkg.com/human-signals/-/human-signals-4.3.1.tgz#ab7f811e851fca97ffbd2c1fe9a958964de321b2" + integrity sha512-nZXjEF2nbo7lIw3mgYjItAfgQXog3OjJogSbKa2CQIIvSGWcKgeJnQlNXip6NglNzYH45nSRiEVimMvYL8DDqQ== + +iconv-lite@0.4.24: + version "0.4.24" + resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b" + integrity sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA== + dependencies: + safer-buffer ">= 2.1.2 < 3" + +ieee754@^1.1.13, ieee754@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/ieee754/-/ieee754-1.2.1.tgz#8eb7a10a63fff25d15a57b001586d177d1b0d352" + integrity sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA== + +ignore@^5.2.0, ignore@^5.2.4, ignore@~5.2.4: + version "5.2.4" + resolved "https://registry.yarnpkg.com/ignore/-/ignore-5.2.4.tgz#a291c0c6178ff1b960befe47fcdec301674a6324" + integrity sha512-MAb38BcSbH0eHNBxn7ql2NH/kX33OkB3lZ1BNdh7ENeRChHTYsTvWrMubiIAMNS2llXEEgZ1MUOBtXChP3kaFQ== + +immutable@^4.0.0-rc.12: + version "4.3.4" + resolved "https://registry.yarnpkg.com/immutable/-/immutable-4.3.4.tgz#2e07b33837b4bb7662f288c244d1ced1ef65a78f" + integrity sha512-fsXeu4J4i6WNWSikpI88v/PcVflZz+6kMhUfIwc5SY+poQRPnaf5V7qds6SUyUN3cVxEzuCab7QIoLOQ+DQ1wA== + +import-fresh@^3.2.1, import-fresh@^3.3.0: + version "3.3.0" + resolved "https://registry.yarnpkg.com/import-fresh/-/import-fresh-3.3.0.tgz#37162c25fcb9ebaa2e6e53d5b4d88ce17d9e0c2b" + integrity sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw== + dependencies: + parent-module "^1.0.0" + resolve-from "^4.0.0" + +imurmurhash@^0.1.4: + version "0.1.4" + resolved "https://registry.yarnpkg.com/imurmurhash/-/imurmurhash-0.1.4.tgz#9218b9b2b928a238b13dc4fb6b6d576f231453ea" + integrity sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA== + +indent-string@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/indent-string/-/indent-string-4.0.0.tgz#624f8f4497d619b2d9768531d58f4122854d7251" + integrity sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg== + +inflight@^1.0.4: + version "1.0.6" + resolved "https://registry.yarnpkg.com/inflight/-/inflight-1.0.6.tgz#49bd6331d7d02d0c09bc910a1075ba8165b56df9" + integrity sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA== + dependencies: + once "^1.3.0" + wrappy "1" + +inherits@2, inherits@2.0.4, inherits@^2.0.1, inherits@^2.0.3, inherits@^2.0.4, inherits@~2.0.1, inherits@~2.0.3: + version "2.0.4" + resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.4.tgz#0fa2c64f932917c3433a0ded55363aae37416b7c" + integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== + +ini@~3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/ini/-/ini-3.0.1.tgz#c76ec81007875bc44d544ff7a11a55d12294102d" + integrity sha512-it4HyVAUTKBc6m8e1iXWvXSTdndF7HbdN713+kvLrymxTaU4AUBWrJ4vEooP+V7fexnVD3LKcBshjGGPefSMUQ== + +internal-slot@^1.0.5: + version "1.0.6" + resolved "https://registry.yarnpkg.com/internal-slot/-/internal-slot-1.0.6.tgz#37e756098c4911c5e912b8edbf71ed3aa116f930" + integrity sha512-Xj6dv+PsbtwyPpEflsejS+oIZxmMlV44zAhG479uYu89MsjcYOhCFnNyKrkJrihbsiasQyY0afoCl/9BLR65bg== + dependencies: + get-intrinsic "^1.2.2" + hasown "^2.0.0" + side-channel "^1.0.4" + +io-ts@1.10.4: + version "1.10.4" + resolved "https://registry.yarnpkg.com/io-ts/-/io-ts-1.10.4.tgz#cd5401b138de88e4f920adbcb7026e2d1967e6e2" + integrity sha512-b23PteSnYXSONJ6JQXRAlvJhuw8KOtkqa87W4wDtvMrud/DTJd5X+NpOOI+O/zZwVq6v0VLAaJ+1EDViKEuN9g== + dependencies: + fp-ts "^1.0.0" + +is-array-buffer@^3.0.1, is-array-buffer@^3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/is-array-buffer/-/is-array-buffer-3.0.2.tgz#f2653ced8412081638ecb0ebbd0c41c6e0aecbbe" + integrity sha512-y+FyyR/w8vfIRq4eQcM1EYgSTnmHXPqaF+IgzgraytCFq5Xh8lllDVmAZolPJiZttZLeFSINPYMaEJ7/vWUa1w== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.2.0" + is-typed-array "^1.1.10" + +is-arrayish@^0.2.1: + version "0.2.1" + resolved "https://registry.yarnpkg.com/is-arrayish/-/is-arrayish-0.2.1.tgz#77c99840527aa8ecb1a8ba697b80645a7a926a9d" + integrity sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg== + +is-bigint@^1.0.1: + version "1.0.4" + resolved "https://registry.yarnpkg.com/is-bigint/-/is-bigint-1.0.4.tgz#08147a1875bc2b32005d41ccd8291dffc6691df3" + integrity sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg== + dependencies: + has-bigints "^1.0.1" + +is-binary-path@~2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-2.1.0.tgz#ea1f7f3b80f064236e83470f86c09c254fb45b09" + integrity sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw== + dependencies: + binary-extensions "^2.0.0" + +is-boolean-object@^1.1.0: + version "1.1.2" + resolved "https://registry.yarnpkg.com/is-boolean-object/-/is-boolean-object-1.1.2.tgz#5c6dc200246dd9321ae4b885a114bb1f75f63719" + integrity sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA== + dependencies: + call-bind "^1.0.2" + has-tostringtag "^1.0.0" + +is-buffer@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/is-buffer/-/is-buffer-2.0.5.tgz#ebc252e400d22ff8d77fa09888821a24a658c191" + integrity sha512-i2R6zNFDwgEHJyQUtJEk0XFi1i0dPFn/oqjK3/vPCcDeJvW5NQ83V8QbicfF1SupOaB0h8ntgBC2YiE7dfyctQ== + +is-callable@^1.1.3, is-callable@^1.1.4, is-callable@^1.2.7: + version "1.2.7" + resolved "https://registry.yarnpkg.com/is-callable/-/is-callable-1.2.7.tgz#3bc2a85ea742d9e36205dcacdd72ca1fdc51b055" + integrity sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA== + +is-core-module@^2.11.0, is-core-module@^2.13.1: + version "2.13.1" + resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.13.1.tgz#ad0d7532c6fea9da1ebdc82742d74525c6273384" + integrity sha512-hHrIjvZsftOsvKSn2TRYl63zvxsgE0K+0mYMoH6gD4omR5IWB2KynivBQczo3+wF1cCkjzvptnI9Q0sPU66ilw== + dependencies: + hasown "^2.0.0" + +is-core-module@^2.13.0: + version "2.13.0" + resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.13.0.tgz#bb52aa6e2cbd49a30c2ba68c42bf3435ba6072db" + integrity sha512-Z7dk6Qo8pOCp3l4tsX2C5ZVas4V+UxwQodwZhLopL91TX8UyyHEXafPcyoeeWuLrwzHcr3igO78wNLwHJHsMCQ== + dependencies: + has "^1.0.3" + +is-date-object@^1.0.1: + version "1.0.5" + resolved "https://registry.yarnpkg.com/is-date-object/-/is-date-object-1.0.5.tgz#0841d5536e724c25597bf6ea62e1bd38298df31f" + integrity sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ== + dependencies: + has-tostringtag "^1.0.0" + +is-docker@^2.0.0: + version "2.2.1" + resolved "https://registry.yarnpkg.com/is-docker/-/is-docker-2.2.1.tgz#33eeabe23cfe86f14bde4408a02c0cfb853acdaa" + integrity sha512-F+i2BKsFrH66iaUFc0woD8sLy8getkwTwtOBjvs56Cx4CgJDeKQeqfz8wAYiSb8JOprWhHH5p77PbmYCvvUuXQ== + +is-docker@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/is-docker/-/is-docker-3.0.0.tgz#90093aa3106277d8a77a5910dbae71747e15a200" + integrity sha512-eljcgEDlEns/7AXFosB5K/2nCM4P7FQPkGc/DWLy5rmFEWvZayGrik1d9/QIY5nJ4f9YsVvBkA6kJpHn9rISdQ== + +is-extglob@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2" + integrity sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ== + +is-fullwidth-code-point@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz#f116f8064fe90b3f7844a38997c0b75051269f1d" + integrity sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg== + +is-glob@^4.0.0, is-glob@^4.0.1, is-glob@^4.0.3, is-glob@~4.0.1: + version "4.0.3" + resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-4.0.3.tgz#64f61e42cbbb2eec2071a9dac0b28ba1e65d5084" + integrity sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg== + dependencies: + is-extglob "^2.1.1" + +is-hex-prefixed@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz#7d8d37e6ad77e5d127148913c573e082d777f554" + integrity sha512-WvtOiug1VFrE9v1Cydwm+FnXd3+w9GaeVUss5W4v/SLy3UW00vP+6iNF2SdnfiBoLy4bTqVdkftNGTUeOFVsbA== + +is-inside-container@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/is-inside-container/-/is-inside-container-1.0.0.tgz#e81fba699662eb31dbdaf26766a61d4814717ea4" + integrity sha512-KIYLCCJghfHZxqjYBE7rEy0OBuTd5xCHS7tHVgvCLkx7StIoaxwNW3hCALgEUjFfeRk+MG/Qxmp/vtETEF3tRA== + dependencies: + is-docker "^3.0.0" + +is-negative-zero@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/is-negative-zero/-/is-negative-zero-2.0.2.tgz#7bf6f03a28003b8b3965de3ac26f664d765f3150" + integrity sha512-dqJvarLawXsFbNDeJW7zAz8ItJ9cd28YufuuFzh0G8pNHjJMnY08Dv7sYX2uF5UpQOwieAeOExEYAWWfu7ZZUA== + +is-number-object@^1.0.4: + version "1.0.7" + resolved "https://registry.yarnpkg.com/is-number-object/-/is-number-object-1.0.7.tgz#59d50ada4c45251784e9904f5246c742f07a42fc" + integrity sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ== + dependencies: + has-tostringtag "^1.0.0" + +is-number@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/is-number/-/is-number-7.0.0.tgz#7535345b896734d5f80c4d06c50955527a14f12b" + integrity sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng== + +is-path-inside@^3.0.3: + version "3.0.3" + resolved "https://registry.yarnpkg.com/is-path-inside/-/is-path-inside-3.0.3.tgz#d231362e53a07ff2b0e0ea7fed049161ffd16283" + integrity sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ== + +is-plain-obj@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/is-plain-obj/-/is-plain-obj-2.1.0.tgz#45e42e37fccf1f40da8e5f76ee21515840c09287" + integrity sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA== + +is-regex@^1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/is-regex/-/is-regex-1.1.4.tgz#eef5663cd59fa4c0ae339505323df6854bb15958" + integrity sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg== + dependencies: + call-bind "^1.0.2" + has-tostringtag "^1.0.0" + +is-shared-array-buffer@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/is-shared-array-buffer/-/is-shared-array-buffer-1.0.2.tgz#8f259c573b60b6a32d4058a1a07430c0a7344c79" + integrity sha512-sqN2UDu1/0y6uvXyStCOzyhAjCSlHceFoMKJW8W9EU9cvic/QdsZ0kEU93HEy3IUEFZIiH/3w+AH/UQbPHNdhA== + dependencies: + call-bind "^1.0.2" + +is-stream@^2.0.0: + version "2.0.1" + resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-2.0.1.tgz#fac1e3d53b97ad5a9d0ae9cef2389f5810a5c077" + integrity sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg== + +is-stream@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-3.0.0.tgz#e6bfd7aa6bef69f4f472ce9bb681e3e57b4319ac" + integrity sha512-LnQR4bZ9IADDRSkvpqMGvt/tEJWclzklNgSw48V5EAaAeDd6qGvN8ei6k5p0tvxSR171VmGyHuTiAOfxAbr8kA== + +is-string@^1.0.5, is-string@^1.0.7: + version "1.0.7" + resolved "https://registry.yarnpkg.com/is-string/-/is-string-1.0.7.tgz#0dd12bf2006f255bb58f695110eff7491eebc0fd" + integrity sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg== + dependencies: + has-tostringtag "^1.0.0" + +is-symbol@^1.0.2, is-symbol@^1.0.3: + version "1.0.4" + resolved "https://registry.yarnpkg.com/is-symbol/-/is-symbol-1.0.4.tgz#a6dac93b635b063ca6872236de88910a57af139c" + integrity sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg== + dependencies: + has-symbols "^1.0.2" + +is-typed-array@^1.1.10, is-typed-array@^1.1.12, is-typed-array@^1.1.9: + version "1.1.12" + resolved "https://registry.yarnpkg.com/is-typed-array/-/is-typed-array-1.1.12.tgz#d0bab5686ef4a76f7a73097b95470ab199c57d4a" + integrity sha512-Z14TF2JNG8Lss5/HMqt0//T9JeHXttXy5pH/DBU4vi98ozO2btxzq9MwYDZYnKwU8nRsz/+GVFVRDq3DkVuSPg== + dependencies: + which-typed-array "^1.1.11" + +is-unicode-supported@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz#3f26c76a809593b52bfa2ecb5710ed2779b522a7" + integrity sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw== + +is-weakref@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/is-weakref/-/is-weakref-1.0.2.tgz#9529f383a9338205e89765e0392efc2f100f06f2" + integrity sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ== + dependencies: + call-bind "^1.0.2" + +is-wsl@^2.2.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/is-wsl/-/is-wsl-2.2.0.tgz#74a4c76e77ca9fd3f932f290c17ea326cd157271" + integrity sha512-fKzAra0rGJUUBwGBgNkHZuToZcn+TtXHpeCgmkMJMMYx1sQDYaCSyjJBSCa2nH1DGm7s3n1oBnohoVTBaN7Lww== + dependencies: + is-docker "^2.0.0" + +isarray@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/isarray/-/isarray-0.0.1.tgz#8a18acfca9a8f4177e09abfc6038939b05d1eedf" + integrity sha512-D2S+3GLxWH+uhrNEcoh/fnmYeP8E8/zHl644d/jdA0g2uyXvy3sb0qxotE+ne0LtccHknQzWwZEzhak7oJ0COQ== + +isarray@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/isarray/-/isarray-2.0.5.tgz#8af1e4c1221244cc62459faf38940d4e644a5723" + integrity sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw== + +isarray@~1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11" + integrity sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ== + +isexe@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/isexe/-/isexe-2.0.0.tgz#e8fbf374dc556ff8947a10dcb0572d633f2cfa10" + integrity sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw== + +js-sdsl@^4.1.4: + version "4.4.2" + resolved "https://registry.yarnpkg.com/js-sdsl/-/js-sdsl-4.4.2.tgz#2e3c031b1f47d3aca8b775532e3ebb0818e7f847" + integrity sha512-dwXFwByc/ajSV6m5bcKAPwe4yDDF6D614pxmIi5odytzxRlwqF6nwoiCek80Ixc7Cvma5awClxrzFtxCQvcM8w== + +js-sha3@0.8.0, js-sha3@^0.8.0: + version "0.8.0" + resolved "https://registry.yarnpkg.com/js-sha3/-/js-sha3-0.8.0.tgz#b9b7a5da73afad7dedd0f8c463954cbde6818840" + integrity sha512-gF1cRrHhIzNfToc802P800N8PpXS+evLLXfsVpowqmAFR9uwbi89WvXg2QspOmXL8QL86J4T1EpFu+yUkwJY3Q== + +js-tokens@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-4.0.0.tgz#19203fb59991df98e3a287050d4647cdeaf32499" + integrity sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ== + +js-yaml@4.1.0, js-yaml@^4.1.0: + version "4.1.0" + resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-4.1.0.tgz#c1fb65f8f5017901cdd2c951864ba18458a10602" + integrity sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA== + dependencies: + argparse "^2.0.1" + +json-buffer@3.0.1: + version "3.0.1" + resolved "https://registry.yarnpkg.com/json-buffer/-/json-buffer-3.0.1.tgz#9338802a30d3b6605fbe0613e094008ca8c05a13" + integrity sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ== + +json-parse-even-better-errors@^2.3.0: + version "2.3.1" + resolved "https://registry.yarnpkg.com/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz#7c47805a94319928e05777405dc12e1f7a4ee02d" + integrity sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w== + +json-schema-traverse@^0.4.1: + version "0.4.1" + resolved "https://registry.yarnpkg.com/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz#69f6a87d9513ab8bb8fe63bdb0979c448e684660" + integrity sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg== + +json-schema-traverse@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz#ae7bcb3656ab77a73ba5c49bf654f38e6b6860e2" + integrity sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug== + +json-stable-stringify-without-jsonify@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz#9db7b59496ad3f3cfef30a75142d2d930ad72651" + integrity sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw== + +json5@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/json5/-/json5-1.0.2.tgz#63d98d60f21b313b77c4d6da18bfa69d80e1d593" + integrity sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA== + dependencies: + minimist "^1.2.0" + +jsonc-parser@~3.2.0: + version "3.2.0" + resolved "https://registry.yarnpkg.com/jsonc-parser/-/jsonc-parser-3.2.0.tgz#31ff3f4c2b9793f89c67212627c51c6394f88e76" + integrity sha512-gfFQZrcTc8CnKXp6Y4/CBT3fTc0OVuDofpre4aEeEpSBPV5X5v4+Vmx+8snU7RLPrNHPKSgLxGo9YuQzz20o+w== + +jsonfile@^2.1.0: + version "2.4.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-2.4.0.tgz#3736a2b428b87bbda0cc83b53fa3d633a35c2ae8" + integrity sha512-PKllAqbgLgxHaj8TElYymKCAgrASebJrWpTnEkOaTowt23VKXXN0sUeriJ+eh7y6ufb/CC5ap11pz71/cM0hUw== + optionalDependencies: + graceful-fs "^4.1.6" + +jsonfile@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-4.0.0.tgz#8771aae0799b64076b76640fca058f9c10e33ecb" + integrity sha512-m6F1R3z8jjlf2imQHS2Qez5sjKWQzbuuhuJ/FKYFRZvPE3PuHcSMVZzfsLhGVOkfd20obL5SWEBew5ShlquNxg== + optionalDependencies: + graceful-fs "^4.1.6" + +jsonfile@^6.0.1: + version "6.1.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-6.1.0.tgz#bc55b2634793c679ec6403094eb13698a6ec0aae" + integrity sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ== + dependencies: + universalify "^2.0.0" + optionalDependencies: + graceful-fs "^4.1.6" + +jsonparse@^1.2.0: + version "1.3.1" + resolved "https://registry.yarnpkg.com/jsonparse/-/jsonparse-1.3.1.tgz#3f4dae4a91fac315f71062f8521cc239f1366280" + integrity sha512-POQXvpdL69+CluYsillJ7SUhKvytYjW9vG/GKpnf+xP8UWgYEM/RaMzHHofbALDiKbbP1W8UEYmgGl39WkPZsg== + +keccak@^3.0.0, keccak@^3.0.2: + version "3.0.3" + resolved "https://registry.yarnpkg.com/keccak/-/keccak-3.0.3.tgz#4bc35ad917be1ef54ff246f904c2bbbf9ac61276" + integrity sha512-JZrLIAJWuZxKbCilMpNz5Vj7Vtb4scDG3dMXLOsbzBmQGyjwE61BbW7bJkfKKCShXiQZt3T6sBgALRtmd+nZaQ== + dependencies: + node-addon-api "^2.0.0" + node-gyp-build "^4.2.0" + readable-stream "^3.6.0" + +keyv@^4.5.3: + version "4.5.4" + resolved "https://registry.yarnpkg.com/keyv/-/keyv-4.5.4.tgz#a879a99e29452f942439f2a405e3af8b31d4de93" + integrity sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw== + dependencies: + json-buffer "3.0.1" + +klaw@^1.0.0: + version "1.3.1" + resolved "https://registry.yarnpkg.com/klaw/-/klaw-1.3.1.tgz#4088433b46b3b1ba259d78785d8e96f73ba02439" + integrity sha512-TED5xi9gGQjGpNnvRWknrwAB1eL5GciPfVFOt3Vk1OJCVDQbzuSfrF3hkUQKlsgKrG1F+0t5W0m+Fje1jIt8rw== + optionalDependencies: + graceful-fs "^4.1.9" + +level-supports@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/level-supports/-/level-supports-4.0.1.tgz#431546f9d81f10ff0fea0e74533a0e875c08c66a" + integrity sha512-PbXpve8rKeNcZ9C1mUicC9auIYFyGpkV9/i6g76tLgANwWhtG2v7I4xNBUlkn3lE2/dZF3Pi0ygYGtLc4RXXdA== + +level-transcoder@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/level-transcoder/-/level-transcoder-1.0.1.tgz#f8cef5990c4f1283d4c86d949e73631b0bc8ba9c" + integrity sha512-t7bFwFtsQeD8cl8NIoQ2iwxA0CL/9IFw7/9gAjOonH0PWTTiRfY7Hq+Ejbsxh86tXobDQ6IOiddjNYIfOBs06w== + dependencies: + buffer "^6.0.3" + module-error "^1.0.1" + +level@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/level/-/level-8.0.0.tgz#41b4c515dabe28212a3e881b61c161ffead14394" + integrity sha512-ypf0jjAk2BWI33yzEaaotpq7fkOPALKAgDBxggO6Q9HGX2MRXn0wbP1Jn/tJv1gtL867+YOjOB49WaUF3UoJNQ== + dependencies: + browser-level "^1.0.1" + classic-level "^1.2.0" + +levn@^0.4.1: + version "0.4.1" + resolved "https://registry.yarnpkg.com/levn/-/levn-0.4.1.tgz#ae4562c007473b932a6200d403268dd2fffc6ade" + integrity sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ== + dependencies: + prelude-ls "^1.2.1" + type-check "~0.4.0" + +lines-and-columns@^1.1.6: + version "1.2.4" + resolved "https://registry.yarnpkg.com/lines-and-columns/-/lines-and-columns-1.2.4.tgz#eca284f75d2965079309dc0ad9255abb2ebc1632" + integrity sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg== + +linkify-it@^4.0.1: + version "4.0.1" + resolved "https://registry.yarnpkg.com/linkify-it/-/linkify-it-4.0.1.tgz#01f1d5e508190d06669982ba31a7d9f56a5751ec" + integrity sha512-C7bfi1UZmoj8+PQx22XyeXCuBlokoyWQL5pWSP+EI6nzRylyThouddufc2c1NDIcP9k5agmN9fLpA7VNJfIiqw== + dependencies: + uc.micro "^1.0.1" + +locate-path@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-2.0.0.tgz#2b568b265eec944c6d9c0de9c3dbbbca0354cd8e" + integrity sha512-NCI2kiDkyR7VeEKm27Kda/iQHyKJe1Bu0FlTbYp3CqJu+9IFe9bLyAjMxf5ZDDbEg+iMPzB5zYyUTSm8wVTKmA== + dependencies: + p-locate "^2.0.0" + path-exists "^3.0.0" + +locate-path@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-6.0.0.tgz#55321eb309febbc59c4801d931a72452a681d286" + integrity sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw== + dependencies: + p-locate "^5.0.0" + +lodash.camelcase@^4.3.0: + version "4.3.0" + resolved "https://registry.yarnpkg.com/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz#b28aa6288a2b9fc651035c7711f65ab6190331a6" + integrity sha512-TwuEnCnxbc3rAvhf/LbG7tJUDzhqXyFnv3dtzLOPgCG/hODL7WFnsbwktkD7yUV0RrreP/l1PALq/YSg6VvjlA== + +lodash.merge@^4.6.2: + version "4.6.2" + resolved "https://registry.yarnpkg.com/lodash.merge/-/lodash.merge-4.6.2.tgz#558aa53b43b661e1925a0afdfa36a9a1085fe57a" + integrity sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ== + +lodash.truncate@^4.4.2: + version "4.4.2" + resolved "https://registry.yarnpkg.com/lodash.truncate/-/lodash.truncate-4.4.2.tgz#5a350da0b1113b837ecfffd5812cbe58d6eae193" + integrity sha512-jttmRe7bRse52OsWIMDLaXxWqRAmtIUccAQ3garviCqJjafXOfNMO0yMfNpdD6zbGaTU0P5Nz7e7gAT6cKmJRw== + +lodash@^4.17.11, lodash@^4.17.15, lodash@^4.17.21: + version "4.17.21" + resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.21.tgz#679591c564c3bffaae8454cf0b3df370c3d6911c" + integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg== + +log-symbols@4.1.0: + version "4.1.0" + resolved "https://registry.yarnpkg.com/log-symbols/-/log-symbols-4.1.0.tgz#3fbdbb95b4683ac9fc785111e792e558d4abd503" + integrity sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg== + dependencies: + chalk "^4.1.0" + is-unicode-supported "^0.1.0" + +loupe@^2.3.1: + version "2.3.6" + resolved "https://registry.yarnpkg.com/loupe/-/loupe-2.3.6.tgz#76e4af498103c532d1ecc9be102036a21f787b53" + integrity sha512-RaPMZKiMy8/JruncMU5Bt6na1eftNoo++R4Y+N2FrxkDVTrGvcyzFTsaGif4QTeKESheMGegbhw6iUAq+5A8zA== + dependencies: + get-func-name "^2.0.0" + +lru-cache@^5.1.1: + version "5.1.1" + resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-5.1.1.tgz#1da27e6710271947695daf6848e847f01d84b920" + integrity sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w== + dependencies: + yallist "^3.0.2" + +lru-cache@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-6.0.0.tgz#6d6fe6570ebd96aaf90fcad1dafa3b2566db3a94" + integrity sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA== + dependencies: + yallist "^4.0.0" + +lru_map@^0.3.3: + version "0.3.3" + resolved "https://registry.yarnpkg.com/lru_map/-/lru_map-0.3.3.tgz#b5c8351b9464cbd750335a79650a0ec0e56118dd" + integrity sha512-Pn9cox5CsMYngeDbmChANltQl+5pi6XmTrraMSzhPmMBbmgcxmqWry0U3PGapCU1yB4/LqCcom7qhHZiF/jGfQ== + +make-error@^1.1.1: + version "1.3.6" + resolved "https://registry.yarnpkg.com/make-error/-/make-error-1.3.6.tgz#2eb2e37ea9b67c4891f684a1394799af484cf7a2" + integrity sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw== + +markdown-it@13.0.1: + version "13.0.1" + resolved "https://registry.yarnpkg.com/markdown-it/-/markdown-it-13.0.1.tgz#c6ecc431cacf1a5da531423fc6a42807814af430" + integrity sha512-lTlxriVoy2criHP0JKRhO2VDG9c2ypWCsT237eDiLqi09rmbKoUetyGHq2uOIRoRS//kfoJckS0eUzzkDR+k2Q== + dependencies: + argparse "^2.0.1" + entities "~3.0.1" + linkify-it "^4.0.1" + mdurl "^1.0.1" + uc.micro "^1.0.5" + +markdownlint-cli@^0.33.0: + version "0.33.0" + resolved "https://registry.yarnpkg.com/markdownlint-cli/-/markdownlint-cli-0.33.0.tgz#703af1234c32c309ab52fcd0e8bc797a34e2b096" + integrity sha512-zMK1oHpjYkhjO+94+ngARiBBrRDEUMzooDHBAHtmEIJ9oYddd9l3chCReY2mPlecwH7gflQp1ApilTo+o0zopQ== + dependencies: + commander "~9.4.1" + get-stdin "~9.0.0" + glob "~8.0.3" + ignore "~5.2.4" + js-yaml "^4.1.0" + jsonc-parser "~3.2.0" + markdownlint "~0.27.0" + minimatch "~5.1.2" + run-con "~1.2.11" + +markdownlint@~0.27.0: + version "0.27.0" + resolved "https://registry.yarnpkg.com/markdownlint/-/markdownlint-0.27.0.tgz#9dabf7710a4999e2835e3c68317f1acd0bc89049" + integrity sha512-HtfVr/hzJJmE0C198F99JLaeada+646B5SaG2pVoEakLFI6iRGsvMqrnnrflq8hm1zQgwskEgqSnhDW11JBp0w== + dependencies: + markdown-it "13.0.1" + +mcl-wasm@^0.7.1: + version "0.7.9" + resolved "https://registry.yarnpkg.com/mcl-wasm/-/mcl-wasm-0.7.9.tgz#c1588ce90042a8700c3b60e40efb339fc07ab87f" + integrity sha512-iJIUcQWA88IJB/5L15GnJVnSQJmf/YaxxV6zRavv83HILHaJQb6y0iFyDMdDO0gN8X37tdxmAOrH/P8B6RB8sQ== + +md5.js@^1.3.4: + version "1.3.5" + resolved "https://registry.yarnpkg.com/md5.js/-/md5.js-1.3.5.tgz#b5d07b8e3216e3e27cd728d72f70d1e6a342005f" + integrity sha512-xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg== + dependencies: + hash-base "^3.0.0" + inherits "^2.0.1" + safe-buffer "^5.1.2" + +mdurl@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/mdurl/-/mdurl-1.0.1.tgz#fe85b2ec75a59037f2adfec100fd6c601761152e" + integrity sha512-/sKlQJCBYVY9Ers9hqzKou4H6V5UWc/M59TH2dvkt+84itfnq7uFOMLpOiOS4ujvHP4etln18fmIxA5R5fll0g== + +memory-level@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/memory-level/-/memory-level-1.0.0.tgz#7323c3fd368f9af2f71c3cd76ba403a17ac41692" + integrity sha512-UXzwewuWeHBz5krr7EvehKcmLFNoXxGcvuYhC41tRnkrTbJohtS7kVn9akmgirtRygg+f7Yjsfi8Uu5SGSQ4Og== + dependencies: + abstract-level "^1.0.0" + functional-red-black-tree "^1.0.1" + module-error "^1.0.1" + +memorystream@^0.3.1: + version "0.3.1" + resolved "https://registry.yarnpkg.com/memorystream/-/memorystream-0.3.1.tgz#86d7090b30ce455d63fbae12dda51a47ddcaf9b2" + integrity sha512-S3UwM3yj5mtUSEfP41UZmt/0SCoVYUcU1rkXv+BQ5Ig8ndL4sPoJNBUJERafdPb5jjHJGuMgytgKvKIf58XNBw== + +merge-stream@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/merge-stream/-/merge-stream-2.0.0.tgz#52823629a14dd00c9770fb6ad47dc6310f2c1f60" + integrity sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w== + +merge2@^1.3.0, merge2@^1.4.1: + version "1.4.1" + resolved "https://registry.yarnpkg.com/merge2/-/merge2-1.4.1.tgz#4368892f885e907455a6fd7dc55c0c9d404990ae" + integrity sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg== + +micromatch@^4.0.4: + version "4.0.5" + resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-4.0.5.tgz#bc8999a7cbbf77cdc89f132f6e467051b49090c6" + integrity sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA== + dependencies: + braces "^3.0.2" + picomatch "^2.3.1" + +mimic-fn@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/mimic-fn/-/mimic-fn-2.1.0.tgz#7ed2c2ccccaf84d3ffcb7a69b57711fc2083401b" + integrity sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg== + +mimic-fn@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/mimic-fn/-/mimic-fn-4.0.0.tgz#60a90550d5cb0b239cca65d893b1a53b29871ecc" + integrity sha512-vqiC06CuhBTUdZH+RYl8sFrL096vA45Ok5ISO6sE/Mr1jRbGH4Csnhi8f3wKVl7x8mO4Au7Ir9D3Oyv1VYMFJw== + +minimalistic-assert@^1.0.0, minimalistic-assert@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz#2e194de044626d4a10e7f7fbc00ce73e83e4d5c7" + integrity sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A== + +minimalistic-crypto-utils@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz#f6c00c1c0b082246e5c4d99dfb8c7c083b2b582a" + integrity sha512-JIYlbt6g8i5jKfJ3xz7rF0LXmv2TkDxBLUkiBeZ7bAx4GnnNMr8xFpGnOxn6GhTEHx3SjRrZEoU+j04prX1ktg== + +minimatch@5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.0.1.tgz#fb9022f7528125187c92bd9e9b6366be1cf3415b" + integrity sha512-nLDxIFRyhDblz3qMuq+SoRZED4+miJ/G+tdDrjkkkRnjAsBexeGpgjLEQ0blJy7rHhR2b93rhQY4SvyWu9v03g== + dependencies: + brace-expansion "^2.0.1" + +minimatch@^3.0.4, minimatch@^3.0.5, minimatch@^3.1.1, minimatch@^3.1.2: + version "3.1.2" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.1.2.tgz#19cd194bfd3e428f049a70817c038d89ab4be35b" + integrity sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw== + dependencies: + brace-expansion "^1.1.7" + +minimatch@^5.0.1, minimatch@~5.1.2: + version "5.1.6" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.1.6.tgz#1cfcb8cf5522ea69952cd2af95ae09477f122a96" + integrity sha512-lKwV/1brpG6mBUFHtb7NUmtABCb2WZZmm2wNiOA5hAb8VdCS4B3dtMWyvcoViccwAW/COERjXLt0zP1zXUN26g== + dependencies: + brace-expansion "^2.0.1" + +minimatch@^7.4.3: + version "7.4.6" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-7.4.6.tgz#845d6f254d8f4a5e4fd6baf44d5f10c8448365fb" + integrity sha512-sBz8G/YjVniEz6lKPNpKxXwazJe4c19fEfV2GDMX6AjFz+MX9uDWIZW8XreVhkFW3fkIdTv/gxWr/Kks5FFAVw== + dependencies: + brace-expansion "^2.0.1" + +minimist@^1.2.0, minimist@^1.2.6, minimist@^1.2.8: + version "1.2.8" + resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.8.tgz#c1a464e7693302e082a075cee0c057741ac4772c" + integrity sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA== + +mkdirp-classic@^0.5.2: + version "0.5.3" + resolved "https://registry.yarnpkg.com/mkdirp-classic/-/mkdirp-classic-0.5.3.tgz#fa10c9115cc6d8865be221ba47ee9bed78601113" + integrity sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A== + +mkdirp@^0.5.1: + version "0.5.6" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-0.5.6.tgz#7def03d2432dcae4ba1d611445c48396062255f6" + integrity sha512-FP+p8RB8OWpF3YZBCrP5gtADmtXApB5AMLn+vdyA+PyxCjrCs00mjyUozssO33cwDeT3wNGdLxJ5M//YqtHAJw== + dependencies: + minimist "^1.2.6" + +mkdirp@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-1.0.4.tgz#3eb5ed62622756d79a5f0e2a221dfebad75c2f7e" + integrity sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw== + +mkdirp@^2.1.6: + version "2.1.6" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-2.1.6.tgz#964fbcb12b2d8c5d6fbc62a963ac95a273e2cc19" + integrity sha512-+hEnITedc8LAtIP9u3HJDFIdcLV2vXP33sqLLIzkv1Db1zO/1OxbvYf0Y1OC/S/Qo5dxHXepofhmxL02PsKe+A== + +mnemonist@^0.38.0: + version "0.38.5" + resolved "https://registry.yarnpkg.com/mnemonist/-/mnemonist-0.38.5.tgz#4adc7f4200491237fe0fa689ac0b86539685cade" + integrity sha512-bZTFT5rrPKtPJxj8KSV0WkPyNxl72vQepqqVUAW2ARUpUSF2qXMB6jZj7hW5/k7C1rtpzqbD/IIbJwLXUjCHeg== + dependencies: + obliterator "^2.0.0" + +mocha@^10.0.0: + version "10.2.0" + resolved "https://registry.yarnpkg.com/mocha/-/mocha-10.2.0.tgz#1fd4a7c32ba5ac372e03a17eef435bd00e5c68b8" + integrity sha512-IDY7fl/BecMwFHzoqF2sg/SHHANeBoMMXFlS9r0OXKDssYE1M5O43wUY/9BVPeIvfH2zmEbBfseqN9gBQZzXkg== + dependencies: + ansi-colors "4.1.1" + browser-stdout "1.3.1" + chokidar "3.5.3" + debug "4.3.4" + diff "5.0.0" + escape-string-regexp "4.0.0" + find-up "5.0.0" + glob "7.2.0" + he "1.2.0" + js-yaml "4.1.0" + log-symbols "4.1.0" + minimatch "5.0.1" + ms "2.1.3" + nanoid "3.3.3" + serialize-javascript "6.0.0" + strip-json-comments "3.1.1" + supports-color "8.1.1" + workerpool "6.2.1" + yargs "16.2.0" + yargs-parser "20.2.4" + yargs-unparser "2.0.0" + +module-error@^1.0.1, module-error@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/module-error/-/module-error-1.0.2.tgz#8d1a48897ca883f47a45816d4fb3e3c6ba404d86" + integrity sha512-0yuvsqSCv8LbaOKhnsQ/T5JhyFlCYLPXK3U2sgV10zoKQwzs/MyfuQUOZQ1V/6OCOJsK/TRgNVrPuPDqtdMFtA== + +ms@2.1.2: + version "2.1.2" + resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.2.tgz#d09d1f357b443f493382a8eb3ccd183872ae6009" + integrity sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w== + +ms@2.1.3, ms@^2.1.1: + version "2.1.3" + resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.3.tgz#574c8138ce1d2b5861f0b44579dbadd60c6615b2" + integrity sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA== + +mz@^2.7.0: + version "2.7.0" + resolved "https://registry.yarnpkg.com/mz/-/mz-2.7.0.tgz#95008057a56cafadc2bc63dde7f9ff6955948e32" + integrity sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q== + dependencies: + any-promise "^1.0.0" + object-assign "^4.0.1" + thenify-all "^1.0.0" + +nan@^2.17.0: + version "2.17.0" + resolved "https://registry.yarnpkg.com/nan/-/nan-2.17.0.tgz#c0150a2368a182f033e9aa5195ec76ea41a199cb" + integrity sha512-2ZTgtl0nJsO0KQCjEpxcIr5D+Yv90plTitZt9JBfQvVJDS5seMl3FOvsh3+9CoYWXf/1l5OaZzzF6nDm4cagaQ== + +nanoid@3.3.3: + version "3.3.3" + resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.3.3.tgz#fd8e8b7aa761fe807dba2d1b98fb7241bb724a25" + integrity sha512-p1sjXuopFs0xg+fPASzQ28agW1oHD7xDsd9Xkf3T15H3c/cifrFHVwrh74PdoklAPi+i7MdRsE47vm2r6JoB+w== + +napi-macros@^2.2.2: + version "2.2.2" + resolved "https://registry.yarnpkg.com/napi-macros/-/napi-macros-2.2.2.tgz#817fef20c3e0e40a963fbf7b37d1600bd0201044" + integrity sha512-hmEVtAGYzVQpCKdbQea4skABsdXW4RUh5t5mJ2zzqowJS2OyXZTU1KhDVFhx+NlWZ4ap9mqR9TcDO3LTTttd+g== + +natural-compare@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/natural-compare/-/natural-compare-1.4.0.tgz#4abebfeed7541f2c27acfb29bdbbd15c8d5ba4f7" + integrity sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw== + +node-addon-api@^2.0.0: + version "2.0.2" + resolved "https://registry.yarnpkg.com/node-addon-api/-/node-addon-api-2.0.2.tgz#432cfa82962ce494b132e9d72a15b29f71ff5d32" + integrity sha512-Ntyt4AIXyaLIuMHF6IOoTakB3K+RWxwtsHNRxllEoA6vPwP9o4866g6YWDLUdnucilZhmkxiHwHr11gAENw+QA== + +node-fetch@^2.6.0: + version "2.7.0" + resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.7.0.tgz#d0f0fa6e3e2dc1d27efcd8ad99d550bda94d187d" + integrity sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A== + dependencies: + whatwg-url "^5.0.0" + +node-gyp-build@^4.2.0, node-gyp-build@^4.3.0: + version "4.6.1" + resolved "https://registry.yarnpkg.com/node-gyp-build/-/node-gyp-build-4.6.1.tgz#24b6d075e5e391b8d5539d98c7fc5c210cac8a3e" + integrity sha512-24vnklJmyRS8ViBNI8KbtK/r/DmXQMRiOMXTNz2nrTnAYUwjmEEbnnpB/+kt+yWRv73bPsSPRFddrcIbAxSiMQ== + +normalize-path@^3.0.0, normalize-path@~3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/normalize-path/-/normalize-path-3.0.0.tgz#0dcd69ff23a1c9b11fd0978316644a0388216a65" + integrity sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA== + +npm-run-path@^4.0.1: + version "4.0.1" + resolved "https://registry.yarnpkg.com/npm-run-path/-/npm-run-path-4.0.1.tgz#b7ecd1e5ed53da8e37a55e1c2269e0b97ed748ea" + integrity sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw== + dependencies: + path-key "^3.0.0" + +npm-run-path@^5.1.0: + version "5.1.0" + resolved "https://registry.yarnpkg.com/npm-run-path/-/npm-run-path-5.1.0.tgz#bc62f7f3f6952d9894bd08944ba011a6ee7b7e00" + integrity sha512-sJOdmRGrY2sjNTRMbSvluQqg+8X7ZK61yvzBEIDhz4f8z1TZFYABsqjjCBd/0PUNE9M6QDgHJXQkGUEm7Q+l9Q== + dependencies: + path-key "^4.0.0" + +object-assign@^4.0.1: + version "4.1.1" + resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863" + integrity sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg== + +object-inspect@^1.13.1, object-inspect@^1.9.0: + version "1.13.1" + resolved "https://registry.yarnpkg.com/object-inspect/-/object-inspect-1.13.1.tgz#b96c6109324ccfef6b12216a956ca4dc2ff94bc2" + integrity sha512-5qoj1RUiKOMsCCNLV1CBiPYE10sziTsnmNxkAI/rZhiD63CF7IqdFGC/XzjWjpSgLf0LxXX3bDFIh0E18f6UhQ== + +object-keys@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/object-keys/-/object-keys-1.1.1.tgz#1c47f272df277f3b1daf061677d9c82e2322c60e" + integrity sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA== + +object.assign@^4.1.4: + version "4.1.4" + resolved "https://registry.yarnpkg.com/object.assign/-/object.assign-4.1.4.tgz#9673c7c7c351ab8c4d0b516f4343ebf4dfb7799f" + integrity sha512-1mxKf0e58bvyjSCtKYY4sRe9itRk3PJpquJOjeIkz885CczcI4IvJJDLPS72oowuSh+pBxUFROpX+TU++hxhZQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.1.4" + has-symbols "^1.0.3" + object-keys "^1.1.1" + +object.fromentries@^2.0.7: + version "2.0.7" + resolved "https://registry.yarnpkg.com/object.fromentries/-/object.fromentries-2.0.7.tgz#71e95f441e9a0ea6baf682ecaaf37fa2a8d7e616" + integrity sha512-UPbPHML6sL8PI/mOqPwsH4G6iyXcCGzLin8KvEPenOZN5lpCNBZZQ+V62vdjB1mQHrmqGQt5/OJzemUA+KJmEA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + +object.groupby@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/object.groupby/-/object.groupby-1.0.1.tgz#d41d9f3c8d6c778d9cbac86b4ee9f5af103152ee" + integrity sha512-HqaQtqLnp/8Bn4GL16cj+CUYbnpe1bh0TtEaWvybszDG4tgxCJuRpV8VGuvNaI1fAnI4lUJzDG55MXcOH4JZcQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + get-intrinsic "^1.2.1" + +object.values@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/object.values/-/object.values-1.1.7.tgz#617ed13272e7e1071b43973aa1655d9291b8442a" + integrity sha512-aU6xnDFYT3x17e/f0IiiwlGPTy2jzMySGfUB4fq6z7CV8l85CWHDk5ErhyhpfDHhrOMwGFhSQkhMGHaIotA6Ng== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + +obliterator@^2.0.0: + version "2.0.4" + resolved "https://registry.yarnpkg.com/obliterator/-/obliterator-2.0.4.tgz#fa650e019b2d075d745e44f1effeb13a2adbe816" + integrity sha512-lgHwxlxV1qIg1Eap7LgIeoBWIMFibOjbrYPIPJZcI1mmGAI2m3lNYpK12Y+GBdPQ0U1hRwSord7GIaawz962qQ== + +once@^1.3.0, once@^1.3.1, once@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1" + integrity sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w== + dependencies: + wrappy "1" + +onetime@^5.1.2: + version "5.1.2" + resolved "https://registry.yarnpkg.com/onetime/-/onetime-5.1.2.tgz#d0e96ebb56b07476df1dd9c4806e5237985ca45e" + integrity sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg== + dependencies: + mimic-fn "^2.1.0" + +onetime@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/onetime/-/onetime-6.0.0.tgz#7c24c18ed1fd2e9bca4bd26806a33613c77d34b4" + integrity sha512-1FlR+gjXK7X+AsAHso35MnyN5KqGwJRi/31ft6x0M194ht7S+rWAvd7PHss9xSKMzE0asv1pyIHaJYq+BbacAQ== + dependencies: + mimic-fn "^4.0.0" + +open@^9.1.0: + version "9.1.0" + resolved "https://registry.yarnpkg.com/open/-/open-9.1.0.tgz#684934359c90ad25742f5a26151970ff8c6c80b6" + integrity sha512-OS+QTnw1/4vrf+9hh1jc1jnYjzSG4ttTBB8UxOwAnInG3Uo4ssetzC1ihqaIHjLJnA5GGlRl6QlZXOTQhRBUvg== + dependencies: + default-browser "^4.0.0" + define-lazy-prop "^3.0.0" + is-inside-container "^1.0.0" + is-wsl "^2.2.0" + +optionator@^0.9.3: + version "0.9.3" + resolved "https://registry.yarnpkg.com/optionator/-/optionator-0.9.3.tgz#007397d44ed1872fdc6ed31360190f81814e2c64" + integrity sha512-JjCoypp+jKn1ttEFExxhetCKeJt9zhAgAve5FXHixTvFDW/5aEktX9bufBKLRRMdU7bNtpLfcGu94B3cdEJgjg== + dependencies: + "@aashutoshrathi/word-wrap" "^1.2.3" + deep-is "^0.1.3" + fast-levenshtein "^2.0.6" + levn "^0.4.1" + prelude-ls "^1.2.1" + type-check "^0.4.0" + +ordinal@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/ordinal/-/ordinal-1.0.3.tgz#1a3c7726a61728112f50944ad7c35c06ae3a0d4d" + integrity sha512-cMddMgb2QElm8G7vdaa02jhUNbTSrhsgAGUz1OokD83uJTwSUn+nKoNoKVVaRa08yF6sgfO7Maou1+bgLd9rdQ== + +os-tmpdir@~1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/os-tmpdir/-/os-tmpdir-1.0.2.tgz#bbe67406c79aa85c5cfec766fe5734555dfa1274" + integrity sha512-D2FR03Vir7FIu45XBY20mTb+/ZSWB00sjU9jdQXt83gDrI4Ztz5Fs7/yy74g2N5SVQY4xY1qDr4rNddwYRVX0g== + +p-limit@^1.1.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-1.3.0.tgz#b86bd5f0c25690911c7590fcbfc2010d54b3ccb8" + integrity sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q== + dependencies: + p-try "^1.0.0" + +p-limit@^3.0.2: + version "3.1.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-3.1.0.tgz#e1daccbe78d0d1388ca18c64fea38e3e57e3706b" + integrity sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ== + dependencies: + yocto-queue "^0.1.0" + +p-limit@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-4.0.0.tgz#914af6544ed32bfa54670b061cafcbd04984b644" + integrity sha512-5b0R4txpzjPWVw/cXXUResoD4hb6U/x9BH08L7nw+GN1sezDzPdxeRvpc9c433fZhBan/wusjbCsqwqm4EIBIQ== + dependencies: + yocto-queue "^1.0.0" + +p-locate@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-2.0.0.tgz#20a0103b222a70c8fd39cc2e580680f3dde5ec43" + integrity sha512-nQja7m7gSKuewoVRen45CtVfODR3crN3goVQ0DDZ9N3yHxgpkuBhZqsaiotSQRrADUrne346peY7kT3TSACykg== + dependencies: + p-limit "^1.1.0" + +p-locate@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-5.0.0.tgz#83c8315c6785005e3bd021839411c9e110e6d834" + integrity sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw== + dependencies: + p-limit "^3.0.2" + +p-map@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/p-map/-/p-map-4.0.0.tgz#bb2f95a5eda2ec168ec9274e06a747c3e2904d2b" + integrity sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ== + dependencies: + aggregate-error "^3.0.0" + +p-try@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/p-try/-/p-try-1.0.0.tgz#cbc79cdbaf8fd4228e13f621f2b1a237c1b207b3" + integrity sha512-U1etNYuMJoIz3ZXSrrySFjsXQTWOx2/jdi86L+2pRvph/qMKL6sbcCYdH23fqsbm8TH2Gn0OybpT4eSFlCVHww== + +parent-module@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/parent-module/-/parent-module-1.0.1.tgz#691d2709e78c79fae3a156622452d00762caaaa2" + integrity sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g== + dependencies: + callsites "^3.0.0" + +parse-json@^5.2.0: + version "5.2.0" + resolved "https://registry.yarnpkg.com/parse-json/-/parse-json-5.2.0.tgz#c76fc66dee54231c962b22bcc8a72cf2f99753cd" + integrity sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg== + dependencies: + "@babel/code-frame" "^7.0.0" + error-ex "^1.3.1" + json-parse-even-better-errors "^2.3.0" + lines-and-columns "^1.1.6" + +path-browserify@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/path-browserify/-/path-browserify-1.0.1.tgz#d98454a9c3753d5790860f16f68867b9e46be1fd" + integrity sha512-b7uo2UCUOYZcnF/3ID0lulOJi/bafxa1xPe7ZPsammBSpjSWQkjNxlt635YGS2MiR9GjvuXCtz2emr3jbsz98g== + +path-exists@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-3.0.0.tgz#ce0ebeaa5f78cb18925ea7d810d7b59b010fd515" + integrity sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ== + +path-exists@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-4.0.0.tgz#513bdbe2d3b95d7762e8c1137efa195c6c61b5b3" + integrity sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w== + +path-is-absolute@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f" + integrity sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg== + +path-key@^3.0.0, path-key@^3.1.0: + version "3.1.1" + resolved "https://registry.yarnpkg.com/path-key/-/path-key-3.1.1.tgz#581f6ade658cbba65a0d3380de7753295054f375" + integrity sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q== + +path-key@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/path-key/-/path-key-4.0.0.tgz#295588dc3aee64154f877adb9d780b81c554bf18" + integrity sha512-haREypq7xkM7ErfgIyA0z+Bj4AGKlMSdlQE2jvJo6huWD1EdkKYV+G/T4nq0YEF2vgTT8kqMFKo1uHn950r4SQ== + +path-parse@^1.0.6, path-parse@^1.0.7: + version "1.0.7" + resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.7.tgz#fbc114b60ca42b30d9daf5858e4bd68bbedb6735" + integrity sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw== + +path-type@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/path-type/-/path-type-4.0.0.tgz#84ed01c0a7ba380afe09d90a8c180dcd9d03043b" + integrity sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw== + +pathington@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/pathington/-/pathington-1.1.7.tgz#caf2d2db899a31fea4e81e3657af6acde5171903" + integrity sha512-JxzhUzagDfNIOm4qqwQqP3rWeo7rNNOfIahy4n+3GTEdwXLqw5cJHUR0soSopQtNEv763lzxb6eA2xBllpR8zw== + +pathval@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/pathval/-/pathval-1.1.1.tgz#8534e77a77ce7ac5a2512ea21e0fdb8fcf6c3d8d" + integrity sha512-Dp6zGqpTdETdR63lehJYPeIOqpiNBNtc7BpWSLrOje7UaIsE5aY92r/AunQA7rsXvet3lrJ3JnZX29UPTKXyKQ== + +pbkdf2@^3.0.17: + version "3.1.2" + resolved "https://registry.yarnpkg.com/pbkdf2/-/pbkdf2-3.1.2.tgz#dd822aa0887580e52f1a039dc3eda108efae3075" + integrity sha512-iuh7L6jA7JEGu2WxDwtQP1ddOpaJNC4KlDEFfdQajSGgGPNi4OyDc2R7QnbY2bR9QjBVGwgvTdNJZoE7RaxUMA== + dependencies: + create-hash "^1.1.2" + create-hmac "^1.1.4" + ripemd160 "^2.0.1" + safe-buffer "^5.0.1" + sha.js "^2.4.8" + +picocolors@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/picocolors/-/picocolors-1.0.0.tgz#cb5bdc74ff3f51892236eaf79d68bc44564ab81c" + integrity sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ== + +picomatch@^2.0.4, picomatch@^2.2.1, picomatch@^2.3.1: + version "2.3.1" + resolved "https://registry.yarnpkg.com/picomatch/-/picomatch-2.3.1.tgz#3ba3833733646d9d3e4995946c1365a67fb07a42" + integrity sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA== + +pluralize@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/pluralize/-/pluralize-8.0.0.tgz#1a6fa16a38d12a1901e0320fa017051c539ce3b1" + integrity sha512-Nc3IT5yHzflTfbjgqWcCPpo7DaKy4FnpB0l/zCAW0Tc7jxAiuqSxHasntB3D7887LSrA93kDJ9IXovxJYxyLCA== + +prelude-ls@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/prelude-ls/-/prelude-ls-1.2.1.tgz#debc6489d7a6e6b0e7611888cec880337d316396" + integrity sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g== + +preprocess@^3.2.0: + version "3.2.0" + resolved "https://registry.yarnpkg.com/preprocess/-/preprocess-3.2.0.tgz#36b3e2c52331fbc6fabb26d4fd5709304b7e3675" + integrity sha512-cO+Rf+Ose/eD+ze8Hxd9p9nS1xT8thYqv8owG/V8+IS/Remd7Z17SvaRK/oJxp08yaM8zb+QTckDKJUul2pk7g== + dependencies: + xregexp "3.1.0" + +prettier-linter-helpers@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/prettier-linter-helpers/-/prettier-linter-helpers-1.0.0.tgz#d23d41fe1375646de2d0104d3454a3008802cf7b" + integrity sha512-GbK2cP9nraSSUF9N2XwUwqfzlAFlMNYYl+ShE/V+H8a9uNl/oUqB1w2EL54Jh0OlyRSd8RfWYJ3coVS4TROP2w== + dependencies: + fast-diff "^1.1.2" + +prettier-plugin-solidity@^1.1.3: + version "1.1.3" + resolved "https://registry.yarnpkg.com/prettier-plugin-solidity/-/prettier-plugin-solidity-1.1.3.tgz#9a35124f578404caf617634a8cab80862d726cba" + integrity sha512-fQ9yucPi2sBbA2U2Xjh6m4isUTJ7S7QLc/XDDsktqqxYfTwdYKJ0EnnywXHwCGAaYbQNK+HIYPL1OemxuMsgeg== + dependencies: + "@solidity-parser/parser" "^0.16.0" + semver "^7.3.8" + solidity-comments-extractor "^0.0.7" + +prettier@^2.1.2: + version "2.7.1" + resolved "https://registry.yarnpkg.com/prettier/-/prettier-2.7.1.tgz#e235806850d057f97bb08368a4f7d899f7760c64" + integrity sha512-ujppO+MkdPqoVINuDFDRLClm7D78qbDt0/NR+wp5FqEZOoTNAjPHWj17QRhu7geIHJfcNhRk1XVQmF8Bp3ye+g== + +prettier@^2.3.1, prettier@^2.8.3: + version "2.8.8" + resolved "https://registry.yarnpkg.com/prettier/-/prettier-2.8.8.tgz#e8c5d7e98a4305ffe3de2e1fc4aca1a71c28b1da" + integrity sha512-tdN8qQGvNjw4CHbY+XXk0JgCXn9QiF21a55rBe5LJAU+kDyC4WQn4+awm2Xfk2lQMk5fKup9XgzTZtGkjBdP9Q== + +prettier@^3.0.3: + version "3.0.3" + resolved "https://registry.yarnpkg.com/prettier/-/prettier-3.0.3.tgz#432a51f7ba422d1469096c0fdc28e235db8f9643" + integrity sha512-L/4pUDMxcNa8R/EthV08Zt42WBO4h1rarVtK0K+QJG0X187OLo7l699jWw0GKuwzkPQ//jMFA/8Xm6Fh3J/DAg== + +process-nextick-args@~2.0.0: + version "2.0.1" + resolved "https://registry.yarnpkg.com/process-nextick-args/-/process-nextick-args-2.0.1.tgz#7820d9b16120cc55ca9ae7792680ae7dba6d7fe2" + integrity sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag== + +proper-lockfile@^4.1.2: + version "4.1.2" + resolved "https://registry.yarnpkg.com/proper-lockfile/-/proper-lockfile-4.1.2.tgz#c8b9de2af6b2f1601067f98e01ac66baa223141f" + integrity sha512-TjNPblN4BwAWMXU8s9AEz4JmQxnD1NNL7bNOY/AKUzyamc379FWASUhc/K1pL2noVb+XmZKLL68cjzLsiOAMaA== + dependencies: + graceful-fs "^4.2.4" + retry "^0.12.0" + signal-exit "^3.0.2" + +pump@^1.0.0: + version "1.0.3" + resolved "https://registry.yarnpkg.com/pump/-/pump-1.0.3.tgz#5dfe8311c33bbf6fc18261f9f34702c47c08a954" + integrity sha512-8k0JupWme55+9tCVE+FS5ULT3K6AbgqrGa58lTT49RpyfwwcGedHqaC5LlQNdEAumn/wFsu6aPwkuPMioy8kqw== + dependencies: + end-of-stream "^1.1.0" + once "^1.3.1" + +pump@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/pump/-/pump-3.0.0.tgz#b4a2116815bde2f4e1ea602354e8c75565107a64" + integrity sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww== + dependencies: + end-of-stream "^1.1.0" + once "^1.3.1" + +punycode@^2.1.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.3.0.tgz#f67fa67c94da8f4d0cfff981aee4118064199b8f" + integrity sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA== + +queue-microtask@^1.2.2, queue-microtask@^1.2.3: + version "1.2.3" + resolved "https://registry.yarnpkg.com/queue-microtask/-/queue-microtask-1.2.3.tgz#4929228bbc724dfac43e0efb058caf7b6cfb6243" + integrity sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A== + +randombytes@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/randombytes/-/randombytes-2.1.0.tgz#df6f84372f0270dc65cdf6291349ab7a473d4f2a" + integrity sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ== + dependencies: + safe-buffer "^5.1.0" + +raw-body@^2.4.1: + version "2.5.2" + resolved "https://registry.yarnpkg.com/raw-body/-/raw-body-2.5.2.tgz#99febd83b90e08975087e8f1f9419a149366b68a" + integrity sha512-8zGqypfENjCIqGhgXToC8aB2r7YrBX+AQAfIPs/Mlk+BtPTztOvTS01NRW/3Eh60J+a48lt8qsCzirQ6loCVfA== + dependencies: + bytes "3.1.2" + http-errors "2.0.0" + iconv-lite "0.4.24" + unpipe "1.0.0" + +readable-stream@^2.2.2, readable-stream@^2.3.0, readable-stream@^2.3.5: + version "2.3.8" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.3.8.tgz#91125e8042bba1b9887f49345f6277027ce8be9b" + integrity sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA== + dependencies: + core-util-is "~1.0.0" + inherits "~2.0.3" + isarray "~1.0.0" + process-nextick-args "~2.0.0" + safe-buffer "~5.1.1" + string_decoder "~1.1.1" + util-deprecate "~1.0.1" + +readable-stream@^3.1.1, readable-stream@^3.4.0, readable-stream@^3.5.0, readable-stream@^3.6.0: + version "3.6.2" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-3.6.2.tgz#56a9b36ea965c00c5a93ef31eb111a0f11056967" + integrity sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA== + dependencies: + inherits "^2.0.3" + string_decoder "^1.1.1" + util-deprecate "^1.0.1" + +readable-stream@~1.0.26-4: + version "1.0.34" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-1.0.34.tgz#125820e34bc842d2f2aaafafe4c2916ee32c157c" + integrity sha512-ok1qVCJuRkNmvebYikljxJA/UEsKwLl2nI1OmaqAu4/UE+h0wKCHok4XkL/gvi39OacXvw59RJUOFUkDib2rHg== + dependencies: + core-util-is "~1.0.0" + inherits "~2.0.1" + isarray "0.0.1" + string_decoder "~0.10.x" + +readdirp@~3.6.0: + version "3.6.0" + resolved "https://registry.yarnpkg.com/readdirp/-/readdirp-3.6.0.tgz#74a370bd857116e245b29cc97340cd431a02a6c7" + integrity sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA== + dependencies: + picomatch "^2.2.1" + +reduce-flatten@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/reduce-flatten/-/reduce-flatten-2.0.0.tgz#734fd84e65f375d7ca4465c69798c25c9d10ae27" + integrity sha512-EJ4UNY/U1t2P/2k6oqotuX2Cc3T6nxJwsM0N0asT7dhrtH1ltUxDn4NalSYmPE2rCkVpcf/X6R0wDwcFpzhd4w== + +regexp.prototype.flags@^1.5.1: + version "1.5.1" + resolved "https://registry.yarnpkg.com/regexp.prototype.flags/-/regexp.prototype.flags-1.5.1.tgz#90ce989138db209f81492edd734183ce99f9677e" + integrity sha512-sy6TXMN+hnP/wMy+ISxg3krXx7BAtWVO4UouuCN/ziM9UEne0euamVNafDfvC83bRNr95y0V5iijeDQFUNpvrg== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + set-function-name "^2.0.0" + +require-directory@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/require-directory/-/require-directory-2.1.1.tgz#8c64ad5fd30dab1c976e2344ffe7f792a6a6df42" + integrity sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q== + +require-from-string@^2.0.0, require-from-string@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/require-from-string/-/require-from-string-2.0.2.tgz#89a7fdd938261267318eafe14f9c32e598c36909" + integrity sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw== + +resolve-from@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/resolve-from/-/resolve-from-4.0.0.tgz#4abcd852ad32dd7baabfe9b40e00a36db5f392e6" + integrity sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g== + +resolve-pkg-maps@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/resolve-pkg-maps/-/resolve-pkg-maps-1.0.0.tgz#616b3dc2c57056b5588c31cdf4b3d64db133720f" + integrity sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw== + +resolve@1.17.0: + version "1.17.0" + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.17.0.tgz#b25941b54968231cc2d1bb76a79cb7f2c0bf8444" + integrity sha512-ic+7JYiV8Vi2yzQGFWOkiZD5Z9z7O2Zhm9XMaTxdJExKasieFCr+yXZ/WmXsckHiKl12ar0y6XiXDx3m4RHn1w== + dependencies: + path-parse "^1.0.6" + +resolve@^1.10.0, resolve@^1.8.1: + version "1.22.4" + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.22.4.tgz#1dc40df46554cdaf8948a486a10f6ba1e2026c34" + integrity sha512-PXNdCiPqDqeUou+w1C2eTQbNfxKSuMxqTCuvlmmMsk1NWHL5fRrhY6Pl0qEYYc6+QqGClco1Qj8XnjPego4wfg== + dependencies: + is-core-module "^2.13.0" + path-parse "^1.0.7" + supports-preserve-symlinks-flag "^1.0.0" + +resolve@^1.22.4: + version "1.22.8" + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.22.8.tgz#b6c87a9f2aa06dfab52e3d70ac8cde321fa5a48d" + integrity sha512-oKWePCxqpd6FlLvGV1VU0x7bkPmmCNolxzjMf4NczoDnQcIWrAF+cPtZn5i6n+RfD2d9i0tzpKnG6Yk168yIyw== + dependencies: + is-core-module "^2.13.0" + path-parse "^1.0.7" + supports-preserve-symlinks-flag "^1.0.0" + +retry@^0.12.0: + version "0.12.0" + resolved "https://registry.yarnpkg.com/retry/-/retry-0.12.0.tgz#1b42a6266a21f07421d1b0b54b7dc167b01c013b" + integrity sha512-9LkiTwjUh6rT555DtE9rTX+BKByPfrMzEAtnlEtdEwr3Nkffwiihqe2bWADg+OQRjt9gl6ICdmB/ZFDCGAtSow== + +reusify@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/reusify/-/reusify-1.0.4.tgz#90da382b1e126efc02146e90845a88db12925d76" + integrity sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw== + +rimraf@^2.2.8: + version "2.7.1" + resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.7.1.tgz#35797f13a7fdadc566142c29d4f07ccad483e3ec" + integrity sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w== + dependencies: + glob "^7.1.3" + +rimraf@^3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-3.0.2.tgz#f1a5402ba6220ad52cc1282bac1ae3aa49fd061a" + integrity sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA== + dependencies: + glob "^7.1.3" + +ripemd160@^2.0.0, ripemd160@^2.0.1: + version "2.0.2" + resolved "https://registry.yarnpkg.com/ripemd160/-/ripemd160-2.0.2.tgz#a1c1a6f624751577ba5d07914cbc92850585890c" + integrity sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA== + dependencies: + hash-base "^3.0.0" + inherits "^2.0.1" + +rlp@^2.2.3: + version "2.2.7" + resolved "https://registry.yarnpkg.com/rlp/-/rlp-2.2.7.tgz#33f31c4afac81124ac4b283e2bd4d9720b30beaf" + integrity sha512-d5gdPmgQ0Z+AklL2NVXr/IoSjNZFfTVvQWzL/AM2AOcSzYP2xjlb0AC8YyCLc41MSNf6P6QVtjgPdmVtzb+4lQ== + dependencies: + bn.js "^5.2.0" + +run-applescript@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/run-applescript/-/run-applescript-5.0.0.tgz#e11e1c932e055d5c6b40d98374e0268d9b11899c" + integrity sha512-XcT5rBksx1QdIhlFOCtgZkB99ZEouFZ1E2Kc2LHqNW13U3/74YGdkQRmThTwxy4QIyookibDKYZOPqX//6BlAg== + dependencies: + execa "^5.0.0" + +run-con@~1.2.11: + version "1.2.12" + resolved "https://registry.yarnpkg.com/run-con/-/run-con-1.2.12.tgz#51c319910e45a3bd71ee773564a89d96635c8c64" + integrity sha512-5257ILMYIF4RztL9uoZ7V9Q97zHtNHn5bN3NobeAnzB1P3ASLgg8qocM2u+R18ttp+VEM78N2LK8XcNVtnSRrg== + dependencies: + deep-extend "^0.6.0" + ini "~3.0.0" + minimist "^1.2.8" + strip-json-comments "~3.1.1" + +run-parallel-limit@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/run-parallel-limit/-/run-parallel-limit-1.1.0.tgz#be80e936f5768623a38a963262d6bef8ff11e7ba" + integrity sha512-jJA7irRNM91jaKc3Hcl1npHsFLOXOoTkPCUL1JEa1R82O2miplXXRaGdjW/KM/98YQWDhJLiSs793CnXfblJUw== + dependencies: + queue-microtask "^1.2.2" + +run-parallel@^1.1.9: + version "1.2.0" + resolved "https://registry.yarnpkg.com/run-parallel/-/run-parallel-1.2.0.tgz#66d1368da7bdf921eb9d95bd1a9229e7f21a43ee" + integrity sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA== + dependencies: + queue-microtask "^1.2.2" + +rustbn.js@~0.2.0: + version "0.2.0" + resolved "https://registry.yarnpkg.com/rustbn.js/-/rustbn.js-0.2.0.tgz#8082cb886e707155fd1cb6f23bd591ab8d55d0ca" + integrity sha512-4VlvkRUuCJvr2J6Y0ImW7NvTCriMi7ErOAqWk1y69vAdoNIzCF3yPmgeNzx+RQTLEDFq5sHfscn1MwHxP9hNfA== + +safe-array-concat@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/safe-array-concat/-/safe-array-concat-1.0.1.tgz#91686a63ce3adbea14d61b14c99572a8ff84754c" + integrity sha512-6XbUAseYE2KtOuGueyeobCySj9L4+66Tn6KQMOPQJrAJEowYKW/YR/MGJZl7FdydUdaFu4LYyDZjxf4/Nmo23Q== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.2.1" + has-symbols "^1.0.3" + isarray "^2.0.5" + +safe-buffer@^5.0.1, safe-buffer@^5.1.0, safe-buffer@^5.1.1, safe-buffer@^5.1.2, safe-buffer@^5.2.0, safe-buffer@~5.2.0: + version "5.2.1" + resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6" + integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ== + +safe-buffer@~5.1.0, safe-buffer@~5.1.1: + version "5.1.2" + resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.1.2.tgz#991ec69d296e0313747d59bdfd2b745c35f8828d" + integrity sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g== + +safe-regex-test@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/safe-regex-test/-/safe-regex-test-1.0.0.tgz#793b874d524eb3640d1873aad03596db2d4f2295" + integrity sha512-JBUUzyOgEwXQY1NuPtvcj/qcBDbDmEvWufhlnXZIm75DEHp+afM1r1ujJpJsV/gSM4t59tpDyPi1sd6ZaPFfsA== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.1.3" + is-regex "^1.1.4" + +"safer-buffer@>= 2.1.2 < 3", safer-buffer@~2.1.0: + version "2.1.2" + resolved "https://registry.yarnpkg.com/safer-buffer/-/safer-buffer-2.1.2.tgz#44fa161b0187b9549dd84bb91802f9bd8385cd6a" + integrity sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg== + +scrypt-js@3.0.1, scrypt-js@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/scrypt-js/-/scrypt-js-3.0.1.tgz#d314a57c2aef69d1ad98a138a21fe9eafa9ee312" + integrity sha512-cdwTTnqPu0Hyvf5in5asVdZocVDTNRmR7XEcJuIzMjJeSHybHl7vpB66AzwTaIg6CLSbtjcxc8fqcySfnTkccA== + +secp256k1@^4.0.1: + version "4.0.3" + resolved "https://registry.yarnpkg.com/secp256k1/-/secp256k1-4.0.3.tgz#c4559ecd1b8d3c1827ed2d1b94190d69ce267303" + integrity sha512-NLZVf+ROMxwtEj3Xa562qgv2BK5e2WNmXPiOdVIPLgs6lyTzMvBq0aWTYMI5XCP9jZMVKOcqZLw/Wc4vDkuxhA== + dependencies: + elliptic "^6.5.4" + node-addon-api "^2.0.0" + node-gyp-build "^4.2.0" + +semver@^5.5.0, semver@^5.6.0: + version "5.7.2" + resolved "https://registry.yarnpkg.com/semver/-/semver-5.7.2.tgz#48d55db737c3287cd4835e17fa13feace1c41ef8" + integrity sha512-cBznnQ9KjJqU67B52RMC65CMarK2600WFnbkcaiwWq3xy/5haFJlshgnpjovMVJ+Hff49d8GEn0b87C5pDQ10g== + +semver@^6.3.0, semver@^6.3.1: + version "6.3.1" + resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.1.tgz#556d2ef8689146e46dcea4bfdd095f3434dffcb4" + integrity sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA== + +semver@^7.3.8, semver@^7.5.1, semver@^7.5.2, semver@^7.5.4: + version "7.5.4" + resolved "https://registry.yarnpkg.com/semver/-/semver-7.5.4.tgz#483986ec4ed38e1c6c48c34894a9182dbff68a6e" + integrity sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA== + dependencies: + lru-cache "^6.0.0" + +serialize-javascript@6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/serialize-javascript/-/serialize-javascript-6.0.0.tgz#efae5d88f45d7924141da8b5c3a7a7e663fefeb8" + integrity sha512-Qr3TosvguFt8ePWqsvRfrKyQXIiW+nGbYpy8XK24NQHE83caxWt+mIymTT19DGFbNWNLfEwsrkSmN64lVWB9ag== + dependencies: + randombytes "^2.1.0" + +set-function-length@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/set-function-length/-/set-function-length-1.1.1.tgz#4bc39fafb0307224a33e106a7d35ca1218d659ed" + integrity sha512-VoaqjbBJKiWtg4yRcKBQ7g7wnGnLV3M8oLvVWwOk2PdYY6PEFegR1vezXR0tw6fZGF9csVakIRjrJiy2veSBFQ== + dependencies: + define-data-property "^1.1.1" + get-intrinsic "^1.2.1" + gopd "^1.0.1" + has-property-descriptors "^1.0.0" + +set-function-name@^2.0.0: + version "2.0.1" + resolved "https://registry.yarnpkg.com/set-function-name/-/set-function-name-2.0.1.tgz#12ce38b7954310b9f61faa12701620a0c882793a" + integrity sha512-tMNCiqYVkXIZgc2Hnoy2IvC/f8ezc5koaRFkCjrpWzGpCd3qbZXPzVy9MAZzK1ch/X0jvSkojys3oqJN0qCmdA== + dependencies: + define-data-property "^1.0.1" + functions-have-names "^1.2.3" + has-property-descriptors "^1.0.0" + +setimmediate@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/setimmediate/-/setimmediate-1.0.5.tgz#290cbb232e306942d7d7ea9b83732ab7856f8285" + integrity sha512-MATJdZp8sLqDl/68LfQmbP8zKPLQNV6BIZoIgrscFDQ+RsvK/BxeDQOgyxKKoh0y/8h3BqVFnCqQ/gd+reiIXA== + +setprototypeof@1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/setprototypeof/-/setprototypeof-1.2.0.tgz#66c9a24a73f9fc28cbe66b09fed3d33dcaf1b424" + integrity sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw== + +sha.js@^2.4.0, sha.js@^2.4.8: + version "2.4.11" + resolved "https://registry.yarnpkg.com/sha.js/-/sha.js-2.4.11.tgz#37a5cf0b81ecbc6943de109ba2960d1b26584ae7" + integrity sha512-QMEp5B7cftE7APOjk5Y6xgrbWu+WkLVQwk8JNjZ8nKRciZaByEW6MubieAiToS7+dwvrjGhH8jRXz3MVd0AYqQ== + dependencies: + inherits "^2.0.1" + safe-buffer "^5.0.1" + +shebang-command@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/shebang-command/-/shebang-command-2.0.0.tgz#ccd0af4f8835fbdc265b82461aaf0c36663f34ea" + integrity sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA== + dependencies: + shebang-regex "^3.0.0" + +shebang-regex@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/shebang-regex/-/shebang-regex-3.0.0.tgz#ae16f1644d873ecad843b0307b143362d4c42172" + integrity sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A== + +side-channel@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/side-channel/-/side-channel-1.0.4.tgz#efce5c8fdc104ee751b25c58d4290011fa5ea2cf" + integrity sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw== + dependencies: + call-bind "^1.0.0" + get-intrinsic "^1.0.2" + object-inspect "^1.9.0" + +signal-exit@^3.0.2, signal-exit@^3.0.3, signal-exit@^3.0.7: + version "3.0.7" + resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.7.tgz#a9a1767f8af84155114eaabd73f99273c8f59ad9" + integrity sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ== + +slash@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/slash/-/slash-3.0.0.tgz#6539be870c165adbd5240220dbe361f1bc4d4634" + integrity sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q== + +slice-ansi@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/slice-ansi/-/slice-ansi-4.0.0.tgz#500e8dd0fd55b05815086255b3195adf2a45fe6b" + integrity sha512-qMCMfhY040cVHT43K9BFygqYbUPFZKHOg7K73mtTWJRb8pyP3fzf4Ixd5SzdEJQ6MRUg/WBnOLxghZtKKurENQ== + dependencies: + ansi-styles "^4.0.0" + astral-regex "^2.0.0" + is-fullwidth-code-point "^3.0.0" + +solc@0.7.3: + version "0.7.3" + resolved "https://registry.yarnpkg.com/solc/-/solc-0.7.3.tgz#04646961bd867a744f63d2b4e3c0701ffdc7d78a" + integrity sha512-GAsWNAjGzIDg7VxzP6mPjdurby3IkGCjQcM8GFYZT6RyaoUZKmMU6Y7YwG+tFGhv7dwZ8rmR4iwFDrrD99JwqA== + dependencies: + command-exists "^1.2.8" + commander "3.0.2" + follow-redirects "^1.12.1" + fs-extra "^0.30.0" + js-sha3 "0.8.0" + memorystream "^0.3.1" + require-from-string "^2.0.0" + semver "^5.5.0" + tmp "0.0.33" + +solhint@^3.6.2: + version "3.6.2" + resolved "https://registry.yarnpkg.com/solhint/-/solhint-3.6.2.tgz#2b2acbec8fdc37b2c68206a71ba89c7f519943fe" + integrity sha512-85EeLbmkcPwD+3JR7aEMKsVC9YrRSxd4qkXuMzrlf7+z2Eqdfm1wHWq1ffTuo5aDhoZxp2I9yF3QkxZOxOL7aQ== + dependencies: + "@solidity-parser/parser" "^0.16.0" + ajv "^6.12.6" + antlr4 "^4.11.0" + ast-parents "^0.0.1" + chalk "^4.1.2" + commander "^10.0.0" + cosmiconfig "^8.0.0" + fast-diff "^1.2.0" + glob "^8.0.3" + ignore "^5.2.4" + js-yaml "^4.1.0" + lodash "^4.17.21" + pluralize "^8.0.0" + semver "^7.5.2" + strip-ansi "^6.0.1" + table "^6.8.1" + text-table "^0.2.0" + optionalDependencies: + prettier "^2.8.3" + +solidity-comments-extractor@^0.0.7: + version "0.0.7" + resolved "https://registry.yarnpkg.com/solidity-comments-extractor/-/solidity-comments-extractor-0.0.7.tgz#99d8f1361438f84019795d928b931f4e5c39ca19" + integrity sha512-wciNMLg/Irp8OKGrh3S2tfvZiZ0NEyILfcRCXCD4mp7SgK/i9gzLfhY2hY7VMCQJ3kH9UB9BzNdibIVMchzyYw== + +solpp@^0.11.5: + version "0.11.5" + resolved "https://registry.yarnpkg.com/solpp/-/solpp-0.11.5.tgz#e5f38b5acc952e1cc2e3871d490fdbed910938dd" + integrity sha512-LjzCGMrTDXtera2C4mbQGZSpBznP+o3/82L2CneAAMNbm+t4xPsvfrgJkIaY+IZ5YLrB8IXn7cYthwHMKvAWnQ== + dependencies: + antlr4 "~4.8.0" + axios "^0.21.1" + bn-str-256 "^1.9.1" + commander "^2.19.0" + ethereumjs-util "^6.0.0" + lodash "^4.17.11" + mz "^2.7.0" + resolve "^1.10.0" + semver "^5.6.0" + +source-map-support@^0.5.13: + version "0.5.21" + resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.5.21.tgz#04fe7c7f9e1ed2d662233c28cb2b35b9f63f6e4f" + integrity sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w== + dependencies: + buffer-from "^1.0.0" + source-map "^0.6.0" + +source-map@^0.6.0: + version "0.6.1" + resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.6.1.tgz#74722af32e9614e9c287a8d0bbde48b5e2f1a263" + integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g== + +split-ca@^1.0.0, split-ca@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/split-ca/-/split-ca-1.0.1.tgz#6c83aff3692fa61256e0cd197e05e9de157691a6" + integrity sha512-Q5thBSxp5t8WPTTJQS59LrGqOZqOsrhDGDVm8azCqIBjSBd7nd9o2PM+mDulQQkh8h//4U6hFZnc/mul8t5pWQ== + +ssh2@^1.11.0: + version "1.14.0" + resolved "https://registry.yarnpkg.com/ssh2/-/ssh2-1.14.0.tgz#8f68440e1b768b66942c9e4e4620b2725b3555bb" + integrity sha512-AqzD1UCqit8tbOKoj6ztDDi1ffJZ2rV2SwlgrVVrHPkV5vWqGJOVp5pmtj18PunkPJAuKQsnInyKV+/Nb2bUnA== + dependencies: + asn1 "^0.2.6" + bcrypt-pbkdf "^1.0.2" + optionalDependencies: + cpu-features "~0.0.8" + nan "^2.17.0" + +stacktrace-parser@^0.1.10: + version "0.1.10" + resolved "https://registry.yarnpkg.com/stacktrace-parser/-/stacktrace-parser-0.1.10.tgz#29fb0cae4e0d0b85155879402857a1639eb6051a" + integrity sha512-KJP1OCML99+8fhOHxwwzyWrlUuVX5GQ0ZpJTd1DFXhdkrvg1szxfHhawXUZ3g9TkXORQd4/WG68jMlQZ2p8wlg== + dependencies: + type-fest "^0.7.1" + +statuses@2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/statuses/-/statuses-2.0.1.tgz#55cb000ccf1d48728bd23c685a063998cf1a1b63" + integrity sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ== + +string-format@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/string-format/-/string-format-2.0.0.tgz#f2df2e7097440d3b65de31b6d40d54c96eaffb9b" + integrity sha512-bbEs3scLeYNXLecRRuk6uJxdXUSj6le/8rNPHChIJTn2V79aXVTR1EH2OH5zLKKoz0V02fOUKZZcw01pLUShZA== + +string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.3: + version "4.2.3" + resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010" + integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g== + dependencies: + emoji-regex "^8.0.0" + is-fullwidth-code-point "^3.0.0" + strip-ansi "^6.0.1" + +string.prototype.trim@^1.2.8: + version "1.2.8" + resolved "https://registry.yarnpkg.com/string.prototype.trim/-/string.prototype.trim-1.2.8.tgz#f9ac6f8af4bd55ddfa8895e6aea92a96395393bd" + integrity sha512-lfjY4HcixfQXOfaqCvcBuOIapyaroTXhbkfJN3gcB1OtyupngWK4sEET9Knd0cXd28kTUqu/kHoV4HKSJdnjiQ== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + +string.prototype.trimend@^1.0.7: + version "1.0.7" + resolved "https://registry.yarnpkg.com/string.prototype.trimend/-/string.prototype.trimend-1.0.7.tgz#1bb3afc5008661d73e2dc015cd4853732d6c471e" + integrity sha512-Ni79DqeB72ZFq1uH/L6zJ+DKZTkOtPIHovb3YZHQViE+HDouuU4mBrLOLDn5Dde3RF8qw5qVETEjhu9locMLvA== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + +string.prototype.trimstart@^1.0.7: + version "1.0.7" + resolved "https://registry.yarnpkg.com/string.prototype.trimstart/-/string.prototype.trimstart-1.0.7.tgz#d4cdb44b83a4737ffbac2d406e405d43d0184298" + integrity sha512-NGhtDFu3jCEm7B4Fy0DpLewdJQOZcQ0rGbwQ/+stjnrp2i+rlKeCvos9hOIeCmqwratM47OBxY7uFZzjxHXmrg== + dependencies: + call-bind "^1.0.2" + define-properties "^1.2.0" + es-abstract "^1.22.1" + +string_decoder@^1.1.1: + version "1.3.0" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.3.0.tgz#42f114594a46cf1a8e30b0a84f56c78c3edac21e" + integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA== + dependencies: + safe-buffer "~5.2.0" + +string_decoder@~0.10.x: + version "0.10.31" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-0.10.31.tgz#62e203bc41766c6c28c9fc84301dab1c5310fa94" + integrity sha512-ev2QzSzWPYmy9GuqfIVildA4OdcGLeFZQrq5ys6RtiuF+RQQiZWr8TZNyAcuVXyQRYfEO+MsoB/1BuQVhOJuoQ== + +string_decoder@~1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.1.1.tgz#9cf1611ba62685d7030ae9e4ba34149c3af03fc8" + integrity sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg== + dependencies: + safe-buffer "~5.1.0" + +strip-ansi@^6.0.0, strip-ansi@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9" + integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A== + dependencies: + ansi-regex "^5.0.1" + +strip-bom@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/strip-bom/-/strip-bom-3.0.0.tgz#2334c18e9c759f7bdd56fdef7e9ae3d588e68ed3" + integrity sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA== + +strip-final-newline@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/strip-final-newline/-/strip-final-newline-2.0.0.tgz#89b852fb2fcbe936f6f4b3187afb0a12c1ab58ad" + integrity sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA== + +strip-final-newline@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/strip-final-newline/-/strip-final-newline-3.0.0.tgz#52894c313fbff318835280aed60ff71ebf12b8fd" + integrity sha512-dOESqjYr96iWYylGObzd39EuNTa5VJxyvVAEm5Jnh7KGo75V43Hk1odPQkNDyXNmUR6k+gEiDVXnjB8HJ3crXw== + +strip-hex-prefix@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/strip-hex-prefix/-/strip-hex-prefix-1.0.0.tgz#0c5f155fef1151373377de9dbb588da05500e36f" + integrity sha512-q8d4ue7JGEiVcypji1bALTos+0pWtyGlivAWyPuTkHzuTCJqrK9sWxYQZUq6Nq3cuyv3bm734IhHvHtGGURU6A== + dependencies: + is-hex-prefixed "1.0.0" + +strip-json-comments@3.1.1, strip-json-comments@^3.1.1, strip-json-comments@~3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz#31f1281b3832630434831c310c01cccda8cbe006" + integrity sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig== + +supports-color@8.1.1: + version "8.1.1" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-8.1.1.tgz#cd6fc17e28500cff56c1b86c0a7fd4a54a73005c" + integrity sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q== + dependencies: + has-flag "^4.0.0" + +supports-color@^5.3.0: + version "5.5.0" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-5.5.0.tgz#e2e69a44ac8772f78a1ec0b35b689df6530efc8f" + integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow== + dependencies: + has-flag "^3.0.0" + +supports-color@^7.1.0: + version "7.2.0" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-7.2.0.tgz#1b7dcdcb32b8138801b3e478ba6a51caa89648da" + integrity sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw== + dependencies: + has-flag "^4.0.0" + +supports-preserve-symlinks-flag@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz#6eda4bd344a3c94aea376d4cc31bc77311039e09" + integrity sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w== + +synckit@^0.8.5: + version "0.8.5" + resolved "https://registry.yarnpkg.com/synckit/-/synckit-0.8.5.tgz#b7f4358f9bb559437f9f167eb6bc46b3c9818fa3" + integrity sha512-L1dapNV6vu2s/4Sputv8xGsCdAVlb5nRDMFU/E27D44l5U6cw1g0dGd45uLc+OXjNMmF4ntiMdCimzcjFKQI8Q== + dependencies: + "@pkgr/utils" "^2.3.1" + tslib "^2.5.0" + +table-layout@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/table-layout/-/table-layout-1.0.2.tgz#c4038a1853b0136d63365a734b6931cf4fad4a04" + integrity sha512-qd/R7n5rQTRFi+Zf2sk5XVVd9UQl6ZkduPFC3S7WEGJAmetDTjY3qPN50eSKzwuzEyQKy5TN2TiZdkIjos2L6A== + dependencies: + array-back "^4.0.1" + deep-extend "~0.6.0" + typical "^5.2.0" + wordwrapjs "^4.0.0" + +table@^6.8.1: + version "6.8.1" + resolved "https://registry.yarnpkg.com/table/-/table-6.8.1.tgz#ea2b71359fe03b017a5fbc296204471158080bdf" + integrity sha512-Y4X9zqrCftUhMeH2EptSSERdVKt/nEdijTOacGD/97EKjhQ/Qs8RTlEGABSJNNN8lac9kheH+af7yAkEWlgneA== + dependencies: + ajv "^8.0.1" + lodash.truncate "^4.4.2" + slice-ansi "^4.0.0" + string-width "^4.2.3" + strip-ansi "^6.0.1" + +tapable@^2.2.0: + version "2.2.1" + resolved "https://registry.yarnpkg.com/tapable/-/tapable-2.2.1.tgz#1967a73ef4060a82f12ab96af86d52fdb76eeca0" + integrity sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ== + +tar-fs@~1.16.3: + version "1.16.3" + resolved "https://registry.yarnpkg.com/tar-fs/-/tar-fs-1.16.3.tgz#966a628841da2c4010406a82167cbd5e0c72d509" + integrity sha512-NvCeXpYx7OsmOh8zIOP/ebG55zZmxLE0etfWRbWok+q2Qo8x/vOR/IJT1taADXPe+jsiu9axDb3X4B+iIgNlKw== + dependencies: + chownr "^1.0.1" + mkdirp "^0.5.1" + pump "^1.0.0" + tar-stream "^1.1.2" + +tar-fs@~2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/tar-fs/-/tar-fs-2.0.1.tgz#e44086c1c60d31a4f0cf893b1c4e155dabfae9e2" + integrity sha512-6tzWDMeroL87uF/+lin46k+Q+46rAJ0SyPGz7OW7wTgblI273hsBqk2C1j0/xNadNLKDTUL9BukSjB7cwgmlPA== + dependencies: + chownr "^1.1.1" + mkdirp-classic "^0.5.2" + pump "^3.0.0" + tar-stream "^2.0.0" + +tar-stream@^1.1.2: + version "1.6.2" + resolved "https://registry.yarnpkg.com/tar-stream/-/tar-stream-1.6.2.tgz#8ea55dab37972253d9a9af90fdcd559ae435c555" + integrity sha512-rzS0heiNf8Xn7/mpdSVVSMAWAoy9bfb1WOTYC78Z0UQKeKa/CWS8FOq0lKGNa8DWKAn9gxjCvMLYc5PGXYlK2A== + dependencies: + bl "^1.0.0" + buffer-alloc "^1.2.0" + end-of-stream "^1.0.0" + fs-constants "^1.0.0" + readable-stream "^2.3.0" + to-buffer "^1.1.1" + xtend "^4.0.0" + +tar-stream@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/tar-stream/-/tar-stream-2.2.0.tgz#acad84c284136b060dc3faa64474aa9aebd77287" + integrity sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ== + dependencies: + bl "^4.0.3" + end-of-stream "^1.4.1" + fs-constants "^1.0.0" + inherits "^2.0.3" + readable-stream "^3.1.1" + +template-file@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/template-file/-/template-file-6.0.1.tgz#ce4d1f48e56d637cc94bb97ec205e6e035bbb2a5" + integrity sha512-02hOa1psJUOsahWfx8w3p40CCulA2/InNFFPh5xLq5rUUm2XTzvmtOn/SXV+KZaq7ylG58SYSnT4yW3y/Smn4w== + dependencies: + "@blakek/deep" "^2.2.0" + glob "^7.1.6" + mkdirp "^1.0.4" + p-limit "^4.0.0" + +text-table@^0.2.0: + version "0.2.0" + resolved "https://registry.yarnpkg.com/text-table/-/text-table-0.2.0.tgz#7f5ee823ae805207c00af2df4a84ec3fcfa570b4" + integrity sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw== + +thenify-all@^1.0.0: + version "1.6.0" + resolved "https://registry.yarnpkg.com/thenify-all/-/thenify-all-1.6.0.tgz#1a1918d402d8fc3f98fbf234db0bcc8cc10e9726" + integrity sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA== + dependencies: + thenify ">= 3.1.0 < 4" + +"thenify@>= 3.1.0 < 4": + version "3.3.1" + resolved "https://registry.yarnpkg.com/thenify/-/thenify-3.3.1.tgz#8932e686a4066038a016dd9e2ca46add9838a95f" + integrity sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw== + dependencies: + any-promise "^1.0.0" + +"through@>=2.2.7 <3": + version "2.3.8" + resolved "https://registry.yarnpkg.com/through/-/through-2.3.8.tgz#0dd4c9ffaabc357960b1b724115d7e0e86a2e1f5" + integrity sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg== + +titleize@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/titleize/-/titleize-3.0.0.tgz#71c12eb7fdd2558aa8a44b0be83b8a76694acd53" + integrity sha512-KxVu8EYHDPBdUYdKZdKtU2aj2XfEx9AfjXxE/Aj0vT06w2icA09Vus1rh6eSu1y01akYg6BjIK/hxyLJINoMLQ== + +tmp@0.0.33: + version "0.0.33" + resolved "https://registry.yarnpkg.com/tmp/-/tmp-0.0.33.tgz#6d34335889768d21b2bcda0aa277ced3b1bfadf9" + integrity sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw== + dependencies: + os-tmpdir "~1.0.2" + +to-buffer@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/to-buffer/-/to-buffer-1.1.1.tgz#493bd48f62d7c43fcded313a03dcadb2e1213a80" + integrity sha512-lx9B5iv7msuFYE3dytT+KE5tap+rNYw+K4jVkb9R/asAb+pbBSM17jtunHplhBe6RRJdZx3Pn2Jph24O32mOVg== + +to-regex-range@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/to-regex-range/-/to-regex-range-5.0.1.tgz#1648c44aae7c8d988a326018ed72f5b4dd0392e4" + integrity sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ== + dependencies: + is-number "^7.0.0" + +toidentifier@1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/toidentifier/-/toidentifier-1.0.1.tgz#3be34321a88a820ed1bd80dfaa33e479fbb8dd35" + integrity sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA== + +tr46@~0.0.3: + version "0.0.3" + resolved "https://registry.yarnpkg.com/tr46/-/tr46-0.0.3.tgz#8184fd347dac9cdc185992f3a6622e14b9d9ab6a" + integrity sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw== + +ts-api-utils@^1.0.1: + version "1.0.3" + resolved "https://registry.yarnpkg.com/ts-api-utils/-/ts-api-utils-1.0.3.tgz#f12c1c781d04427313dbac808f453f050e54a331" + integrity sha512-wNMeqtMz5NtwpT/UZGY5alT+VoKdSsOOP/kqHFcUW1P/VRhH2wJ48+DN2WwUliNbQ976ETwDL0Ifd2VVvgonvg== + +ts-command-line-args@^2.2.0: + version "2.5.1" + resolved "https://registry.yarnpkg.com/ts-command-line-args/-/ts-command-line-args-2.5.1.tgz#e64456b580d1d4f6d948824c274cf6fa5f45f7f0" + integrity sha512-H69ZwTw3rFHb5WYpQya40YAX2/w7Ut75uUECbgBIsLmM+BNuYnxsltfyyLMxy6sEeKxgijLTnQtLd0nKd6+IYw== + dependencies: + chalk "^4.1.0" + command-line-args "^5.1.1" + command-line-usage "^6.1.0" + string-format "^2.0.0" + +ts-essentials@^1.0.0: + version "1.0.4" + resolved "https://registry.yarnpkg.com/ts-essentials/-/ts-essentials-1.0.4.tgz#ce3b5dade5f5d97cf69889c11bf7d2da8555b15a" + integrity sha512-q3N1xS4vZpRouhYHDPwO0bDW3EZ6SK9CrrDHxi/D6BPReSjpVgWIOpLS2o0gSBZm+7q/wyKp6RVM1AeeW7uyfQ== + +ts-essentials@^7.0.1: + version "7.0.3" + resolved "https://registry.yarnpkg.com/ts-essentials/-/ts-essentials-7.0.3.tgz#686fd155a02133eedcc5362dc8b5056cde3e5a38" + integrity sha512-8+gr5+lqO3G84KdiTSMRLtuyJ+nTBVRKuCrK4lidMPdVeEp0uqC875uE5NMcaA7YYMN7XsNiFQuMvasF8HT/xQ== + +ts-generator@^0.1.1: + version "0.1.1" + resolved "https://registry.yarnpkg.com/ts-generator/-/ts-generator-0.1.1.tgz#af46f2fb88a6db1f9785977e9590e7bcd79220ab" + integrity sha512-N+ahhZxTLYu1HNTQetwWcx3so8hcYbkKBHTr4b4/YgObFTIKkOSSsaa+nal12w8mfrJAyzJfETXawbNjSfP2gQ== + dependencies: + "@types/mkdirp" "^0.5.2" + "@types/prettier" "^2.1.1" + "@types/resolve" "^0.0.8" + chalk "^2.4.1" + glob "^7.1.2" + mkdirp "^0.5.1" + prettier "^2.1.2" + resolve "^1.8.1" + ts-essentials "^1.0.0" + +ts-morph@^19.0.0: + version "19.0.0" + resolved "https://registry.yarnpkg.com/ts-morph/-/ts-morph-19.0.0.tgz#43e95fb0156c3fe3c77c814ac26b7d0be2f93169" + integrity sha512-D6qcpiJdn46tUqV45vr5UGM2dnIEuTGNxVhg0sk5NX11orcouwj6i1bMqZIz2mZTZB1Hcgy7C3oEVhAT+f6mbQ== + dependencies: + "@ts-morph/common" "~0.20.0" + code-block-writer "^12.0.0" + +ts-node@^10.7.0: + version "10.9.1" + resolved "https://registry.yarnpkg.com/ts-node/-/ts-node-10.9.1.tgz#e73de9102958af9e1f0b168a6ff320e25adcff4b" + integrity sha512-NtVysVPkxxrwFGUUxGYhfux8k78pQB3JqYBXlLRZgdGUqTO5wU/UyHop5p70iEbGhB7q5KmiZiU0Y3KlJrScEw== + dependencies: + "@cspotcode/source-map-support" "^0.8.0" + "@tsconfig/node10" "^1.0.7" + "@tsconfig/node12" "^1.0.7" + "@tsconfig/node14" "^1.0.0" + "@tsconfig/node16" "^1.0.2" + acorn "^8.4.1" + acorn-walk "^8.1.1" + arg "^4.1.0" + create-require "^1.1.0" + diff "^4.0.1" + make-error "^1.1.1" + v8-compile-cache-lib "^3.0.1" + yn "3.1.1" + +tsconfig-paths@^3.14.2: + version "3.14.2" + resolved "https://registry.yarnpkg.com/tsconfig-paths/-/tsconfig-paths-3.14.2.tgz#6e32f1f79412decd261f92d633a9dc1cfa99f088" + integrity sha512-o/9iXgCYc5L/JxCHPe3Hvh8Q/2xm5Z+p18PESBU6Ff33695QnCHBEjcytY2q19ua7Mbl/DavtBOLq+oG0RCL+g== + dependencies: + "@types/json5" "^0.0.29" + json5 "^1.0.2" + minimist "^1.2.6" + strip-bom "^3.0.0" + +tslib@^1.9.3: + version "1.14.1" + resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.14.1.tgz#cf2d38bdc34a134bcaf1091c41f6619e2f672d00" + integrity sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg== + +tslib@^2.5.0, tslib@^2.6.0: + version "2.6.2" + resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.6.2.tgz#703ac29425e7b37cd6fd456e92404d46d1f3e4ae" + integrity sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q== + +tsort@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/tsort/-/tsort-0.0.1.tgz#e2280f5e817f8bf4275657fd0f9aebd44f5a2786" + integrity sha512-Tyrf5mxF8Ofs1tNoxA13lFeZ2Zrbd6cKbuH3V+MQ5sb6DtBj5FjrXVsRWT8YvNAQTqNoz66dz1WsbigI22aEnw== + +tweetnacl-util@^0.15.1: + version "0.15.1" + resolved "https://registry.yarnpkg.com/tweetnacl-util/-/tweetnacl-util-0.15.1.tgz#b80fcdb5c97bcc508be18c44a4be50f022eea00b" + integrity sha512-RKJBIj8lySrShN4w6i/BonWp2Z/uxwC3h4y7xsRrpP59ZboCd0GpEVsOnMDYLMmKBpYhb5TgHzZXy7wTfYFBRw== + +tweetnacl@^0.14.3: + version "0.14.5" + resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-0.14.5.tgz#5ae68177f192d4456269d108afa93ff8743f4f64" + integrity sha512-KXXFFdAbFXY4geFIwoyNK+f5Z1b7swfXABfL7HXCmoIWMKU3dmS26672A4EeQtDzLKy7SXmfBu51JolvEKwtGA== + +tweetnacl@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-1.0.3.tgz#ac0af71680458d8a6378d0d0d050ab1407d35596" + integrity sha512-6rt+RN7aOi1nGMyC4Xa5DdYiukl2UWCbcJft7YhxReBGQD7OAM8Pbxw6YMo4r2diNEA8FEmu32YOn9rhaiE5yw== + +type-check@^0.4.0, type-check@~0.4.0: + version "0.4.0" + resolved "https://registry.yarnpkg.com/type-check/-/type-check-0.4.0.tgz#07b8203bfa7056c0657050e3ccd2c37730bab8f1" + integrity sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew== + dependencies: + prelude-ls "^1.2.1" + +type-detect@^4.0.0, type-detect@^4.0.5: + version "4.0.8" + resolved "https://registry.yarnpkg.com/type-detect/-/type-detect-4.0.8.tgz#7646fb5f18871cfbb7749e69bd39a6388eb7450c" + integrity sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g== + +type-fest@^0.20.2: + version "0.20.2" + resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.20.2.tgz#1bf207f4b28f91583666cb5fbd327887301cd5f4" + integrity sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ== + +type-fest@^0.21.3: + version "0.21.3" + resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.21.3.tgz#d260a24b0198436e133fa26a524a6d65fa3b2e37" + integrity sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w== + +type-fest@^0.7.1: + version "0.7.1" + resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.7.1.tgz#8dda65feaf03ed78f0a3f9678f1869147f7c5c48" + integrity sha512-Ne2YiiGN8bmrmJJEuTWTLJR32nh/JdL1+PSicowtNb0WFpn59GK8/lfD61bVtzguz7b3PBt74nxpv/Pw5po5Rg== + +typechain@^8.1.1: + version "8.3.1" + resolved "https://registry.yarnpkg.com/typechain/-/typechain-8.3.1.tgz#dccbc839b94877997536c356380eff7325395cfb" + integrity sha512-fA7clol2IP/56yq6vkMTR+4URF1nGjV82Wx6Rf09EsqD4tkzMAvEaqYxVFCavJm/1xaRga/oD55K+4FtuXwQOQ== + dependencies: + "@types/prettier" "^2.1.1" + debug "^4.3.1" + fs-extra "^7.0.0" + glob "7.1.7" + js-sha3 "^0.8.0" + lodash "^4.17.15" + mkdirp "^1.0.4" + prettier "^2.3.1" + ts-command-line-args "^2.2.0" + ts-essentials "^7.0.1" + +typed-array-buffer@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/typed-array-buffer/-/typed-array-buffer-1.0.0.tgz#18de3e7ed7974b0a729d3feecb94338d1472cd60" + integrity sha512-Y8KTSIglk9OZEr8zywiIHG/kmQ7KWyjseXs1CbSo8vC42w7hg2HgYTxSWwP0+is7bWDc1H+Fo026CpHFwm8tkw== + dependencies: + call-bind "^1.0.2" + get-intrinsic "^1.2.1" + is-typed-array "^1.1.10" + +typed-array-byte-length@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/typed-array-byte-length/-/typed-array-byte-length-1.0.0.tgz#d787a24a995711611fb2b87a4052799517b230d0" + integrity sha512-Or/+kvLxNpeQ9DtSydonMxCx+9ZXOswtwJn17SNLvhptaXYDJvkFFP5zbfU/uLmvnBJlI4yrnXRxpdWH/M5tNA== + dependencies: + call-bind "^1.0.2" + for-each "^0.3.3" + has-proto "^1.0.1" + is-typed-array "^1.1.10" + +typed-array-byte-offset@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/typed-array-byte-offset/-/typed-array-byte-offset-1.0.0.tgz#cbbe89b51fdef9cd6aaf07ad4707340abbc4ea0b" + integrity sha512-RD97prjEt9EL8YgAgpOkf3O4IF9lhJFr9g0htQkm0rchFp/Vx7LW5Q8fSXXub7BXAODyUQohRMyOc3faCPd0hg== + dependencies: + available-typed-arrays "^1.0.5" + call-bind "^1.0.2" + for-each "^0.3.3" + has-proto "^1.0.1" + is-typed-array "^1.1.10" + +typed-array-length@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/typed-array-length/-/typed-array-length-1.0.4.tgz#89d83785e5c4098bec72e08b319651f0eac9c1bb" + integrity sha512-KjZypGq+I/H7HI5HlOoGHkWUUGq+Q0TPhQurLbyrVrvnKTBgzLhIJ7j6J/XTQOi0d1RjyZ0wdas8bKs2p0x3Ng== + dependencies: + call-bind "^1.0.2" + for-each "^0.3.3" + is-typed-array "^1.1.9" + +typedarray@^0.0.6: + version "0.0.6" + resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777" + integrity sha512-/aCDEGatGvZ2BIk+HmLf4ifCJFwvKFNb9/JeZPMulfgFracn9QFcAf5GO8B/mweUjSoblS5In0cWhqpfs/5PQA== + +typescript@^4.6.4: + version "4.9.5" + resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.9.5.tgz#095979f9bcc0d09da324d58d03ce8f8374cbe65a" + integrity sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g== + +typical@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/typical/-/typical-4.0.0.tgz#cbeaff3b9d7ae1e2bbfaf5a4e6f11eccfde94fc4" + integrity sha512-VAH4IvQ7BDFYglMd7BPRDfLgxZZX4O4TFcRDA6EN5X7erNJJq+McIEp8np9aVtxrCJ6qx4GTYVfOWNjcqwZgRw== + +typical@^5.2.0: + version "5.2.0" + resolved "https://registry.yarnpkg.com/typical/-/typical-5.2.0.tgz#4daaac4f2b5315460804f0acf6cb69c52bb93066" + integrity sha512-dvdQgNDNJo+8B2uBQoqdb11eUCE1JQXhvjC/CZtgvZseVd5TYMXnq0+vuUemXbd/Se29cTaUuPX3YIc2xgbvIg== + +uc.micro@^1.0.1, uc.micro@^1.0.5: + version "1.0.6" + resolved "https://registry.yarnpkg.com/uc.micro/-/uc.micro-1.0.6.tgz#9c411a802a409a91fc6cf74081baba34b24499ac" + integrity sha512-8Y75pvTYkLJW2hWQHXxoqRgV7qb9B+9vFEtidML+7koHUFapnVJAZ6cKs+Qjz5Aw3aZWHMC6u0wJE3At+nSGwA== + +unbox-primitive@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/unbox-primitive/-/unbox-primitive-1.0.2.tgz#29032021057d5e6cdbd08c5129c226dff8ed6f9e" + integrity sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw== + dependencies: + call-bind "^1.0.2" + has-bigints "^1.0.2" + has-symbols "^1.0.3" + which-boxed-primitive "^1.0.2" + +undici@^5.14.0: + version "5.26.4" + resolved "https://registry.yarnpkg.com/undici/-/undici-5.26.4.tgz#dc861c35fb53ae025a173a790d984aa9b2e279a1" + integrity sha512-OG+QOf0fTLtazL9P9X7yqWxQ+Z0395Wk6DSkyTxtaq3wQEjIroVe7Y4asCX/vcCxYpNGMnwz8F0qbRYUoaQVMw== + dependencies: + "@fastify/busboy" "^2.0.0" + +universalify@^0.1.0: + version "0.1.2" + resolved "https://registry.yarnpkg.com/universalify/-/universalify-0.1.2.tgz#b646f69be3942dabcecc9d6639c80dc105efaa66" + integrity sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg== + +universalify@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/universalify/-/universalify-2.0.0.tgz#75a4984efedc4b08975c5aeb73f530d02df25717" + integrity sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ== + +unpipe@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/unpipe/-/unpipe-1.0.0.tgz#b2bf4ee8514aae6165b4817829d21b2ef49904ec" + integrity sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ== + +untildify@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/untildify/-/untildify-4.0.0.tgz#2bc947b953652487e4600949fb091e3ae8cd919b" + integrity sha512-KK8xQ1mkzZeg9inewmFVDNkg3l5LUhoq9kN6iWYB/CC9YMG8HA+c1Q8HwDe6dEX7kErrEVNVBO3fWsVq5iDgtw== + +uri-js@^4.2.2: + version "4.4.1" + resolved "https://registry.yarnpkg.com/uri-js/-/uri-js-4.4.1.tgz#9b1a52595225859e55f669d928f88c6c57f2a77e" + integrity sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg== + dependencies: + punycode "^2.1.0" + +util-deprecate@^1.0.1, util-deprecate@~1.0.1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" + integrity sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw== + +uuid@^8.3.2: + version "8.3.2" + resolved "https://registry.yarnpkg.com/uuid/-/uuid-8.3.2.tgz#80d5b5ced271bb9af6c445f21a1a04c606cefbe2" + integrity sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg== + +v8-compile-cache-lib@^3.0.1: + version "3.0.1" + resolved "https://registry.yarnpkg.com/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz#6336e8d71965cb3d35a1bbb7868445a7c05264bf" + integrity sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg== + +webidl-conversions@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/webidl-conversions/-/webidl-conversions-3.0.1.tgz#24534275e2a7bc6be7bc86611cc16ae0a5654871" + integrity sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ== + +whatwg-url@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/whatwg-url/-/whatwg-url-5.0.0.tgz#966454e8765462e37644d3626f6742ce8b70965d" + integrity sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw== + dependencies: + tr46 "~0.0.3" + webidl-conversions "^3.0.0" + +which-boxed-primitive@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/which-boxed-primitive/-/which-boxed-primitive-1.0.2.tgz#13757bc89b209b049fe5d86430e21cf40a89a8e6" + integrity sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg== + dependencies: + is-bigint "^1.0.1" + is-boolean-object "^1.1.0" + is-number-object "^1.0.4" + is-string "^1.0.5" + is-symbol "^1.0.3" + +which-typed-array@^1.1.11, which-typed-array@^1.1.13: + version "1.1.13" + resolved "https://registry.yarnpkg.com/which-typed-array/-/which-typed-array-1.1.13.tgz#870cd5be06ddb616f504e7b039c4c24898184d36" + integrity sha512-P5Nra0qjSncduVPEAr7xhoF5guty49ArDTwzJ/yNuPIbZppyRxFQsRCWrocxIY+CnMVG+qfbU2FmDKyvSGClow== + dependencies: + available-typed-arrays "^1.0.5" + call-bind "^1.0.4" + for-each "^0.3.3" + gopd "^1.0.1" + has-tostringtag "^1.0.0" + +which@^2.0.1: + version "2.0.2" + resolved "https://registry.yarnpkg.com/which/-/which-2.0.2.tgz#7c6a8dd0a636a0327e10b59c9286eee93f3f51b1" + integrity sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA== + dependencies: + isexe "^2.0.0" + +wordwrapjs@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/wordwrapjs/-/wordwrapjs-4.0.1.tgz#d9790bccfb110a0fc7836b5ebce0937b37a8b98f" + integrity sha512-kKlNACbvHrkpIw6oPeYDSmdCTu2hdMHoyXLTcUKala++lx5Y+wjJ/e474Jqv5abnVmwxw08DiTuHmw69lJGksA== + dependencies: + reduce-flatten "^2.0.0" + typical "^5.2.0" + +workerpool@6.2.1: + version "6.2.1" + resolved "https://registry.yarnpkg.com/workerpool/-/workerpool-6.2.1.tgz#46fc150c17d826b86a008e5a4508656777e9c343" + integrity sha512-ILEIE97kDZvF9Wb9f6h5aXK4swSlKGUcOEGiIYb2OOu/IrDU9iwj0fD//SsA6E5ibwJxpEvhullJY4Sl4GcpAw== + +wrap-ansi@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43" + integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q== + dependencies: + ansi-styles "^4.0.0" + string-width "^4.1.0" + strip-ansi "^6.0.0" + +wrappy@1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" + integrity sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ== + +ws@7.4.6: + version "7.4.6" + resolved "https://registry.yarnpkg.com/ws/-/ws-7.4.6.tgz#5654ca8ecdeee47c33a9a4bf6d28e2be2980377c" + integrity sha512-YmhHDO4MzaDLB+M9ym/mDA5z0naX8j7SIlT8f8z+I0VtzsRbekxEutHSme7NPS2qE8StCYQNUnfWdXta/Yu85A== + +ws@^7.4.6: + version "7.5.9" + resolved "https://registry.yarnpkg.com/ws/-/ws-7.5.9.tgz#54fa7db29f4c7cec68b1ddd3a89de099942bb591" + integrity sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q== + +xregexp@3.1.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/xregexp/-/xregexp-3.1.0.tgz#14d8461e0bdd38224bfee5039a0898fc42fcd336" + integrity sha512-4Y1x6DyB8xRoxosooa6PlGWqmmSKatbzhrftZ7Purmm4B8R4qIEJG1A2hZsdz5DhmIqS0msC0I7KEq93GphEVg== + +xtend@^4.0.0: + version "4.0.2" + resolved "https://registry.yarnpkg.com/xtend/-/xtend-4.0.2.tgz#bb72779f5fa465186b1f438f674fa347fdb5db54" + integrity sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ== + +y18n@^5.0.5: + version "5.0.8" + resolved "https://registry.yarnpkg.com/y18n/-/y18n-5.0.8.tgz#7f4934d0f7ca8c56f95314939ddcd2dd91ce1d55" + integrity sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA== + +yallist@^3.0.2: + version "3.1.1" + resolved "https://registry.yarnpkg.com/yallist/-/yallist-3.1.1.tgz#dbb7daf9bfd8bac9ab45ebf602b8cbad0d5d08fd" + integrity sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g== + +yallist@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/yallist/-/yallist-4.0.0.tgz#9bb92790d9c0effec63be73519e11a35019a3a72" + integrity sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A== + +yargs-parser@20.2.4: + version "20.2.4" + resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.4.tgz#b42890f14566796f85ae8e3a25290d205f154a54" + integrity sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA== + +yargs-parser@^20.2.2: + version "20.2.9" + resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.9.tgz#2eb7dc3b0289718fc295f362753845c41a0c94ee" + integrity sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w== + +yargs-unparser@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/yargs-unparser/-/yargs-unparser-2.0.0.tgz#f131f9226911ae5d9ad38c432fe809366c2325eb" + integrity sha512-7pRTIA9Qc1caZ0bZ6RYRGbHJthJWuakf+WmHK0rVeLkNrrGhfoabBNdue6kdINI6r4if7ocq9aD/n7xwKOdzOA== + dependencies: + camelcase "^6.0.0" + decamelize "^4.0.0" + flat "^5.0.2" + is-plain-obj "^2.1.0" + +yargs@16.2.0: + version "16.2.0" + resolved "https://registry.yarnpkg.com/yargs/-/yargs-16.2.0.tgz#1c82bf0f6b6a66eafce7ef30e376f49a12477f66" + integrity sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw== + dependencies: + cliui "^7.0.2" + escalade "^3.1.1" + get-caller-file "^2.0.5" + require-directory "^2.1.1" + string-width "^4.2.0" + y18n "^5.0.5" + yargs-parser "^20.2.2" + +yn@3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/yn/-/yn-3.1.1.tgz#1e87401a09d767c1d5eab26a6e4c185182d2eb50" + integrity sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q== + +yocto-queue@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-0.1.0.tgz#0294eb3dee05028d31ee1a5fa2c556a6aaf10a1b" + integrity sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q== + +yocto-queue@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-1.0.0.tgz#7f816433fb2cbc511ec8bf7d263c3b58a1a3c251" + integrity sha512-9bnSc/HEW2uRy67wc+T8UwauLuPJVn28jb+GtJY16iiKWyvmYJRXVT4UamsAEGQfPohgr2q4Tq0sQbQlxTfi1g== + +zksync-web3@^0.14.3: + version "0.14.3" + resolved "https://registry.yarnpkg.com/zksync-web3/-/zksync-web3-0.14.3.tgz#64ac2a16d597464c3fc4ae07447a8007631c57c9" + integrity sha512-hT72th4AnqyLW1d5Jlv8N2B/qhEnl2NePK2A3org7tAa24niem/UAaHMkEvmWI3SF9waYUPtqAtjpf+yvQ9zvQ== diff --git a/.test-node-subtree/etc/test-contracts/.gitignore b/.test-node-subtree/etc/test-contracts/.gitignore new file mode 100644 index 00000000..b922ea06 --- /dev/null +++ b/.test-node-subtree/etc/test-contracts/.gitignore @@ -0,0 +1,5 @@ +node_modules +typechain-types +cache-zk +artifacts-zk +build-info diff --git a/.test-node-subtree/etc/test-contracts/SystemConfig.json b/.test-node-subtree/etc/test-contracts/SystemConfig.json new file mode 100644 index 00000000..5ac25bb6 --- /dev/null +++ b/.test-node-subtree/etc/test-contracts/SystemConfig.json @@ -0,0 +1,17 @@ +{ + "GUARANTEED_PUBDATA_BYTES": 4000, + "MAX_PUBDATA_PER_BATCH": 110000, + "MAX_TRANSACTIONS_IN_BATCH": 1024, + "BATCH_OVERHEAD_L2_GAS": 1200000, + "BATCH_OVERHEAD_L1_GAS": 1000000, + "L2_TX_INTRINSIC_GAS": 14070, + "L2_TX_INTRINSIC_PUBDATA": 0, + "L1_TX_INTRINSIC_L2_GAS": 167157, + "L1_TX_INTRINSIC_PUBDATA": 88, + "MAX_GAS_PER_TRANSACTION": 80000000, + "BOOTLOADER_MEMORY_FOR_TXS": 485225, + "REFUND_GAS": 7343, + "KECCAK_ROUND_COST_GAS": 40, + "SHA256_ROUND_COST_GAS": 7, + "ECRECOVER_COST_GAS": 1112 +} diff --git a/.test-node-subtree/etc/test-contracts/contracts/tracing/Primary.sol b/.test-node-subtree/etc/test-contracts/contracts/tracing/Primary.sol new file mode 100644 index 00000000..272d253f --- /dev/null +++ b/.test-node-subtree/etc/test-contracts/contracts/tracing/Primary.sol @@ -0,0 +1,25 @@ +// SPDX-License-Identifier: MIT + +pragma solidity ^0.8.0; + +import "./Secondary.sol"; + +contract Primary { + Secondary secondary; + + constructor(address _secondary) { + secondary = Secondary(_secondary); + } + + function name() public pure returns (string memory) { + return "Primary"; + } + + function calculate(uint256 value) public returns (uint) { + return secondary.multiply(value); + } + + function shouldRevert() public view returns (uint) { + return secondary.shouldRevert(); + } +} diff --git a/.test-node-subtree/etc/test-contracts/contracts/tracing/Secondary.sol b/.test-node-subtree/etc/test-contracts/contracts/tracing/Secondary.sol new file mode 100644 index 00000000..43c0cb3e --- /dev/null +++ b/.test-node-subtree/etc/test-contracts/contracts/tracing/Secondary.sol @@ -0,0 +1,24 @@ +// SPDX-License-Identifier: MIT + +pragma solidity ^0.8.0; + +contract Secondary { + uint data; + + constructor(uint _data) { + data = _data; + } + + function name() public pure returns (string memory) { + return "Secondary"; + } + + function multiply(uint256 value) public view returns (uint) { + return data * value; + } + + function shouldRevert() public pure returns (uint) { + require(false, "This should revert"); + return 1; + } +} diff --git a/.test-node-subtree/etc/test-contracts/hardhat.config.ts b/.test-node-subtree/etc/test-contracts/hardhat.config.ts new file mode 100644 index 00000000..595347cf --- /dev/null +++ b/.test-node-subtree/etc/test-contracts/hardhat.config.ts @@ -0,0 +1,37 @@ +import '@nomiclabs/hardhat-solpp'; +import '@typechain/hardhat' +import '@nomiclabs/hardhat-ethers'; +import '@matterlabs/hardhat-zksync-solc'; + +const systemConfig = require('./SystemConfig.json'); + +export default { + zksolc: { + version: 'latest', + compilerSource: 'binary', + settings: { + isSystem: true + } + }, + zkSyncDeploy: { + zkSyncNetwork: 'http://localhost:3050', + ethNetwork: 'http://localhost:8545' + }, + solidity: { + version: '0.8.17' + }, + solpp: { + defs: (() => { + return { + ECRECOVER_COST_GAS: systemConfig.ECRECOVER_COST_GAS, + KECCAK_ROUND_COST_GAS: systemConfig.KECCAK_ROUND_COST_GAS, + SHA256_ROUND_COST_GAS: systemConfig.SHA256_ROUND_COST_GAS + } + })() + }, + networks: { + hardhat: { + zksync: true + } + } +}; diff --git a/.test-node-subtree/etc/test-contracts/package.json b/.test-node-subtree/etc/test-contracts/package.json new file mode 100644 index 00000000..f934e4a2 --- /dev/null +++ b/.test-node-subtree/etc/test-contracts/package.json @@ -0,0 +1,48 @@ +{ + "name": "system-contracts", + "version": "0.1.0", + "repository": "git@github.com:matter-labs/system-contracts.git", + "license": "MIT", + "dependencies": { + "@matterlabs/hardhat-zksync-deploy": "^0.6.5", + "@nomiclabs/hardhat-solpp": "^2.0.1", + "commander": "^9.4.1", + "ethers": "^5.7.0", + "hardhat": "^2.11.0", + "preprocess": "^3.2.0", + "zksync-web3": "^0.13.0" + }, + "devDependencies": { + "@matterlabs/hardhat-zksync-solc": "^0.4.2", + "@nomiclabs/hardhat-ethers": "^2.0.6", + "@typechain/ethers-v5": "^10.0.0", + "@typechain/ethers-v6": "0.4.0", + "@typechain/hardhat": "8.0.0", + "@types/chai": "^4.3.1", + "@types/mocha": "^9.1.1", + "@types/node": "^17.0.34", + "chai": "^4.3.6", + "mocha": "^10.0.0", + "prettier": "^2.3.0", + "prettier-plugin-solidity": "^1.0.0-alpha.27", + "template-file": "^6.0.1", + "ts-generator": "^0.1.1", + "ts-node": "^10.7.0", + "typechain": "^8.1.1", + "typescript": "^4.6.4" + }, + "mocha": { + "timeout": 240000, + "exit": true, + "color": false, + "slow": 0, + "require": [ + "ts-node/register" + ] + }, + "scripts": { + "build": "hardhat compile", + "clean": "hardhat clean" + }, + "packageManager": "yarn@1.22.19" +} \ No newline at end of file diff --git a/.test-node-subtree/etc/test-contracts/yarn.lock b/.test-node-subtree/etc/test-contracts/yarn.lock new file mode 100644 index 00000000..ca539f0c --- /dev/null +++ b/.test-node-subtree/etc/test-contracts/yarn.lock @@ -0,0 +1,3519 @@ +# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. +# yarn lockfile v1 + + +"@balena/dockerignore@^1.0.2": + version "1.0.2" + resolved "https://registry.yarnpkg.com/@balena/dockerignore/-/dockerignore-1.0.2.tgz#9ffe4726915251e8eb69f44ef3547e0da2c03e0d" + integrity sha512-wMue2Sy4GAVTk6Ic4tJVcnfdau+gx2EnG7S+uAEe+TWJFqE4YoWN4/H8MSLj4eYJKxGg26lZwboEniNiNwZQ6Q== + +"@blakek/curry@^2.0.2": + version "2.0.2" + resolved "https://registry.yarnpkg.com/@blakek/curry/-/curry-2.0.2.tgz#979e927bcf5fa0426d2af681d7131df5791d1cd4" + integrity sha512-B/KkDnZqm9Y92LwETU80BaxbQ61bYTR2GaAY41mKisaICwBoC8lcuw7lwQLl52InMhviCTJBO39GJOA8d+BrVw== + +"@blakek/deep@^2.2.0": + version "2.2.0" + resolved "https://registry.yarnpkg.com/@blakek/deep/-/deep-2.2.0.tgz#eb97488e4a0943df4da09ad50efba4a98789f5e5" + integrity sha512-aRq/qF1yrlhCWNk2tI4epXNpo+cA8/MrxsR5oIkpKKNYtYOQKjAxRMbgnhASPx+b328MkDN+T706yFKJg8VZkQ== + dependencies: + "@blakek/curry" "^2.0.2" + pathington "^1.1.7" + +"@chainsafe/as-sha256@^0.3.1": + version "0.3.1" + resolved "https://registry.yarnpkg.com/@chainsafe/as-sha256/-/as-sha256-0.3.1.tgz#3639df0e1435cab03f4d9870cc3ac079e57a6fc9" + integrity sha512-hldFFYuf49ed7DAakWVXSJODuq3pzJEguD8tQ7h+sGkM18vja+OFoJI9krnGmgzyuZC2ETX0NOIcCTy31v2Mtg== + +"@chainsafe/persistent-merkle-tree@^0.4.2": + version "0.4.2" + resolved "https://registry.yarnpkg.com/@chainsafe/persistent-merkle-tree/-/persistent-merkle-tree-0.4.2.tgz#4c9ee80cc57cd3be7208d98c40014ad38f36f7ff" + integrity sha512-lLO3ihKPngXLTus/L7WHKaw9PnNJWizlOF1H9NNzHP6Xvh82vzg9F2bzkXhYIFshMZ2gTCEz8tq6STe7r5NDfQ== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + +"@chainsafe/persistent-merkle-tree@^0.5.0": + version "0.5.0" + resolved "https://registry.yarnpkg.com/@chainsafe/persistent-merkle-tree/-/persistent-merkle-tree-0.5.0.tgz#2b4a62c9489a5739dedd197250d8d2f5427e9f63" + integrity sha512-l0V1b5clxA3iwQLXP40zYjyZYospQLZXzBVIhhr9kDg/1qHZfzzHw0jj4VPBijfYCArZDlPkRi1wZaV2POKeuw== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + +"@chainsafe/ssz@^0.10.0": + version "0.10.2" + resolved "https://registry.yarnpkg.com/@chainsafe/ssz/-/ssz-0.10.2.tgz#c782929e1bb25fec66ba72e75934b31fd087579e" + integrity sha512-/NL3Lh8K+0q7A3LsiFq09YXS9fPE+ead2rr7vM2QK8PLzrNsw3uqrif9bpRX5UxgeRjM+vYi+boCM3+GM4ovXg== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + "@chainsafe/persistent-merkle-tree" "^0.5.0" + +"@chainsafe/ssz@^0.9.2": + version "0.9.4" + resolved "https://registry.yarnpkg.com/@chainsafe/ssz/-/ssz-0.9.4.tgz#696a8db46d6975b600f8309ad3a12f7c0e310497" + integrity sha512-77Qtg2N1ayqs4Bg/wvnWfg5Bta7iy7IRh8XqXh7oNMeP2HBbBwx8m6yTpA8p0EHItWPEBkgZd5S5/LSlp3GXuQ== + dependencies: + "@chainsafe/as-sha256" "^0.3.1" + "@chainsafe/persistent-merkle-tree" "^0.4.2" + case "^1.6.3" + +"@cspotcode/source-map-support@^0.8.0": + version "0.8.1" + resolved "https://registry.yarnpkg.com/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz#00629c35a688e05a88b1cda684fb9d5e73f000a1" + integrity sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw== + dependencies: + "@jridgewell/trace-mapping" "0.3.9" + +"@ethersproject/abi@5.7.0", "@ethersproject/abi@^5.1.2", "@ethersproject/abi@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abi/-/abi-5.7.0.tgz#b3f3e045bbbeed1af3947335c247ad625a44e449" + integrity sha512-351ktp42TiRcYB3H1OP8yajPeAQstMW/yCFokj/AthP9bLHzQFPlOrxOcwYEDkUAICmOHljvN4K39OMTMUa9RA== + dependencies: + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/abstract-provider@5.7.0", "@ethersproject/abstract-provider@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abstract-provider/-/abstract-provider-5.7.0.tgz#b0a8550f88b6bf9d51f90e4795d48294630cb9ef" + integrity sha512-R41c9UkchKCpAqStMYUpdunjo3pkEvZC3FAwZn5S5MGbXoMQOHIdHItezTETxAO5bevtMApSyEhn9+CHcDsWBw== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/networks" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/web" "^5.7.0" + +"@ethersproject/abstract-signer@5.7.0", "@ethersproject/abstract-signer@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/abstract-signer/-/abstract-signer-5.7.0.tgz#13f4f32117868452191a4649723cb086d2b596b2" + integrity sha512-a16V8bq1/Cz+TGCkE2OPMTOUDLS3grCpdjoJCYNnVBbdYEMSgKrU0+B90s8b6H+ByYTBZN7a3g76jdIJi7UfKQ== + dependencies: + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + +"@ethersproject/address@5.7.0", "@ethersproject/address@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/address/-/address-5.7.0.tgz#19b56c4d74a3b0a46bfdbb6cfcc0a153fc697f37" + integrity sha512-9wYhYt7aghVGo758POM5nqcOMaE168Q6aRLJZwUmiqSrAungkG74gSSeKEIR7ukixesdRZGPgVqme6vmxs1fkA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + +"@ethersproject/base64@5.7.0", "@ethersproject/base64@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/base64/-/base64-5.7.0.tgz#ac4ee92aa36c1628173e221d0d01f53692059e1c" + integrity sha512-Dr8tcHt2mEbsZr/mwTPIQAf3Ai0Bks/7gTw9dSqk1mQvhW3XvRlmDJr/4n+wg1JmCl16NZue17CDh8xb/vZ0sQ== + dependencies: + "@ethersproject/bytes" "^5.7.0" + +"@ethersproject/basex@5.7.0", "@ethersproject/basex@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/basex/-/basex-5.7.0.tgz#97034dc7e8938a8ca943ab20f8a5e492ece4020b" + integrity sha512-ywlh43GwZLv2Voc2gQVTKBoVQ1mti3d8HK5aMxsfu/nRDnMmNqaSJ3r3n85HBByT8OpoY96SXM1FogC533T4zw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + +"@ethersproject/bignumber@5.7.0", "@ethersproject/bignumber@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/bignumber/-/bignumber-5.7.0.tgz#e2f03837f268ba655ffba03a57853e18a18dc9c2" + integrity sha512-n1CAdIHRWjSucQO3MC1zPSVgV/6dy/fjL9pMrPP9peL+QxEg9wOsVqwD4+818B6LUEtaXzVHQiuivzRoxPxUGw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + bn.js "^5.2.1" + +"@ethersproject/bytes@5.7.0", "@ethersproject/bytes@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/bytes/-/bytes-5.7.0.tgz#a00f6ea8d7e7534d6d87f47188af1148d71f155d" + integrity sha512-nsbxwgFXWh9NyYWo+U8atvmMsSdKJprTcICAkvbBffT75qDocbuggBU0SJiVK2MuTrp0q+xvLkTnGMPK1+uA9A== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/constants@5.7.0", "@ethersproject/constants@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/constants/-/constants-5.7.0.tgz#df80a9705a7e08984161f09014ea012d1c75295e" + integrity sha512-DHI+y5dBNvkpYUMiRQyxRBYBefZkJfo70VUkUAsRjcPs47muV9evftfZ0PJVCXYbAiCgght0DtcF9srFQmIgWA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + +"@ethersproject/contracts@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/contracts/-/contracts-5.7.0.tgz#c305e775abd07e48aa590e1a877ed5c316f8bd1e" + integrity sha512-5GJbzEU3X+d33CdfPhcyS+z8MzsTrBGk/sc+G+59+tPa9yFkl6HQ9D6L0QMgNTA9q8dT0XKxxkyp883XsQvbbg== + dependencies: + "@ethersproject/abi" "^5.7.0" + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + +"@ethersproject/hash@5.7.0", "@ethersproject/hash@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/hash/-/hash-5.7.0.tgz#eb7aca84a588508369562e16e514b539ba5240a7" + integrity sha512-qX5WrQfnah1EFnO5zJv1v46a8HW0+E5xuBBDTwMFZLuVTx0tbU2kkx15NqdjxecrLGatQN9FGQKpb1FKdHCt+g== + dependencies: + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/base64" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/hdnode@5.7.0", "@ethersproject/hdnode@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/hdnode/-/hdnode-5.7.0.tgz#e627ddc6b466bc77aebf1a6b9e47405ca5aef9cf" + integrity sha512-OmyYo9EENBPPf4ERhR7oj6uAtUAhYGqOnIS+jE5pTXvdKBS99ikzq1E7Iv0ZQZ5V36Lqx1qZLeak0Ra16qpeOg== + dependencies: + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/basex" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/pbkdf2" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + "@ethersproject/signing-key" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/wordlists" "^5.7.0" + +"@ethersproject/json-wallets@5.7.0", "@ethersproject/json-wallets@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/json-wallets/-/json-wallets-5.7.0.tgz#5e3355287b548c32b368d91014919ebebddd5360" + integrity sha512-8oee5Xgu6+RKgJTkvEMl2wDgSPSAQ9MB/3JYjFV9jlKvcYHUXZC+cQp0njgmxdHkYWn8s6/IqIZYm0YWCjO/0g== + dependencies: + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/hdnode" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/pbkdf2" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/random" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + aes-js "3.0.0" + scrypt-js "3.0.1" + +"@ethersproject/keccak256@5.7.0", "@ethersproject/keccak256@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/keccak256/-/keccak256-5.7.0.tgz#3186350c6e1cd6aba7940384ec7d6d9db01f335a" + integrity sha512-2UcPboeL/iW+pSg6vZ6ydF8tCnv3Iu/8tUmLLzWWGzxWKFFqOBQFLo6uLUv6BDrLgCDfN28RJ/wtByx+jZ4KBg== + dependencies: + "@ethersproject/bytes" "^5.7.0" + js-sha3 "0.8.0" + +"@ethersproject/logger@5.7.0", "@ethersproject/logger@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/logger/-/logger-5.7.0.tgz#6ce9ae168e74fecf287be17062b590852c311892" + integrity sha512-0odtFdXu/XHtjQXJYA3u9G0G8btm0ND5Cu8M7i5vhEcE8/HmF4Lbdqanwyv4uQTr2tx6b7fQRmgLrsnpQlmnig== + +"@ethersproject/networks@5.7.1", "@ethersproject/networks@^5.7.0": + version "5.7.1" + resolved "https://registry.yarnpkg.com/@ethersproject/networks/-/networks-5.7.1.tgz#118e1a981d757d45ccea6bb58d9fd3d9db14ead6" + integrity sha512-n/MufjFYv3yFcUyfhnXotyDlNdFb7onmkSy8aQERi2PjNcnWQ66xXxa3XlS8nCcA8aJKJjIIMNJTC7tu80GwpQ== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/pbkdf2@5.7.0", "@ethersproject/pbkdf2@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/pbkdf2/-/pbkdf2-5.7.0.tgz#d2267d0a1f6e123f3771007338c47cccd83d3102" + integrity sha512-oR/dBRZR6GTyaofd86DehG72hY6NpAjhabkhxgr3X2FpJtJuodEl2auADWBZfhDHgVCbu3/H/Ocq2uC6dpNjjw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + +"@ethersproject/properties@5.7.0", "@ethersproject/properties@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/properties/-/properties-5.7.0.tgz#a6e12cb0439b878aaf470f1902a176033067ed30" + integrity sha512-J87jy8suntrAkIZtecpxEPxY//szqr1mlBaYlQ0r4RCaiD2hjheqF9s1LVE8vVuJCXisjIP+JgtK/Do54ej4Sw== + dependencies: + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/providers@5.7.2", "@ethersproject/providers@^5.7.1", "@ethersproject/providers@^5.7.2": + version "5.7.2" + resolved "https://registry.yarnpkg.com/@ethersproject/providers/-/providers-5.7.2.tgz#f8b1a4f275d7ce58cf0a2eec222269a08beb18cb" + integrity sha512-g34EWZ1WWAVgr4aptGlVBF8mhl3VWjv+8hoAnzStu8Ah22VHBsuGzP17eb6xDVRzw895G4W7vvx60lFFur/1Rg== + dependencies: + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/base64" "^5.7.0" + "@ethersproject/basex" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/networks" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/random" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/web" "^5.7.0" + bech32 "1.1.4" + ws "7.4.6" + +"@ethersproject/random@5.7.0", "@ethersproject/random@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/random/-/random-5.7.0.tgz#af19dcbc2484aae078bb03656ec05df66253280c" + integrity sha512-19WjScqRA8IIeWclFme75VMXSBvi4e6InrUNuaR4s5pTF2qNhcGdCUwdxUVGtDDqC00sDLCO93jPQoDUH4HVmQ== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/rlp@5.7.0", "@ethersproject/rlp@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/rlp/-/rlp-5.7.0.tgz#de39e4d5918b9d74d46de93af80b7685a9c21304" + integrity sha512-rBxzX2vK8mVF7b0Tol44t5Tb8gomOHkj5guL+HhzQ1yBh/ydjGnpw6at+X6Iw0Kp3OzzzkcKp8N9r0W4kYSs9w== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/sha2@5.7.0", "@ethersproject/sha2@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/sha2/-/sha2-5.7.0.tgz#9a5f7a7824ef784f7f7680984e593a800480c9fb" + integrity sha512-gKlH42riwb3KYp0reLsFTokByAKoJdgFCwI+CCiX/k+Jm2mbNs6oOaCjYQSlI1+XBVejwH2KrmCbMAT/GnRDQw== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + hash.js "1.1.7" + +"@ethersproject/signing-key@5.7.0", "@ethersproject/signing-key@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/signing-key/-/signing-key-5.7.0.tgz#06b2df39411b00bc57c7c09b01d1e41cf1b16ab3" + integrity sha512-MZdy2nL3wO0u7gkB4nA/pEf8lu1TlFswPNmy8AiYkfKTdO6eXBJyUdmHO/ehm/htHw9K/qF8ujnTyUAD+Ry54Q== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + bn.js "^5.2.1" + elliptic "6.5.4" + hash.js "1.1.7" + +"@ethersproject/solidity@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/solidity/-/solidity-5.7.0.tgz#5e9c911d8a2acce2a5ebb48a5e2e0af20b631cb8" + integrity sha512-HmabMd2Dt/raavyaGukF4XxizWKhKQ24DoLtdNbBmNKUOPqwjsKQSdV9GQtj9CBEea9DlzETlVER1gYeXXBGaA== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/sha2" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/strings@5.7.0", "@ethersproject/strings@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/strings/-/strings-5.7.0.tgz#54c9d2a7c57ae8f1205c88a9d3a56471e14d5ed2" + integrity sha512-/9nu+lj0YswRNSH0NXYqrh8775XNyEdUQAuf3f+SmOrnVewcJ5SBNAjF7lpgehKi4abvNNXyf+HX86czCdJ8Mg== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/transactions@5.7.0", "@ethersproject/transactions@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/transactions/-/transactions-5.7.0.tgz#91318fc24063e057885a6af13fdb703e1f993d3b" + integrity sha512-kmcNicCp1lp8qanMTC3RIikGgoJ80ztTyvtsFvCYpSCfkjhD0jZ2LOrnbcuxuToLIUYYf+4XwD1rP+B/erDIhQ== + dependencies: + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/rlp" "^5.7.0" + "@ethersproject/signing-key" "^5.7.0" + +"@ethersproject/units@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/units/-/units-5.7.0.tgz#637b563d7e14f42deeee39245275d477aae1d8b1" + integrity sha512-pD3xLMy3SJu9kG5xDGI7+xhTEmGXlEqXU4OfNapmfnxLVY4EMSSRp7j1k7eezutBPH7RBN/7QPnwR7hzNlEFeg== + dependencies: + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/constants" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + +"@ethersproject/wallet@5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/wallet/-/wallet-5.7.0.tgz#4e5d0790d96fe21d61d38fb40324e6c7ef350b2d" + integrity sha512-MhmXlJXEJFBFVKrDLB4ZdDzxcBxQ3rLyCkhNqVu3CDYvR97E+8r01UgrI+TI99Le+aYm/in/0vp86guJuM7FCA== + dependencies: + "@ethersproject/abstract-provider" "^5.7.0" + "@ethersproject/abstract-signer" "^5.7.0" + "@ethersproject/address" "^5.7.0" + "@ethersproject/bignumber" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/hdnode" "^5.7.0" + "@ethersproject/json-wallets" "^5.7.0" + "@ethersproject/keccak256" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/random" "^5.7.0" + "@ethersproject/signing-key" "^5.7.0" + "@ethersproject/transactions" "^5.7.0" + "@ethersproject/wordlists" "^5.7.0" + +"@ethersproject/web@5.7.1", "@ethersproject/web@^5.7.0": + version "5.7.1" + resolved "https://registry.yarnpkg.com/@ethersproject/web/-/web-5.7.1.tgz#de1f285b373149bee5928f4eb7bcb87ee5fbb4ae" + integrity sha512-Gueu8lSvyjBWL4cYsWsjh6MtMwM0+H4HvqFPZfB6dV8ctbP9zFAO73VG1cMWae0FLPCtz0peKPpZY8/ugJJX2w== + dependencies: + "@ethersproject/base64" "^5.7.0" + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@ethersproject/wordlists@5.7.0", "@ethersproject/wordlists@^5.7.0": + version "5.7.0" + resolved "https://registry.yarnpkg.com/@ethersproject/wordlists/-/wordlists-5.7.0.tgz#8fb2c07185d68c3e09eb3bfd6e779ba2774627f5" + integrity sha512-S2TFNJNfHWVHNE6cNDjbVlZ6MgE17MIxMbMg2zv3wn+3XSJGosL1m9ZVv3GXCf/2ymSsQ+hRI5IzoMJTG6aoVA== + dependencies: + "@ethersproject/bytes" "^5.7.0" + "@ethersproject/hash" "^5.7.0" + "@ethersproject/logger" "^5.7.0" + "@ethersproject/properties" "^5.7.0" + "@ethersproject/strings" "^5.7.0" + +"@jridgewell/resolve-uri@^3.0.3": + version "3.1.1" + resolved "https://registry.yarnpkg.com/@jridgewell/resolve-uri/-/resolve-uri-3.1.1.tgz#c08679063f279615a3326583ba3a90d1d82cc721" + integrity sha512-dSYZh7HhCDtCKm4QakX0xFpsRDqjjtZf/kjI/v3T3Nwt5r8/qz/M19F9ySyOqU94SXBmeG9ttTul+YnR4LOxFA== + +"@jridgewell/sourcemap-codec@^1.4.10": + version "1.4.15" + resolved "https://registry.yarnpkg.com/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz#d7c6e6755c78567a951e04ab52ef0fd26de59f32" + integrity sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg== + +"@jridgewell/trace-mapping@0.3.9": + version "0.3.9" + resolved "https://registry.yarnpkg.com/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz#6534fd5933a53ba7cbf3a17615e273a0d1273ff9" + integrity sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ== + dependencies: + "@jridgewell/resolve-uri" "^3.0.3" + "@jridgewell/sourcemap-codec" "^1.4.10" + +"@matterlabs/hardhat-zksync-deploy@^0.6.5": + version "0.6.5" + resolved "https://registry.yarnpkg.com/@matterlabs/hardhat-zksync-deploy/-/hardhat-zksync-deploy-0.6.5.tgz#fe56bf30850e71c8d328ac1a06a100c1a0af6e3e" + integrity sha512-EZpvn8pDslfO3UA2obT8FOi5jsHhxYS5ndIR7tjL2zXKbvkbpoJR5rgKoGTJJm0riaCud674sQcxMOybVQ+2gg== + dependencies: + "@matterlabs/hardhat-zksync-solc" "0.4.2" + chalk "4.1.2" + ts-morph "^19.0.0" + +"@matterlabs/hardhat-zksync-solc@0.4.2", "@matterlabs/hardhat-zksync-solc@^0.4.2": + version "0.4.2" + resolved "https://registry.yarnpkg.com/@matterlabs/hardhat-zksync-solc/-/hardhat-zksync-solc-0.4.2.tgz#64121082e88c5ab22eb4e9594d120e504f6af499" + integrity sha512-6NFWPSZiOAoo7wNuhMg4ztj7mMEH+tLrx09WuCbcURrHPijj/KxYNsJD6Uw5lapKr7G8H7SQISGid1/MTXVmXQ== + dependencies: + "@nomiclabs/hardhat-docker" "^2.0.0" + chalk "4.1.2" + dockerode "^3.3.4" + fs-extra "^11.1.1" + proper-lockfile "^4.1.2" + semver "^7.5.1" + +"@metamask/eth-sig-util@^4.0.0": + version "4.0.1" + resolved "https://registry.yarnpkg.com/@metamask/eth-sig-util/-/eth-sig-util-4.0.1.tgz#3ad61f6ea9ad73ba5b19db780d40d9aae5157088" + integrity sha512-tghyZKLHZjcdlDqCA3gNZmLeR0XvOE9U1qoQO9ohyAZT6Pya+H9vkBPcsyXytmYLNgVoin7CKCmweo/R43V+tQ== + dependencies: + ethereumjs-abi "^0.6.8" + ethereumjs-util "^6.2.1" + ethjs-util "^0.1.6" + tweetnacl "^1.0.3" + tweetnacl-util "^0.15.1" + +"@noble/hashes@1.2.0", "@noble/hashes@~1.2.0": + version "1.2.0" + resolved "https://registry.yarnpkg.com/@noble/hashes/-/hashes-1.2.0.tgz#a3150eeb09cc7ab207ebf6d7b9ad311a9bdbed12" + integrity sha512-FZfhjEDbT5GRswV3C6uvLPHMiVD6lQBmpoX5+eSiPaMTXte/IKqI5dykDxzZB/WBeK/CDuQRBWarPdi3FNY2zQ== + +"@noble/secp256k1@1.7.1", "@noble/secp256k1@~1.7.0": + version "1.7.1" + resolved "https://registry.yarnpkg.com/@noble/secp256k1/-/secp256k1-1.7.1.tgz#b251c70f824ce3ca7f8dc3df08d58f005cc0507c" + integrity sha512-hOUk6AyBFmqVrv7k5WAw/LpszxVbj9gGN4JRkIX52fdFAj1UA61KXmZDvqVEm+pOyec3+fIeZB02LYa/pWOArw== + +"@nodelib/fs.scandir@2.1.5": + version "2.1.5" + resolved "https://registry.yarnpkg.com/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz#7619c2eb21b25483f6d167548b4cfd5a7488c3d5" + integrity sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g== + dependencies: + "@nodelib/fs.stat" "2.0.5" + run-parallel "^1.1.9" + +"@nodelib/fs.stat@2.0.5", "@nodelib/fs.stat@^2.0.2": + version "2.0.5" + resolved "https://registry.yarnpkg.com/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz#5bd262af94e9d25bd1e71b05deed44876a222e8b" + integrity sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A== + +"@nodelib/fs.walk@^1.2.3": + version "1.2.8" + resolved "https://registry.yarnpkg.com/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz#e95737e8bb6746ddedf69c556953494f196fe69a" + integrity sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg== + dependencies: + "@nodelib/fs.scandir" "2.1.5" + fastq "^1.6.0" + +"@nomicfoundation/ethereumjs-block@5.0.2": + version "5.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-block/-/ethereumjs-block-5.0.2.tgz#13a7968f5964f1697da941281b7f7943b0465d04" + integrity sha512-hSe6CuHI4SsSiWWjHDIzWhSiAVpzMUcDRpWYzN0T9l8/Rz7xNn3elwVOJ/tAyS0LqL6vitUD78Uk7lQDXZun7Q== + dependencies: + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-trie" "6.0.2" + "@nomicfoundation/ethereumjs-tx" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + ethereum-cryptography "0.1.3" + ethers "^5.7.1" + +"@nomicfoundation/ethereumjs-blockchain@7.0.2": + version "7.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-blockchain/-/ethereumjs-blockchain-7.0.2.tgz#45323b673b3d2fab6b5008535340d1b8fea7d446" + integrity sha512-8UUsSXJs+MFfIIAKdh3cG16iNmWzWC/91P40sazNvrqhhdR/RtGDlFk2iFTGbBAZPs2+klZVzhRX8m2wvuvz3w== + dependencies: + "@nomicfoundation/ethereumjs-block" "5.0.2" + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-ethash" "3.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-trie" "6.0.2" + "@nomicfoundation/ethereumjs-tx" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + abstract-level "^1.0.3" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + level "^8.0.0" + lru-cache "^5.1.1" + memory-level "^1.0.0" + +"@nomicfoundation/ethereumjs-common@4.0.2": + version "4.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-common/-/ethereumjs-common-4.0.2.tgz#a15d1651ca36757588fdaf2a7d381a150662a3c3" + integrity sha512-I2WGP3HMGsOoycSdOTSqIaES0ughQTueOsddJ36aYVpI3SN8YSusgRFLwzDJwRFVIYDKx/iJz0sQ5kBHVgdDwg== + dependencies: + "@nomicfoundation/ethereumjs-util" "9.0.2" + crc-32 "^1.2.0" + +"@nomicfoundation/ethereumjs-ethash@3.0.2": + version "3.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-ethash/-/ethereumjs-ethash-3.0.2.tgz#da77147f806401ee996bfddfa6487500118addca" + integrity sha512-8PfoOQCcIcO9Pylq0Buijuq/O73tmMVURK0OqdjhwqcGHYC2PwhbajDh7GZ55ekB0Px197ajK3PQhpKoiI/UPg== + dependencies: + "@nomicfoundation/ethereumjs-block" "5.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + abstract-level "^1.0.3" + bigint-crypto-utils "^3.0.23" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-evm@2.0.2": + version "2.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-evm/-/ethereumjs-evm-2.0.2.tgz#4c2f4b84c056047102a4fa41c127454e3f0cfcf6" + integrity sha512-rBLcUaUfANJxyOx9HIdMX6uXGin6lANCulIm/pjMgRqfiCRMZie3WKYxTSd8ZE/d+qT+zTedBF4+VHTdTSePmQ== + dependencies: + "@ethersproject/providers" "^5.7.1" + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-tx" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + mcl-wasm "^0.7.1" + rustbn.js "~0.2.0" + +"@nomicfoundation/ethereumjs-rlp@5.0.2": + version "5.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-rlp/-/ethereumjs-rlp-5.0.2.tgz#4fee8dc58a53ac6ae87fb1fca7c15dc06c6b5dea" + integrity sha512-QwmemBc+MMsHJ1P1QvPl8R8p2aPvvVcKBbvHnQOKBpBztEo0omN0eaob6FeZS/e3y9NSe+mfu3nNFBHszqkjTA== + +"@nomicfoundation/ethereumjs-statemanager@2.0.2": + version "2.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-statemanager/-/ethereumjs-statemanager-2.0.2.tgz#3ba4253b29b1211cafe4f9265fee5a0d780976e0" + integrity sha512-dlKy5dIXLuDubx8Z74sipciZnJTRSV/uHG48RSijhgm1V7eXYFC567xgKtsKiVZB1ViTP9iFL4B6Je0xD6X2OA== + dependencies: + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + ethers "^5.7.1" + js-sdsl "^4.1.4" + +"@nomicfoundation/ethereumjs-trie@6.0.2": + version "6.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-trie/-/ethereumjs-trie-6.0.2.tgz#9a6dbd28482dca1bc162d12b3733acab8cd12835" + integrity sha512-yw8vg9hBeLYk4YNg5MrSJ5H55TLOv2FSWUTROtDtTMMmDGROsAu+0tBjiNGTnKRi400M6cEzoFfa89Fc5k8NTQ== + dependencies: + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + "@types/readable-stream" "^2.3.13" + ethereum-cryptography "0.1.3" + readable-stream "^3.6.0" + +"@nomicfoundation/ethereumjs-tx@5.0.2": + version "5.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-tx/-/ethereumjs-tx-5.0.2.tgz#117813b69c0fdc14dd0446698a64be6df71d7e56" + integrity sha512-T+l4/MmTp7VhJeNloMkM+lPU3YMUaXdcXgTGCf8+ZFvV9NYZTRLFekRwlG6/JMmVfIfbrW+dRRJ9A6H5Q/Z64g== + dependencies: + "@chainsafe/ssz" "^0.9.2" + "@ethersproject/providers" "^5.7.2" + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-util@9.0.2": + version "9.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-util/-/ethereumjs-util-9.0.2.tgz#16bdc1bb36f333b8a3559bbb4b17dac805ce904d" + integrity sha512-4Wu9D3LykbSBWZo8nJCnzVIYGvGCuyiYLIJa9XXNVt1q1jUzHdB+sJvx95VGCpPkCT+IbLecW6yfzy3E1bQrwQ== + dependencies: + "@chainsafe/ssz" "^0.10.0" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + ethereum-cryptography "0.1.3" + +"@nomicfoundation/ethereumjs-vm@7.0.2": + version "7.0.2" + resolved "https://registry.yarnpkg.com/@nomicfoundation/ethereumjs-vm/-/ethereumjs-vm-7.0.2.tgz#3b0852cb3584df0e18c182d0672a3596c9ca95e6" + integrity sha512-Bj3KZT64j54Tcwr7Qm/0jkeZXJMfdcAtRBedou+Hx0dPOSIgqaIr0vvLwP65TpHbak2DmAq+KJbW2KNtIoFwvA== + dependencies: + "@nomicfoundation/ethereumjs-block" "5.0.2" + "@nomicfoundation/ethereumjs-blockchain" "7.0.2" + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-evm" "2.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-statemanager" "2.0.2" + "@nomicfoundation/ethereumjs-trie" "6.0.2" + "@nomicfoundation/ethereumjs-tx" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + debug "^4.3.3" + ethereum-cryptography "0.1.3" + mcl-wasm "^0.7.1" + rustbn.js "~0.2.0" + +"@nomicfoundation/solidity-analyzer-darwin-arm64@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-darwin-arm64/-/solidity-analyzer-darwin-arm64-0.1.1.tgz#4c858096b1c17fe58a474fe81b46815f93645c15" + integrity sha512-KcTodaQw8ivDZyF+D76FokN/HdpgGpfjc/gFCImdLUyqB6eSWVaZPazMbeAjmfhx3R0zm/NYVzxwAokFKgrc0w== + +"@nomicfoundation/solidity-analyzer-darwin-x64@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-darwin-x64/-/solidity-analyzer-darwin-x64-0.1.1.tgz#6e25ccdf6e2d22389c35553b64fe6f3fdaec432c" + integrity sha512-XhQG4BaJE6cIbjAVtzGOGbK3sn1BO9W29uhk9J8y8fZF1DYz0Doj8QDMfpMu+A6TjPDs61lbsmeYodIDnfveSA== + +"@nomicfoundation/solidity-analyzer-freebsd-x64@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-freebsd-x64/-/solidity-analyzer-freebsd-x64-0.1.1.tgz#0a224ea50317139caeebcdedd435c28a039d169c" + integrity sha512-GHF1VKRdHW3G8CndkwdaeLkVBi5A9u2jwtlS7SLhBc8b5U/GcoL39Q+1CSO3hYqePNP+eV5YI7Zgm0ea6kMHoA== + +"@nomicfoundation/solidity-analyzer-linux-arm64-gnu@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-arm64-gnu/-/solidity-analyzer-linux-arm64-gnu-0.1.1.tgz#dfa085d9ffab9efb2e7b383aed3f557f7687ac2b" + integrity sha512-g4Cv2fO37ZsUENQ2vwPnZc2zRenHyAxHcyBjKcjaSmmkKrFr64yvzeNO8S3GBFCo90rfochLs99wFVGT/0owpg== + +"@nomicfoundation/solidity-analyzer-linux-arm64-musl@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-arm64-musl/-/solidity-analyzer-linux-arm64-musl-0.1.1.tgz#c9e06b5d513dd3ab02a7ac069c160051675889a4" + integrity sha512-WJ3CE5Oek25OGE3WwzK7oaopY8xMw9Lhb0mlYuJl/maZVo+WtP36XoQTb7bW/i8aAdHW5Z+BqrHMux23pvxG3w== + +"@nomicfoundation/solidity-analyzer-linux-x64-gnu@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-x64-gnu/-/solidity-analyzer-linux-x64-gnu-0.1.1.tgz#8d328d16839e52571f72f2998c81e46bf320f893" + integrity sha512-5WN7leSr5fkUBBjE4f3wKENUy9HQStu7HmWqbtknfXkkil+eNWiBV275IOlpXku7v3uLsXTOKpnnGHJYI2qsdA== + +"@nomicfoundation/solidity-analyzer-linux-x64-musl@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-linux-x64-musl/-/solidity-analyzer-linux-x64-musl-0.1.1.tgz#9b49d0634b5976bb5ed1604a1e1b736f390959bb" + integrity sha512-KdYMkJOq0SYPQMmErv/63CwGwMm5XHenEna9X9aB8mQmhDBrYrlAOSsIPgFCUSL0hjxE3xHP65/EPXR/InD2+w== + +"@nomicfoundation/solidity-analyzer-win32-arm64-msvc@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-arm64-msvc/-/solidity-analyzer-win32-arm64-msvc-0.1.1.tgz#e2867af7264ebbcc3131ef837878955dd6a3676f" + integrity sha512-VFZASBfl4qiBYwW5xeY20exWhmv6ww9sWu/krWSesv3q5hA0o1JuzmPHR4LPN6SUZj5vcqci0O6JOL8BPw+APg== + +"@nomicfoundation/solidity-analyzer-win32-ia32-msvc@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-ia32-msvc/-/solidity-analyzer-win32-ia32-msvc-0.1.1.tgz#0685f78608dd516c8cdfb4896ed451317e559585" + integrity sha512-JnFkYuyCSA70j6Si6cS1A9Gh1aHTEb8kOTBApp/c7NRTFGNMH8eaInKlyuuiIbvYFhlXW4LicqyYuWNNq9hkpQ== + +"@nomicfoundation/solidity-analyzer-win32-x64-msvc@0.1.1": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer-win32-x64-msvc/-/solidity-analyzer-win32-x64-msvc-0.1.1.tgz#c9a44f7108646f083b82e851486e0f6aeb785836" + integrity sha512-HrVJr6+WjIXGnw3Q9u6KQcbZCtk0caVWhCdFADySvRyUxJ8PnzlaP+MhwNE8oyT8OZ6ejHBRrrgjSqDCFXGirw== + +"@nomicfoundation/solidity-analyzer@^0.1.0": + version "0.1.1" + resolved "https://registry.yarnpkg.com/@nomicfoundation/solidity-analyzer/-/solidity-analyzer-0.1.1.tgz#f5f4d36d3f66752f59a57e7208cd856f3ddf6f2d" + integrity sha512-1LMtXj1puAxyFusBgUIy5pZk3073cNXYnXUpuNKFghHbIit/xZgbk0AokpUADbNm3gyD6bFWl3LRFh3dhVdREg== + optionalDependencies: + "@nomicfoundation/solidity-analyzer-darwin-arm64" "0.1.1" + "@nomicfoundation/solidity-analyzer-darwin-x64" "0.1.1" + "@nomicfoundation/solidity-analyzer-freebsd-x64" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-arm64-gnu" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-arm64-musl" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-x64-gnu" "0.1.1" + "@nomicfoundation/solidity-analyzer-linux-x64-musl" "0.1.1" + "@nomicfoundation/solidity-analyzer-win32-arm64-msvc" "0.1.1" + "@nomicfoundation/solidity-analyzer-win32-ia32-msvc" "0.1.1" + "@nomicfoundation/solidity-analyzer-win32-x64-msvc" "0.1.1" + +"@nomiclabs/hardhat-docker@^2.0.0": + version "2.0.2" + resolved "https://registry.yarnpkg.com/@nomiclabs/hardhat-docker/-/hardhat-docker-2.0.2.tgz#ae964be17951275a55859ff7358e9e7c77448846" + integrity sha512-XgGEpRT3wlA1VslyB57zyAHV+oll8KnV1TjwnxxC1tpAL04/lbdwpdO5KxInVN8irMSepqFpsiSkqlcnvbE7Ng== + dependencies: + dockerode "^2.5.8" + fs-extra "^7.0.1" + node-fetch "^2.6.0" + +"@nomiclabs/hardhat-ethers@^2.0.6": + version "2.2.3" + resolved "https://registry.yarnpkg.com/@nomiclabs/hardhat-ethers/-/hardhat-ethers-2.2.3.tgz#b41053e360c31a32c2640c9a45ee981a7e603fe0" + integrity sha512-YhzPdzb612X591FOe68q+qXVXGG2ANZRvDo0RRUtimev85rCrAlv/TLMEZw5c+kq9AbzocLTVX/h2jVIFPL9Xg== + +"@nomiclabs/hardhat-solpp@^2.0.1": + version "2.0.1" + resolved "https://registry.yarnpkg.com/@nomiclabs/hardhat-solpp/-/hardhat-solpp-2.0.1.tgz#04039b3745b8d2b48c9b8bec6509e9785631aaba" + integrity sha512-aWYvB91GPJcnye4Ph26Jd9BfBNNisI1iRNSbHB2i09OpxucSHAPMvvqTfWDN1HE5EMjqlTJ2rQLdlDcYqQxPJw== + dependencies: + fs-extra "^7.0.1" + solpp "^0.11.5" + +"@scure/base@~1.1.0": + version "1.1.3" + resolved "https://registry.yarnpkg.com/@scure/base/-/base-1.1.3.tgz#8584115565228290a6c6c4961973e0903bb3df2f" + integrity sha512-/+SgoRjLq7Xlf0CWuLHq2LUZeL/w65kfzAPG5NH9pcmBhs+nunQTn4gvdwgMTIXnt9b2C/1SeL2XiysZEyIC9Q== + +"@scure/bip32@1.1.5": + version "1.1.5" + resolved "https://registry.yarnpkg.com/@scure/bip32/-/bip32-1.1.5.tgz#d2ccae16dcc2e75bc1d75f5ef3c66a338d1ba300" + integrity sha512-XyNh1rB0SkEqd3tXcXMi+Xe1fvg+kUIcoRIEujP1Jgv7DqW2r9lg3Ah0NkFaCs9sTkQAQA8kw7xiRXzENi9Rtw== + dependencies: + "@noble/hashes" "~1.2.0" + "@noble/secp256k1" "~1.7.0" + "@scure/base" "~1.1.0" + +"@scure/bip39@1.1.1": + version "1.1.1" + resolved "https://registry.yarnpkg.com/@scure/bip39/-/bip39-1.1.1.tgz#b54557b2e86214319405db819c4b6a370cf340c5" + integrity sha512-t+wDck2rVkh65Hmv280fYdVdY25J9YeEUIgn2LG1WM6gxFkGzcksoDiUkWVpVp3Oex9xGC68JU2dSbUfwZ2jPg== + dependencies: + "@noble/hashes" "~1.2.0" + "@scure/base" "~1.1.0" + +"@sentry/core@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/core/-/core-5.30.0.tgz#6b203664f69e75106ee8b5a2fe1d717379b331f3" + integrity sha512-TmfrII8w1PQZSZgPpUESqjB+jC6MvZJZdLtE/0hZ+SrnKhW3x5WlYLvTXZpcWePYBku7rl2wn1RZu6uT0qCTeg== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/minimal" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/hub@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/hub/-/hub-5.30.0.tgz#2453be9b9cb903404366e198bd30c7ca74cdc100" + integrity sha512-2tYrGnzb1gKz2EkMDQcfLrDTvmGcQPuWxLnJKXJvYTQDGLlEvi2tWz1VIHjunmOvJrB5aIQLhm+dcMRwFZDCqQ== + dependencies: + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/minimal@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/minimal/-/minimal-5.30.0.tgz#ce3d3a6a273428e0084adcb800bc12e72d34637b" + integrity sha512-BwWb/owZKtkDX+Sc4zCSTNcvZUq7YcH3uAVlmh/gtR9rmUvbzAA3ewLuB3myi4wWRAMEtny6+J/FN/x+2wn9Xw== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/types" "5.30.0" + tslib "^1.9.3" + +"@sentry/node@^5.18.1": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/node/-/node-5.30.0.tgz#4ca479e799b1021285d7fe12ac0858951c11cd48" + integrity sha512-Br5oyVBF0fZo6ZS9bxbJZG4ApAjRqAnqFFurMVJJdunNb80brh7a5Qva2kjhm+U6r9NJAB5OmDyPkA1Qnt+QVg== + dependencies: + "@sentry/core" "5.30.0" + "@sentry/hub" "5.30.0" + "@sentry/tracing" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + cookie "^0.4.1" + https-proxy-agent "^5.0.0" + lru_map "^0.3.3" + tslib "^1.9.3" + +"@sentry/tracing@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/tracing/-/tracing-5.30.0.tgz#501d21f00c3f3be7f7635d8710da70d9419d4e1f" + integrity sha512-dUFowCr0AIMwiLD7Fs314Mdzcug+gBVo/+NCMyDw8tFxJkwWAKl7Qa2OZxLQ0ZHjakcj1hNKfCQJ9rhyfOl4Aw== + dependencies: + "@sentry/hub" "5.30.0" + "@sentry/minimal" "5.30.0" + "@sentry/types" "5.30.0" + "@sentry/utils" "5.30.0" + tslib "^1.9.3" + +"@sentry/types@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/types/-/types-5.30.0.tgz#19709bbe12a1a0115bc790b8942917da5636f402" + integrity sha512-R8xOqlSTZ+htqrfteCWU5Nk0CDN5ApUTvrlvBuiH1DyP6czDZ4ktbZB0hAgBlVcK0U+qpD3ag3Tqqpa5Q67rPw== + +"@sentry/utils@5.30.0": + version "5.30.0" + resolved "https://registry.yarnpkg.com/@sentry/utils/-/utils-5.30.0.tgz#9a5bd7ccff85ccfe7856d493bffa64cabc41e980" + integrity sha512-zaYmoH0NWWtvnJjC9/CBseXMtKHm/tm40sz3YfJRxeQjyzRqNQPgivpd9R/oDJCYj999mzdW382p/qi2ypjLww== + dependencies: + "@sentry/types" "5.30.0" + tslib "^1.9.3" + +"@solidity-parser/parser@^0.16.0": + version "0.16.1" + resolved "https://registry.yarnpkg.com/@solidity-parser/parser/-/parser-0.16.1.tgz#f7c8a686974e1536da0105466c4db6727311253c" + integrity sha512-PdhRFNhbTtu3x8Axm0uYpqOy/lODYQK+MlYSgqIsq2L8SFYEHJPHNUiOTAJbDGzNjjr1/n9AcIayxafR/fWmYw== + dependencies: + antlr4ts "^0.5.0-alpha.4" + +"@ts-morph/common@~0.20.0": + version "0.20.0" + resolved "https://registry.yarnpkg.com/@ts-morph/common/-/common-0.20.0.tgz#3f161996b085ba4519731e4d24c35f6cba5b80af" + integrity sha512-7uKjByfbPpwuzkstL3L5MQyuXPSKdoNG93Fmi2JoDcTf3pEP731JdRFAduRVkOs8oqxPsXKA+ScrWkdQ8t/I+Q== + dependencies: + fast-glob "^3.2.12" + minimatch "^7.4.3" + mkdirp "^2.1.6" + path-browserify "^1.0.1" + +"@tsconfig/node10@^1.0.7": + version "1.0.9" + resolved "https://registry.yarnpkg.com/@tsconfig/node10/-/node10-1.0.9.tgz#df4907fc07a886922637b15e02d4cebc4c0021b2" + integrity sha512-jNsYVVxU8v5g43Erja32laIDHXeoNvFEpX33OK4d6hljo3jDhCBDhx5dhCCTMWUojscpAagGiRkBKxpdl9fxqA== + +"@tsconfig/node12@^1.0.7": + version "1.0.11" + resolved "https://registry.yarnpkg.com/@tsconfig/node12/-/node12-1.0.11.tgz#ee3def1f27d9ed66dac6e46a295cffb0152e058d" + integrity sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag== + +"@tsconfig/node14@^1.0.0": + version "1.0.3" + resolved "https://registry.yarnpkg.com/@tsconfig/node14/-/node14-1.0.3.tgz#e4386316284f00b98435bf40f72f75a09dabf6c1" + integrity sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow== + +"@tsconfig/node16@^1.0.2": + version "1.0.4" + resolved "https://registry.yarnpkg.com/@tsconfig/node16/-/node16-1.0.4.tgz#0b92dcc0cc1c81f6f306a381f28e31b1a56536e9" + integrity sha512-vxhUy4J8lyeyinH7Azl1pdd43GJhZH/tP2weN8TntQblOY+A0XbT8DJk1/oCPuOOyg/Ja757rG0CgHcWC8OfMA== + +"@typechain/ethers-v5@^10.0.0": + version "10.2.1" + resolved "https://registry.yarnpkg.com/@typechain/ethers-v5/-/ethers-v5-10.2.1.tgz#50241e6957683281ecfa03fb5a6724d8a3ce2391" + integrity sha512-n3tQmCZjRE6IU4h6lqUGiQ1j866n5MTCBJreNEHHVWXa2u9GJTaeYyU1/k+1qLutkyw+sS6VAN+AbeiTqsxd/A== + dependencies: + lodash "^4.17.15" + ts-essentials "^7.0.1" + +"@typechain/ethers-v6@0.4.0": + version "0.4.0" + resolved "https://registry.yarnpkg.com/@typechain/ethers-v6/-/ethers-v6-0.4.0.tgz#fb9e9b8eeadc455fd1fc9048b2340309860deaca" + integrity sha512-vD3Agzz63Gf2XlU3ed2/y+8dLWQj+wf+4Eq+0JXsyOio/plyV5F6r0yYe+s3XdGI858U3Sr263pl8mliDrUqbw== + dependencies: + lodash "^4.17.15" + ts-essentials "^7.0.1" + +"@typechain/hardhat@8.0.0": + version "8.0.0" + resolved "https://registry.yarnpkg.com/@typechain/hardhat/-/hardhat-8.0.0.tgz#60568b7a2d0260cc741fb0830a8caee8eb06ac64" + integrity sha512-XUVbqlMx8tJTOmzZCD/r196CidtNWAnTBZRcYxjLTKgcJMvc/kHQpWBnVMMB5QHxVKpYpCiz8g07FYCpG8rrjA== + dependencies: + fs-extra "^9.1.0" + +"@types/bn.js@^4.11.3": + version "4.11.6" + resolved "https://registry.yarnpkg.com/@types/bn.js/-/bn.js-4.11.6.tgz#c306c70d9358aaea33cd4eda092a742b9505967c" + integrity sha512-pqr857jrp2kPuO9uRjZ3PwnJTjoQy+fcdxvBTvHm6dkmEL9q+hDD/2j/0ELOBPtPnS8LjCX0gI9nbl8lVkadpg== + dependencies: + "@types/node" "*" + +"@types/bn.js@^5.1.0": + version "5.1.1" + resolved "https://registry.yarnpkg.com/@types/bn.js/-/bn.js-5.1.1.tgz#b51e1b55920a4ca26e9285ff79936bbdec910682" + integrity sha512-qNrYbZqMx0uJAfKnKclPh+dTwK33KfLHYqtyODwd5HnXOjnkhc4qgn3BrK6RWyGZm5+sIFE7Q7Vz6QQtJB7w7g== + dependencies: + "@types/node" "*" + +"@types/chai@^4.3.1": + version "4.3.6" + resolved "https://registry.yarnpkg.com/@types/chai/-/chai-4.3.6.tgz#7b489e8baf393d5dd1266fb203ddd4ea941259e6" + integrity sha512-VOVRLM1mBxIRxydiViqPcKn6MIxZytrbMpd6RJLIWKxUNr3zux8no0Oc7kJx0WAPIitgZ0gkrDS+btlqQpubpw== + +"@types/lru-cache@^5.1.0": + version "5.1.1" + resolved "https://registry.yarnpkg.com/@types/lru-cache/-/lru-cache-5.1.1.tgz#c48c2e27b65d2a153b19bfc1a317e30872e01eef" + integrity sha512-ssE3Vlrys7sdIzs5LOxCzTVMsU7i9oa/IaW92wF32JFb3CVczqOkru2xspuKczHEbG3nvmPY7IFqVmGGHdNbYw== + +"@types/mkdirp@^0.5.2": + version "0.5.2" + resolved "https://registry.yarnpkg.com/@types/mkdirp/-/mkdirp-0.5.2.tgz#503aacfe5cc2703d5484326b1b27efa67a339c1f" + integrity sha512-U5icWpv7YnZYGsN4/cmh3WD2onMY0aJIiTE6+51TwJCttdHvtCYmkBNOobHlXwrJRL0nkH9jH4kD+1FAdMN4Tg== + dependencies: + "@types/node" "*" + +"@types/mocha@^9.1.1": + version "9.1.1" + resolved "https://registry.yarnpkg.com/@types/mocha/-/mocha-9.1.1.tgz#e7c4f1001eefa4b8afbd1eee27a237fee3bf29c4" + integrity sha512-Z61JK7DKDtdKTWwLeElSEBcWGRLY8g95ic5FoQqI9CMx0ns/Ghep3B4DfcEimiKMvtamNVULVNKEsiwV3aQmXw== + +"@types/node@*": + version "20.6.0" + resolved "https://registry.yarnpkg.com/@types/node/-/node-20.6.0.tgz#9d7daa855d33d4efec8aea88cd66db1c2f0ebe16" + integrity sha512-najjVq5KN2vsH2U/xyh2opaSEz6cZMR2SetLIlxlj08nOcmPOemJmUK2o4kUzfLqfrWE0PIrNeE16XhYDd3nqg== + +"@types/node@^17.0.34": + version "17.0.45" + resolved "https://registry.yarnpkg.com/@types/node/-/node-17.0.45.tgz#2c0fafd78705e7a18b7906b5201a522719dc5190" + integrity sha512-w+tIMs3rq2afQdsPJlODhoUEKzFP1ayaoyl1CcnwtIlsVe7K7bA1NGm4s3PraqTLlXnbIN84zuBlxBWo1u9BLw== + +"@types/pbkdf2@^3.0.0": + version "3.1.0" + resolved "https://registry.yarnpkg.com/@types/pbkdf2/-/pbkdf2-3.1.0.tgz#039a0e9b67da0cdc4ee5dab865caa6b267bb66b1" + integrity sha512-Cf63Rv7jCQ0LaL8tNXmEyqTHuIJxRdlS5vMh1mj5voN4+QFhVZnlZruezqpWYDiJ8UTzhP0VmeLXCmBk66YrMQ== + dependencies: + "@types/node" "*" + +"@types/prettier@^2.1.1": + version "2.7.3" + resolved "https://registry.yarnpkg.com/@types/prettier/-/prettier-2.7.3.tgz#3e51a17e291d01d17d3fc61422015a933af7a08f" + integrity sha512-+68kP9yzs4LMp7VNh8gdzMSPZFL44MLGqiHWvttYJe+6qnuVr4Ek9wSBQoveqY/r+LwjCcU29kNVkidwim+kYA== + +"@types/readable-stream@^2.3.13": + version "2.3.15" + resolved "https://registry.yarnpkg.com/@types/readable-stream/-/readable-stream-2.3.15.tgz#3d79c9ceb1b6a57d5f6e6976f489b9b5384321ae" + integrity sha512-oM5JSKQCcICF1wvGgmecmHldZ48OZamtMxcGGVICOJA8o8cahXC1zEVAif8iwoc5j8etxFaRFnf095+CDsuoFQ== + dependencies: + "@types/node" "*" + safe-buffer "~5.1.1" + +"@types/resolve@^0.0.8": + version "0.0.8" + resolved "https://registry.yarnpkg.com/@types/resolve/-/resolve-0.0.8.tgz#f26074d238e02659e323ce1a13d041eee280e194" + integrity sha512-auApPaJf3NPfe18hSoJkp8EbZzer2ISk7o8mCC3M9he/a04+gbMF97NkpD2S8riMGvm4BMRI59/SZQSaLTKpsQ== + dependencies: + "@types/node" "*" + +"@types/secp256k1@^4.0.1": + version "4.0.3" + resolved "https://registry.yarnpkg.com/@types/secp256k1/-/secp256k1-4.0.3.tgz#1b8e55d8e00f08ee7220b4d59a6abe89c37a901c" + integrity sha512-Da66lEIFeIz9ltsdMZcpQvmrmmoqrfju8pm1BH8WbYjZSwUgCwXLb9C+9XYogwBITnbsSaMdVPb2ekf7TV+03w== + dependencies: + "@types/node" "*" + +JSONStream@1.3.2: + version "1.3.2" + resolved "https://registry.yarnpkg.com/JSONStream/-/JSONStream-1.3.2.tgz#c102371b6ec3a7cf3b847ca00c20bb0fce4c6dea" + integrity sha512-mn0KSip7N4e0UDPZHnqDsHECo5uGQrixQKnAskOM1BIB8hd7QKbd6il8IPRPudPHOeHiECoCFqhyMaRO9+nWyA== + dependencies: + jsonparse "^1.2.0" + through ">=2.2.7 <3" + +abstract-level@^1.0.0, abstract-level@^1.0.2, abstract-level@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/abstract-level/-/abstract-level-1.0.3.tgz#78a67d3d84da55ee15201486ab44c09560070741" + integrity sha512-t6jv+xHy+VYwc4xqZMn2Pa9DjcdzvzZmQGRjTFc8spIbRGHgBrEKbPq+rYXc7CCo0lxgYvSgKVg9qZAhpVQSjA== + dependencies: + buffer "^6.0.3" + catering "^2.1.0" + is-buffer "^2.0.5" + level-supports "^4.0.0" + level-transcoder "^1.0.1" + module-error "^1.0.1" + queue-microtask "^1.2.3" + +acorn-walk@^8.1.1: + version "8.2.0" + resolved "https://registry.yarnpkg.com/acorn-walk/-/acorn-walk-8.2.0.tgz#741210f2e2426454508853a2f44d0ab83b7f69c1" + integrity sha512-k+iyHEuPgSw6SbuDpGQM+06HQUa04DZ3o+F6CSzXMvvI5KMvnaEqXe+YVe555R9nn6GPt404fos4wcgpw12SDA== + +acorn@^8.4.1: + version "8.10.0" + resolved "https://registry.yarnpkg.com/acorn/-/acorn-8.10.0.tgz#8be5b3907a67221a81ab23c7889c4c5526b62ec5" + integrity sha512-F0SAmZ8iUtS//m8DmCTA0jlh6TDKkHQyK6xc6V4KDTyZKA9dnvX9/3sRTVQrWm79glUAZbnmmNcdYwUIHWVybw== + +adm-zip@^0.4.16: + version "0.4.16" + resolved "https://registry.yarnpkg.com/adm-zip/-/adm-zip-0.4.16.tgz#cf4c508fdffab02c269cbc7f471a875f05570365" + integrity sha512-TFi4HBKSGfIKsK5YCkKaaFG2m4PEDyViZmEwof3MTIgzimHLto6muaHVpbrljdIvIrFZzEq/p4nafOeLcYegrg== + +aes-js@3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/aes-js/-/aes-js-3.0.0.tgz#e21df10ad6c2053295bcbb8dab40b09dbea87e4d" + integrity sha512-H7wUZRn8WpTq9jocdxQ2c8x2sKo9ZVmzfRE13GiNJXfp7NcKYEdvl3vspKjXox6RIG2VtaRe4JFvxG4rqp2Zuw== + +agent-base@6: + version "6.0.2" + resolved "https://registry.yarnpkg.com/agent-base/-/agent-base-6.0.2.tgz#49fff58577cfee3f37176feab4c22e00f86d7f77" + integrity sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ== + dependencies: + debug "4" + +aggregate-error@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/aggregate-error/-/aggregate-error-3.1.0.tgz#92670ff50f5359bdb7a3e0d40d0ec30c5737687a" + integrity sha512-4I7Td01quW/RpocfNayFdFVk1qSuoh0E7JrbRJ16nH01HhKFQ88INq9Sd+nd72zqRySlr9BmDA8xlEJ6vJMrYA== + dependencies: + clean-stack "^2.0.0" + indent-string "^4.0.0" + +ansi-colors@4.1.1: + version "4.1.1" + resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-4.1.1.tgz#cbb9ae256bf750af1eab344f229aa27fe94ba348" + integrity sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA== + +ansi-colors@^4.1.1: + version "4.1.3" + resolved "https://registry.yarnpkg.com/ansi-colors/-/ansi-colors-4.1.3.tgz#37611340eb2243e70cc604cad35d63270d48781b" + integrity sha512-/6w/C21Pm1A7aZitlI5Ni/2J6FFQN8i1Cvz3kHABAAbw93v/NlvKdVOqz7CCWz/3iv/JplRSEEZ83XION15ovw== + +ansi-escapes@^4.3.0: + version "4.3.2" + resolved "https://registry.yarnpkg.com/ansi-escapes/-/ansi-escapes-4.3.2.tgz#6b2291d1db7d98b6521d5f1efa42d0f3a9feb65e" + integrity sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ== + dependencies: + type-fest "^0.21.3" + +ansi-regex@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-5.0.1.tgz#082cb2c89c9fe8659a311a53bd6a4dc5301db304" + integrity sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ== + +ansi-styles@^3.2.1: + version "3.2.1" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-3.2.1.tgz#41fbb20243e50b12be0f04b8dedbf07520ce841d" + integrity sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA== + dependencies: + color-convert "^1.9.0" + +ansi-styles@^4.0.0, ansi-styles@^4.1.0: + version "4.3.0" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-4.3.0.tgz#edd803628ae71c04c85ae7a0906edad34b648937" + integrity sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg== + dependencies: + color-convert "^2.0.1" + +antlr4@~4.8.0: + version "4.8.0" + resolved "https://registry.yarnpkg.com/antlr4/-/antlr4-4.8.0.tgz#f938ec171be7fc2855cd3a533e87647185b32b6a" + integrity sha512-en/MxQ4OkPgGJQ3wD/muzj1uDnFSzdFIhc2+c6bHZokWkuBb6RRvFjpWhPxWLbgQvaEzldJZ0GSQpfSAaE3hqg== + +antlr4ts@^0.5.0-alpha.4: + version "0.5.0-alpha.4" + resolved "https://registry.yarnpkg.com/antlr4ts/-/antlr4ts-0.5.0-alpha.4.tgz#71702865a87478ed0b40c0709f422cf14d51652a" + integrity sha512-WPQDt1B74OfPv/IMS2ekXAKkTZIHl88uMetg6q3OTqgFxZ/dxDXI0EWLyZid/1Pe6hTftyg5N7gel5wNAGxXyQ== + +any-promise@^1.0.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/any-promise/-/any-promise-1.3.0.tgz#abc6afeedcea52e809cdc0376aed3ce39635d17f" + integrity sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A== + +anymatch@~3.1.2: + version "3.1.3" + resolved "https://registry.yarnpkg.com/anymatch/-/anymatch-3.1.3.tgz#790c58b19ba1720a84205b57c618d5ad8524973e" + integrity sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw== + dependencies: + normalize-path "^3.0.0" + picomatch "^2.0.4" + +arg@^4.1.0: + version "4.1.3" + resolved "https://registry.yarnpkg.com/arg/-/arg-4.1.3.tgz#269fc7ad5b8e42cb63c896d5666017261c144089" + integrity sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA== + +argparse@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/argparse/-/argparse-2.0.1.tgz#246f50f3ca78a3240f6c997e8a9bd1eac49e4b38" + integrity sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q== + +array-back@^3.0.1, array-back@^3.1.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/array-back/-/array-back-3.1.0.tgz#b8859d7a508871c9a7b2cf42f99428f65e96bfb0" + integrity sha512-TkuxA4UCOvxuDK6NZYXCalszEzj+TLszyASooky+i742l9TqsOdYCMJJupxRic61hwquNtppB3hgcuq9SVSH1Q== + +array-back@^4.0.1, array-back@^4.0.2: + version "4.0.2" + resolved "https://registry.yarnpkg.com/array-back/-/array-back-4.0.2.tgz#8004e999a6274586beeb27342168652fdb89fa1e" + integrity sha512-NbdMezxqf94cnNfWLL7V/im0Ub+Anbb0IoZhvzie8+4HJ4nMQuzHuy49FkGYCJK2yAloZ3meiB6AVMClbrI1vg== + +asn1@^0.2.6: + version "0.2.6" + resolved "https://registry.yarnpkg.com/asn1/-/asn1-0.2.6.tgz#0d3a7bb6e64e02a90c0303b31f292868ea09a08d" + integrity sha512-ix/FxPn0MDjeyJ7i/yoHGFt/EX6LyNbxSEhPPXODPL+KB0VPk86UYfL0lMdy+KCnv+fmvIzySwaK5COwqVbWTQ== + dependencies: + safer-buffer "~2.1.0" + +assertion-error@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/assertion-error/-/assertion-error-1.1.0.tgz#e60b6b0e8f301bd97e5375215bda406c85118c0b" + integrity sha512-jgsaNduz+ndvGyFt3uSuWqvy4lCnIJiovtouQN5JZHOKCS2QuhEdbcQHFhVksz2N2U9hXJo8odG7ETyWlEeuDw== + +at-least-node@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/at-least-node/-/at-least-node-1.0.0.tgz#602cd4b46e844ad4effc92a8011a3c46e0238dc2" + integrity sha512-+q/t7Ekv1EDY2l6Gda6LLiX14rU9TV20Wa3ofeQmwPFZbOMo9DXrLbOjFaaclkXKWidIaopwAObQDqwWtGUjqg== + +axios@^0.21.1: + version "0.21.4" + resolved "https://registry.yarnpkg.com/axios/-/axios-0.21.4.tgz#c67b90dc0568e5c1cf2b0b858c43ba28e2eda575" + integrity sha512-ut5vewkiu8jjGBdqpM44XxjuCjq9LAKeHVmoVfHVzy8eHgxxq8SbAVQNovDA8mVi05kP0Ea/n/UzcSHcTJQfNg== + dependencies: + follow-redirects "^1.14.0" + +balanced-match@^1.0.0: + version "1.0.2" + resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.2.tgz#e83e3a7e3f300b34cb9d87f615fa0cbf357690ee" + integrity sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw== + +base-x@^3.0.2: + version "3.0.9" + resolved "https://registry.yarnpkg.com/base-x/-/base-x-3.0.9.tgz#6349aaabb58526332de9f60995e548a53fe21320" + integrity sha512-H7JU6iBHTal1gp56aKoaa//YUxEaAOUiydvrV/pILqIHXTtqxSkATOnDA2u+jZ/61sD+L/412+7kzXRtWukhpQ== + dependencies: + safe-buffer "^5.0.1" + +base64-js@^1.3.1: + version "1.5.1" + resolved "https://registry.yarnpkg.com/base64-js/-/base64-js-1.5.1.tgz#1b1b440160a5bf7ad40b650f095963481903930a" + integrity sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA== + +bcrypt-pbkdf@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz#a4301d389b6a43f9b67ff3ca11a3f6637e360e9e" + integrity sha512-qeFIXtP4MSoi6NLqO12WfqARWWuCKi2Rn/9hJLEmtB5yTNr9DqFWkJRCf2qShWzPeAMRnOgCrq0sg/KLv5ES9w== + dependencies: + tweetnacl "^0.14.3" + +bech32@1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/bech32/-/bech32-1.1.4.tgz#e38c9f37bf179b8eb16ae3a772b40c356d4832e9" + integrity sha512-s0IrSOzLlbvX7yp4WBfPITzpAU8sqQcpsmwXDiKwrG4r491vwCO/XpejasRNl0piBMe/DvP4Tz0mIS/X1DPJBQ== + +bigint-crypto-utils@^3.0.23: + version "3.3.0" + resolved "https://registry.yarnpkg.com/bigint-crypto-utils/-/bigint-crypto-utils-3.3.0.tgz#72ad00ae91062cf07f2b1def9594006c279c1d77" + integrity sha512-jOTSb+drvEDxEq6OuUybOAv/xxoh3cuYRUIPyu8sSHQNKM303UQ2R1DAo45o1AkcIXw6fzbaFI1+xGGdaXs2lg== + +binary-extensions@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/binary-extensions/-/binary-extensions-2.2.0.tgz#75f502eeaf9ffde42fc98829645be4ea76bd9e2d" + integrity sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA== + +bl@^1.0.0: + version "1.2.3" + resolved "https://registry.yarnpkg.com/bl/-/bl-1.2.3.tgz#1e8dd80142eac80d7158c9dccc047fb620e035e7" + integrity sha512-pvcNpa0UU69UT341rO6AYy4FVAIkUHuZXRIWbq+zHnsVcRzDDjIAhGuuYoi0d//cwIwtt4pkpKycWEfjdV+vww== + dependencies: + readable-stream "^2.3.5" + safe-buffer "^5.1.1" + +bl@^4.0.3: + version "4.1.0" + resolved "https://registry.yarnpkg.com/bl/-/bl-4.1.0.tgz#451535264182bec2fbbc83a62ab98cf11d9f7b3a" + integrity sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w== + dependencies: + buffer "^5.5.0" + inherits "^2.0.4" + readable-stream "^3.4.0" + +blakejs@^1.1.0: + version "1.2.1" + resolved "https://registry.yarnpkg.com/blakejs/-/blakejs-1.2.1.tgz#5057e4206eadb4a97f7c0b6e197a505042fc3814" + integrity sha512-QXUSXI3QVc/gJME0dBpXrag1kbzOqCjCX8/b54ntNyW6sjtoqxqRk3LTmXzaJoh71zMsDCjM+47jS7XiwN/+fQ== + +bn-str-256@^1.9.1: + version "1.9.1" + resolved "https://registry.yarnpkg.com/bn-str-256/-/bn-str-256-1.9.1.tgz#898cebee70a3edc3968f97b4cebbc4771025aa82" + integrity sha512-u3muv3WO5sYv9nUQsPnDGLg731yNt/MOlKPK5pmBVqClcl7tY97tyfKxw8ed44HVrpi+7dkgJgQpbXP47a3GoQ== + dependencies: + decimal.js-light "^2.5.0" + lodash "^4.17.11" + +bn.js@^4.11.0, bn.js@^4.11.8, bn.js@^4.11.9: + version "4.12.0" + resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-4.12.0.tgz#775b3f278efbb9718eec7361f483fb36fbbfea88" + integrity sha512-c98Bf3tPniI+scsdk237ku1Dc3ujXQTSgyiPUDEOe7tRkhrqridvh8klBv0HCEso1OLOYcHuCv/cS6DNxKH+ZA== + +bn.js@^5.2.0, bn.js@^5.2.1: + version "5.2.1" + resolved "https://registry.yarnpkg.com/bn.js/-/bn.js-5.2.1.tgz#0bc527a6a0d18d0aa8d5b0538ce4a77dccfa7b70" + integrity sha512-eXRvHzWyYPBuB4NBy0cmYQjGitUrtqwbvlzP3G6VFnNRbsZQIxQ10PbKKHt8gZ/HW/D/747aDl+QkDqg3KQLMQ== + +brace-expansion@^1.1.7: + version "1.1.11" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd" + integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA== + dependencies: + balanced-match "^1.0.0" + concat-map "0.0.1" + +brace-expansion@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-2.0.1.tgz#1edc459e0f0c548486ecf9fc99f2221364b9a0ae" + integrity sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA== + dependencies: + balanced-match "^1.0.0" + +braces@^3.0.2, braces@~3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/braces/-/braces-3.0.2.tgz#3454e1a462ee8d599e236df336cd9ea4f8afe107" + integrity sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A== + dependencies: + fill-range "^7.0.1" + +brorand@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/brorand/-/brorand-1.1.0.tgz#12c25efe40a45e3c323eb8675a0a0ce57b22371f" + integrity sha512-cKV8tMCEpQs4hK/ik71d6LrPOnpkpGBR0wzxqr68g2m/LB2GxVYQroAjMJZRVM1Y4BCjCKc3vAamxSzOY2RP+w== + +browser-level@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/browser-level/-/browser-level-1.0.1.tgz#36e8c3183d0fe1c405239792faaab5f315871011" + integrity sha512-XECYKJ+Dbzw0lbydyQuJzwNXtOpbMSq737qxJN11sIRTErOMShvDpbzTlgju7orJKvx4epULolZAuJGLzCmWRQ== + dependencies: + abstract-level "^1.0.2" + catering "^2.1.1" + module-error "^1.0.2" + run-parallel-limit "^1.1.0" + +browser-stdout@1.3.1: + version "1.3.1" + resolved "https://registry.yarnpkg.com/browser-stdout/-/browser-stdout-1.3.1.tgz#baa559ee14ced73452229bad7326467c61fabd60" + integrity sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw== + +browserify-aes@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/browserify-aes/-/browserify-aes-1.2.0.tgz#326734642f403dabc3003209853bb70ad428ef48" + integrity sha512-+7CHXqGuspUn/Sl5aO7Ea0xWGAtETPXNSAjHo48JfLdPWcMng33Xe4znFvQweqc/uzk5zSOI3H52CYnjCfb5hA== + dependencies: + buffer-xor "^1.0.3" + cipher-base "^1.0.0" + create-hash "^1.1.0" + evp_bytestokey "^1.0.3" + inherits "^2.0.1" + safe-buffer "^5.0.1" + +bs58@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/bs58/-/bs58-4.0.1.tgz#be161e76c354f6f788ae4071f63f34e8c4f0a42a" + integrity sha512-Ok3Wdf5vOIlBrgCvTq96gBkJw+JUEzdBgyaza5HLtPm7yTHkjRy8+JzNyHF7BHa0bNWOQIp3m5YF0nnFcOIKLw== + dependencies: + base-x "^3.0.2" + +bs58check@^2.1.2: + version "2.1.2" + resolved "https://registry.yarnpkg.com/bs58check/-/bs58check-2.1.2.tgz#53b018291228d82a5aa08e7d796fdafda54aebfc" + integrity sha512-0TS1jicxdU09dwJMNZtVAfzPi6Q6QeN0pM1Fkzrjn+XYHvzMKPU3pHVpva+769iNVSfIYWf7LJ6WR+BuuMf8cA== + dependencies: + bs58 "^4.0.0" + create-hash "^1.1.0" + safe-buffer "^5.1.2" + +buffer-alloc-unsafe@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/buffer-alloc-unsafe/-/buffer-alloc-unsafe-1.1.0.tgz#bd7dc26ae2972d0eda253be061dba992349c19f0" + integrity sha512-TEM2iMIEQdJ2yjPJoSIsldnleVaAk1oW3DBVUykyOLsEsFmEc9kn+SFFPz+gl54KQNxlDnAwCXosOS9Okx2xAg== + +buffer-alloc@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/buffer-alloc/-/buffer-alloc-1.2.0.tgz#890dd90d923a873e08e10e5fd51a57e5b7cce0ec" + integrity sha512-CFsHQgjtW1UChdXgbyJGtnm+O/uLQeZdtbDo8mfUgYXCHSM1wgrVxXm6bSyrUuErEb+4sYVGCzASBRot7zyrow== + dependencies: + buffer-alloc-unsafe "^1.1.0" + buffer-fill "^1.0.0" + +buffer-fill@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/buffer-fill/-/buffer-fill-1.0.0.tgz#f8f78b76789888ef39f205cd637f68e702122b2c" + integrity sha512-T7zexNBwiiaCOGDg9xNX9PBmjrubblRkENuptryuI64URkXDFum9il/JGL8Lm8wYfAXpredVXXZz7eMHilimiQ== + +buffer-from@^1.0.0: + version "1.1.2" + resolved "https://registry.yarnpkg.com/buffer-from/-/buffer-from-1.1.2.tgz#2b146a6fd72e80b4f55d255f35ed59a3a9a41bd5" + integrity sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ== + +buffer-xor@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/buffer-xor/-/buffer-xor-1.0.3.tgz#26e61ed1422fb70dd42e6e36729ed51d855fe8d9" + integrity sha512-571s0T7nZWK6vB67HI5dyUF7wXiNcfaPPPTl6zYCNApANjIvYJTg7hlud/+cJpdAhS7dVzqMLmfhfHR3rAcOjQ== + +buffer@^5.5.0: + version "5.7.1" + resolved "https://registry.yarnpkg.com/buffer/-/buffer-5.7.1.tgz#ba62e7c13133053582197160851a8f648e99eed0" + integrity sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ== + dependencies: + base64-js "^1.3.1" + ieee754 "^1.1.13" + +buffer@^6.0.3: + version "6.0.3" + resolved "https://registry.yarnpkg.com/buffer/-/buffer-6.0.3.tgz#2ace578459cc8fbe2a70aaa8f52ee63b6a74c6c6" + integrity sha512-FTiCpNxtwiZZHEZbcbTIcZjERVICn9yq/pDFkTl95/AxzD1naBctN7YO68riM/gLSDY7sdrMby8hofADYuuqOA== + dependencies: + base64-js "^1.3.1" + ieee754 "^1.2.1" + +buildcheck@~0.0.6: + version "0.0.6" + resolved "https://registry.yarnpkg.com/buildcheck/-/buildcheck-0.0.6.tgz#89aa6e417cfd1e2196e3f8fe915eb709d2fe4238" + integrity sha512-8f9ZJCUXyT1M35Jx7MkBgmBMo3oHTTBIPLiY9xyL0pl3T5RwcPEY8cUHr5LBNfu/fk6c2T4DJZuVM/8ZZT2D2A== + +busboy@^1.6.0: + version "1.6.0" + resolved "https://registry.yarnpkg.com/busboy/-/busboy-1.6.0.tgz#966ea36a9502e43cdb9146962523b92f531f6893" + integrity sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA== + dependencies: + streamsearch "^1.1.0" + +bytes@3.1.2: + version "3.1.2" + resolved "https://registry.yarnpkg.com/bytes/-/bytes-3.1.2.tgz#8b0beeb98605adf1b128fa4386403c009e0221a5" + integrity sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg== + +camelcase@^6.0.0: + version "6.3.0" + resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-6.3.0.tgz#5685b95eb209ac9c0c177467778c9c84df58ba9a" + integrity sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA== + +case@^1.6.3: + version "1.6.3" + resolved "https://registry.yarnpkg.com/case/-/case-1.6.3.tgz#0a4386e3e9825351ca2e6216c60467ff5f1ea1c9" + integrity sha512-mzDSXIPaFwVDvZAHqZ9VlbyF4yyXRuX6IvB06WvPYkqJVO24kX1PPhv9bfpKNFZyxYFmmgo03HUiD8iklmJYRQ== + +catering@^2.1.0, catering@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/catering/-/catering-2.1.1.tgz#66acba06ed5ee28d5286133982a927de9a04b510" + integrity sha512-K7Qy8O9p76sL3/3m7/zLKbRkyOlSZAgzEaLhyj2mXS8PsCud2Eo4hAb8aLtZqHh0QGqLcb9dlJSu6lHRVENm1w== + +chai@^4.3.6: + version "4.3.8" + resolved "https://registry.yarnpkg.com/chai/-/chai-4.3.8.tgz#40c59718ad6928da6629c70496fe990b2bb5b17c" + integrity sha512-vX4YvVVtxlfSZ2VecZgFUTU5qPCYsobVI2O9FmwEXBhDigYGQA6jRXCycIs1yJnnWbZ6/+a2zNIF5DfVCcJBFQ== + dependencies: + assertion-error "^1.1.0" + check-error "^1.0.2" + deep-eql "^4.1.2" + get-func-name "^2.0.0" + loupe "^2.3.1" + pathval "^1.1.1" + type-detect "^4.0.5" + +chalk@4.1.2, chalk@^4.1.0: + version "4.1.2" + resolved "https://registry.yarnpkg.com/chalk/-/chalk-4.1.2.tgz#aac4e2b7734a740867aeb16bf02aad556a1e7a01" + integrity sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA== + dependencies: + ansi-styles "^4.1.0" + supports-color "^7.1.0" + +chalk@^2.4.1, chalk@^2.4.2: + version "2.4.2" + resolved "https://registry.yarnpkg.com/chalk/-/chalk-2.4.2.tgz#cd42541677a54333cf541a49108c1432b44c9424" + integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ== + dependencies: + ansi-styles "^3.2.1" + escape-string-regexp "^1.0.5" + supports-color "^5.3.0" + +check-error@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/check-error/-/check-error-1.0.2.tgz#574d312edd88bb5dd8912e9286dd6c0aed4aac82" + integrity sha512-BrgHpW9NURQgzoNyjfq0Wu6VFO6D7IZEmJNdtgNqpzGG8RuNFHt2jQxWlAs4HMe119chBnv+34syEZtc6IhLtA== + +chokidar@3.5.3, chokidar@^3.4.0: + version "3.5.3" + resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-3.5.3.tgz#1cf37c8707b932bd1af1ae22c0432e2acd1903bd" + integrity sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw== + dependencies: + anymatch "~3.1.2" + braces "~3.0.2" + glob-parent "~5.1.2" + is-binary-path "~2.1.0" + is-glob "~4.0.1" + normalize-path "~3.0.0" + readdirp "~3.6.0" + optionalDependencies: + fsevents "~2.3.2" + +chownr@^1.0.1, chownr@^1.1.1: + version "1.1.4" + resolved "https://registry.yarnpkg.com/chownr/-/chownr-1.1.4.tgz#6fc9d7b42d32a583596337666e7d08084da2cc6b" + integrity sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg== + +ci-info@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/ci-info/-/ci-info-2.0.0.tgz#67a9e964be31a51e15e5010d58e6f12834002f46" + integrity sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ== + +cipher-base@^1.0.0, cipher-base@^1.0.1, cipher-base@^1.0.3: + version "1.0.4" + resolved "https://registry.yarnpkg.com/cipher-base/-/cipher-base-1.0.4.tgz#8760e4ecc272f4c363532f926d874aae2c1397de" + integrity sha512-Kkht5ye6ZGmwv40uUDZztayT2ThLQGfnj/T71N/XzeZeo3nf8foyW7zGTsPYkEya3m5f3cAypH+qe7YOrM1U2Q== + dependencies: + inherits "^2.0.1" + safe-buffer "^5.0.1" + +classic-level@^1.2.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/classic-level/-/classic-level-1.3.0.tgz#5e36680e01dc6b271775c093f2150844c5edd5c8" + integrity sha512-iwFAJQYtqRTRM0F6L8h4JCt00ZSGdOyqh7yVrhhjrOpFhmBjNlRUey64MCiyo6UmQHMJ+No3c81nujPv+n9yrg== + dependencies: + abstract-level "^1.0.2" + catering "^2.1.0" + module-error "^1.0.1" + napi-macros "^2.2.2" + node-gyp-build "^4.3.0" + +clean-stack@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/clean-stack/-/clean-stack-2.2.0.tgz#ee8472dbb129e727b31e8a10a427dee9dfe4008b" + integrity sha512-4diC9HaTE+KRAMWhDhrGOECgWZxoevMc5TlkObMqNSsVU62PYzXZ/SMTjzyGAFF1YusgxGcSWTEXBhp0CPwQ1A== + +cliui@^7.0.2: + version "7.0.4" + resolved "https://registry.yarnpkg.com/cliui/-/cliui-7.0.4.tgz#a0265ee655476fc807aea9df3df8df7783808b4f" + integrity sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ== + dependencies: + string-width "^4.2.0" + strip-ansi "^6.0.0" + wrap-ansi "^7.0.0" + +code-block-writer@^12.0.0: + version "12.0.0" + resolved "https://registry.yarnpkg.com/code-block-writer/-/code-block-writer-12.0.0.tgz#4dd58946eb4234105aff7f0035977b2afdc2a770" + integrity sha512-q4dMFMlXtKR3XNBHyMHt/3pwYNA69EDk00lloMOaaUMKPUXBw6lpXtbu3MMVG6/uOihGnRDOlkyqsONEUj60+w== + +color-convert@^1.9.0: + version "1.9.3" + resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-1.9.3.tgz#bb71850690e1f136567de629d2d5471deda4c1e8" + integrity sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg== + dependencies: + color-name "1.1.3" + +color-convert@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/color-convert/-/color-convert-2.0.1.tgz#72d3a68d598c9bdb3af2ad1e84f21d896abd4de3" + integrity sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ== + dependencies: + color-name "~1.1.4" + +color-name@1.1.3: + version "1.1.3" + resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.3.tgz#a7d0558bd89c42f795dd42328f740831ca53bc25" + integrity sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw== + +color-name@~1.1.4: + version "1.1.4" + resolved "https://registry.yarnpkg.com/color-name/-/color-name-1.1.4.tgz#c2a09a87acbde69543de6f63fa3995c826c536a2" + integrity sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA== + +command-exists@^1.2.8: + version "1.2.9" + resolved "https://registry.yarnpkg.com/command-exists/-/command-exists-1.2.9.tgz#c50725af3808c8ab0260fd60b01fbfa25b954f69" + integrity sha512-LTQ/SGc+s0Xc0Fu5WaKnR0YiygZkm9eKFvyS+fRsU7/ZWFF8ykFM6Pc9aCVf1+xasOOZpO3BAVgVrKvsqKHV7w== + +command-line-args@^5.1.1: + version "5.2.1" + resolved "https://registry.yarnpkg.com/command-line-args/-/command-line-args-5.2.1.tgz#c44c32e437a57d7c51157696893c5909e9cec42e" + integrity sha512-H4UfQhZyakIjC74I9d34fGYDwk3XpSr17QhEd0Q3I9Xq1CETHo4Hcuo87WyWHpAF1aSLjLRf5lD9ZGX2qStUvg== + dependencies: + array-back "^3.1.0" + find-replace "^3.0.0" + lodash.camelcase "^4.3.0" + typical "^4.0.0" + +command-line-usage@^6.1.0: + version "6.1.3" + resolved "https://registry.yarnpkg.com/command-line-usage/-/command-line-usage-6.1.3.tgz#428fa5acde6a838779dfa30e44686f4b6761d957" + integrity sha512-sH5ZSPr+7UStsloltmDh7Ce5fb8XPlHyoPzTpyyMuYCtervL65+ubVZ6Q61cFtFl62UyJlc8/JwERRbAFPUqgw== + dependencies: + array-back "^4.0.2" + chalk "^2.4.2" + table-layout "^1.0.2" + typical "^5.2.0" + +commander@3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/commander/-/commander-3.0.2.tgz#6837c3fb677ad9933d1cfba42dd14d5117d6b39e" + integrity sha512-Gar0ASD4BDyKC4hl4DwHqDrmvjoxWKZigVnAbn5H1owvm4CxCPdb0HQDehwNYMJpla5+M2tPmPARzhtYuwpHow== + +commander@^2.19.0: + version "2.20.3" + resolved "https://registry.yarnpkg.com/commander/-/commander-2.20.3.tgz#fd485e84c03eb4881c20722ba48035e8531aeb33" + integrity sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ== + +commander@^9.4.1: + version "9.5.0" + resolved "https://registry.yarnpkg.com/commander/-/commander-9.5.0.tgz#bc08d1eb5cedf7ccb797a96199d41c7bc3e60d30" + integrity sha512-KRs7WVDKg86PWiuAqhDrAQnTXZKraVcCc6vFdL14qrZ/DcWwuRo7VoiYXalXO7S5GKpqYiVEwCbgFDfxNHKJBQ== + +concat-map@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" + integrity sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg== + +concat-stream@~1.6.2: + version "1.6.2" + resolved "https://registry.yarnpkg.com/concat-stream/-/concat-stream-1.6.2.tgz#904bdf194cd3122fc675c77fc4ac3d4ff0fd1a34" + integrity sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw== + dependencies: + buffer-from "^1.0.0" + inherits "^2.0.3" + readable-stream "^2.2.2" + typedarray "^0.0.6" + +cookie@^0.4.1: + version "0.4.2" + resolved "https://registry.yarnpkg.com/cookie/-/cookie-0.4.2.tgz#0e41f24de5ecf317947c82fc789e06a884824432" + integrity sha512-aSWTXFzaKWkvHO1Ny/s+ePFpvKsPnjc551iI41v3ny/ow6tBG5Vd+FuqGNhh1LxOmVzOlGUriIlOaokOvhaStA== + +core-util-is@~1.0.0: + version "1.0.3" + resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.3.tgz#a6042d3634c2b27e9328f837b965fac83808db85" + integrity sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ== + +cpu-features@~0.0.8: + version "0.0.9" + resolved "https://registry.yarnpkg.com/cpu-features/-/cpu-features-0.0.9.tgz#5226b92f0f1c63122b0a3eb84cb8335a4de499fc" + integrity sha512-AKjgn2rP2yJyfbepsmLfiYcmtNn/2eUvocUyM/09yB0YDiz39HteK/5/T4Onf0pmdYDMgkBoGvRLvEguzyL7wQ== + dependencies: + buildcheck "~0.0.6" + nan "^2.17.0" + +crc-32@^1.2.0: + version "1.2.2" + resolved "https://registry.yarnpkg.com/crc-32/-/crc-32-1.2.2.tgz#3cad35a934b8bf71f25ca524b6da51fb7eace2ff" + integrity sha512-ROmzCKrTnOwybPcJApAA6WBWij23HVfGVNKqqrZpuyZOHqK2CwHSvpGuyt/UNNvaIjEd8X5IFGp4Mh+Ie1IHJQ== + +create-hash@^1.1.0, create-hash@^1.1.2, create-hash@^1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/create-hash/-/create-hash-1.2.0.tgz#889078af11a63756bcfb59bd221996be3a9ef196" + integrity sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg== + dependencies: + cipher-base "^1.0.1" + inherits "^2.0.1" + md5.js "^1.3.4" + ripemd160 "^2.0.1" + sha.js "^2.4.0" + +create-hmac@^1.1.4, create-hmac@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/create-hmac/-/create-hmac-1.1.7.tgz#69170c78b3ab957147b2b8b04572e47ead2243ff" + integrity sha512-MJG9liiZ+ogc4TzUwuvbER1JRdgvUFSB5+VR/g5h82fGaIRWMWddtKBHi7/sVhfjQZ6SehlyhvQYrcYkaUIpLg== + dependencies: + cipher-base "^1.0.3" + create-hash "^1.1.0" + inherits "^2.0.1" + ripemd160 "^2.0.0" + safe-buffer "^5.0.1" + sha.js "^2.4.8" + +create-require@^1.1.0: + version "1.1.1" + resolved "https://registry.yarnpkg.com/create-require/-/create-require-1.1.1.tgz#c1d7e8f1e5f6cfc9ff65f9cd352d37348756c333" + integrity sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ== + +debug@4, debug@4.3.4, debug@^4.1.1, debug@^4.3.1, debug@^4.3.3: + version "4.3.4" + resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.4.tgz#1319f6579357f2338d3337d2cdd4914bb5dcc865" + integrity sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ== + dependencies: + ms "2.1.2" + +debug@^3.2.6: + version "3.2.7" + resolved "https://registry.yarnpkg.com/debug/-/debug-3.2.7.tgz#72580b7e9145fb39b6676f9c5e5fb100b934179a" + integrity sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ== + dependencies: + ms "^2.1.1" + +decamelize@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-4.0.0.tgz#aa472d7bf660eb15f3494efd531cab7f2a709837" + integrity sha512-9iE1PgSik9HeIIw2JO94IidnE3eBoQrFJ3w7sFuzSX4DpmZ3v5sZpUiV5Swcf6mQEF+Y0ru8Neo+p+nyh2J+hQ== + +decimal.js-light@^2.5.0: + version "2.5.1" + resolved "https://registry.yarnpkg.com/decimal.js-light/-/decimal.js-light-2.5.1.tgz#134fd32508f19e208f4fb2f8dac0d2626a867934" + integrity sha512-qIMFpTMZmny+MMIitAB6D7iVPEorVw6YQRWkvarTkT4tBeSLLiHzcwj6q0MmYSFCiVpiqPJTJEYIrpcPzVEIvg== + +deep-eql@^4.1.2: + version "4.1.3" + resolved "https://registry.yarnpkg.com/deep-eql/-/deep-eql-4.1.3.tgz#7c7775513092f7df98d8df9996dd085eb668cc6d" + integrity sha512-WaEtAOpRA1MQ0eohqZjpGD8zdI0Ovsm8mmFhaDN8dvDZzyoUMcYDnf5Y6iu7HTXxf8JDS23qWa4a+hKCDyOPzw== + dependencies: + type-detect "^4.0.0" + +deep-extend@~0.6.0: + version "0.6.0" + resolved "https://registry.yarnpkg.com/deep-extend/-/deep-extend-0.6.0.tgz#c4fa7c95404a17a9c3e8ca7e1537312b736330ac" + integrity sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA== + +depd@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/depd/-/depd-2.0.0.tgz#b696163cc757560d09cf22cc8fad1571b79e76df" + integrity sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw== + +diff@5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/diff/-/diff-5.0.0.tgz#7ed6ad76d859d030787ec35855f5b1daf31d852b" + integrity sha512-/VTCrvm5Z0JGty/BWHljh+BAiw3IK+2j87NGMu8Nwc/f48WoDAC395uomO9ZD117ZOBaHmkX1oyLvkVM/aIT3w== + +diff@^4.0.1: + version "4.0.2" + resolved "https://registry.yarnpkg.com/diff/-/diff-4.0.2.tgz#60f3aecb89d5fae520c11aa19efc2bb982aade7d" + integrity sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A== + +docker-modem@^1.0.8: + version "1.0.9" + resolved "https://registry.yarnpkg.com/docker-modem/-/docker-modem-1.0.9.tgz#a1f13e50e6afb6cf3431b2d5e7aac589db6aaba8" + integrity sha512-lVjqCSCIAUDZPAZIeyM125HXfNvOmYYInciphNrLrylUtKyW66meAjSPXWchKVzoIYZx69TPnAepVSSkeawoIw== + dependencies: + JSONStream "1.3.2" + debug "^3.2.6" + readable-stream "~1.0.26-4" + split-ca "^1.0.0" + +docker-modem@^3.0.0: + version "3.0.8" + resolved "https://registry.yarnpkg.com/docker-modem/-/docker-modem-3.0.8.tgz#ef62c8bdff6e8a7d12f0160988c295ea8705e77a" + integrity sha512-f0ReSURdM3pcKPNS30mxOHSbaFLcknGmQjwSfmbcdOw1XWKXVhukM3NJHhr7NpY9BIyyWQb0EBo3KQvvuU5egQ== + dependencies: + debug "^4.1.1" + readable-stream "^3.5.0" + split-ca "^1.0.1" + ssh2 "^1.11.0" + +dockerode@^2.5.8: + version "2.5.8" + resolved "https://registry.yarnpkg.com/dockerode/-/dockerode-2.5.8.tgz#1b661e36e1e4f860e25f56e0deabe9f87f1d0acc" + integrity sha512-+7iOUYBeDTScmOmQqpUYQaE7F4vvIt6+gIZNHWhqAQEI887tiPFB9OvXI/HzQYqfUNvukMK+9myLW63oTJPZpw== + dependencies: + concat-stream "~1.6.2" + docker-modem "^1.0.8" + tar-fs "~1.16.3" + +dockerode@^3.3.4: + version "3.3.5" + resolved "https://registry.yarnpkg.com/dockerode/-/dockerode-3.3.5.tgz#7ae3f40f2bec53ae5e9a741ce655fff459745629" + integrity sha512-/0YNa3ZDNeLr/tSckmD69+Gq+qVNhvKfAHNeZJBnp7EOP6RGKV8ORrJHkUn20So5wU+xxT7+1n5u8PjHbfjbSA== + dependencies: + "@balena/dockerignore" "^1.0.2" + docker-modem "^3.0.0" + tar-fs "~2.0.1" + +elliptic@6.5.4, elliptic@^6.5.2, elliptic@^6.5.4: + version "6.5.4" + resolved "https://registry.yarnpkg.com/elliptic/-/elliptic-6.5.4.tgz#da37cebd31e79a1367e941b592ed1fbebd58abbb" + integrity sha512-iLhC6ULemrljPZb+QutR5TQGB+pdW6KGD5RSegS+8sorOZT+rdQFbsQFJgvN3eRqNALqJer4oQ16YvJHlU8hzQ== + dependencies: + bn.js "^4.11.9" + brorand "^1.1.0" + hash.js "^1.0.0" + hmac-drbg "^1.0.1" + inherits "^2.0.4" + minimalistic-assert "^1.0.1" + minimalistic-crypto-utils "^1.0.1" + +emoji-regex@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-8.0.0.tgz#e818fd69ce5ccfcb404594f842963bf53164cc37" + integrity sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A== + +end-of-stream@^1.0.0, end-of-stream@^1.1.0, end-of-stream@^1.4.1: + version "1.4.4" + resolved "https://registry.yarnpkg.com/end-of-stream/-/end-of-stream-1.4.4.tgz#5ae64a5f45057baf3626ec14da0ca5e4b2431eb0" + integrity sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q== + dependencies: + once "^1.4.0" + +enquirer@^2.3.0: + version "2.4.1" + resolved "https://registry.yarnpkg.com/enquirer/-/enquirer-2.4.1.tgz#93334b3fbd74fc7097b224ab4a8fb7e40bf4ae56" + integrity sha512-rRqJg/6gd538VHvR3PSrdRBb/1Vy2YfzHqzvbhGIQpDRKIa4FgV/54b5Q1xYSxOOwKvjXweS26E0Q+nAMwp2pQ== + dependencies: + ansi-colors "^4.1.1" + strip-ansi "^6.0.1" + +env-paths@^2.2.0: + version "2.2.1" + resolved "https://registry.yarnpkg.com/env-paths/-/env-paths-2.2.1.tgz#420399d416ce1fbe9bc0a07c62fa68d67fd0f8f2" + integrity sha512-+h1lkLKhZMTYjog1VEpJNG7NZJWcuc2DDk/qsqSTRRCOXiLjeQ1d1/udrUGhqMxUgAlwKNZ0cf2uqan5GLuS2A== + +escalade@^3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/escalade/-/escalade-3.1.1.tgz#d8cfdc7000965c5a0174b4a82eaa5c0552742e40" + integrity sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw== + +escape-string-regexp@4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz#14ba83a5d373e3d311e5afca29cf5bfad965bf34" + integrity sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA== + +escape-string-regexp@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4" + integrity sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg== + +ethereum-cryptography@0.1.3, ethereum-cryptography@^0.1.3: + version "0.1.3" + resolved "https://registry.yarnpkg.com/ethereum-cryptography/-/ethereum-cryptography-0.1.3.tgz#8d6143cfc3d74bf79bbd8edecdf29e4ae20dd191" + integrity sha512-w8/4x1SGGzc+tO97TASLja6SLd3fRIK2tLVcV2Gx4IB21hE19atll5Cq9o3d0ZmAYC/8aw0ipieTSiekAea4SQ== + dependencies: + "@types/pbkdf2" "^3.0.0" + "@types/secp256k1" "^4.0.1" + blakejs "^1.1.0" + browserify-aes "^1.2.0" + bs58check "^2.1.2" + create-hash "^1.2.0" + create-hmac "^1.1.7" + hash.js "^1.1.7" + keccak "^3.0.0" + pbkdf2 "^3.0.17" + randombytes "^2.1.0" + safe-buffer "^5.1.2" + scrypt-js "^3.0.0" + secp256k1 "^4.0.1" + setimmediate "^1.0.5" + +ethereum-cryptography@^1.0.3: + version "1.2.0" + resolved "https://registry.yarnpkg.com/ethereum-cryptography/-/ethereum-cryptography-1.2.0.tgz#5ccfa183e85fdaf9f9b299a79430c044268c9b3a" + integrity sha512-6yFQC9b5ug6/17CQpCyE3k9eKBMdhyVjzUy1WkiuY/E4vj/SXDBbCw8QEIaXqf0Mf2SnY6RmpDcwlUmBSS0EJw== + dependencies: + "@noble/hashes" "1.2.0" + "@noble/secp256k1" "1.7.1" + "@scure/bip32" "1.1.5" + "@scure/bip39" "1.1.1" + +ethereumjs-abi@^0.6.8: + version "0.6.8" + resolved "https://registry.yarnpkg.com/ethereumjs-abi/-/ethereumjs-abi-0.6.8.tgz#71bc152db099f70e62f108b7cdfca1b362c6fcae" + integrity sha512-Tx0r/iXI6r+lRsdvkFDlut0N08jWMnKRZ6Gkq+Nmw75lZe4e6o3EkSnkaBP5NF6+m5PTGAr9JP43N3LyeoglsA== + dependencies: + bn.js "^4.11.8" + ethereumjs-util "^6.0.0" + +ethereumjs-util@^6.0.0, ethereumjs-util@^6.2.1: + version "6.2.1" + resolved "https://registry.yarnpkg.com/ethereumjs-util/-/ethereumjs-util-6.2.1.tgz#fcb4e4dd5ceacb9d2305426ab1a5cd93e3163b69" + integrity sha512-W2Ktez4L01Vexijrm5EB6w7dg4n/TgpoYU4avuT5T3Vmnw/eCRtiBrJfQYS/DCSvDIOLn2k57GcHdeBcgVxAqw== + dependencies: + "@types/bn.js" "^4.11.3" + bn.js "^4.11.0" + create-hash "^1.1.2" + elliptic "^6.5.2" + ethereum-cryptography "^0.1.3" + ethjs-util "0.1.6" + rlp "^2.2.3" + +ethers@^5.7.0, ethers@^5.7.1: + version "5.7.2" + resolved "https://registry.yarnpkg.com/ethers/-/ethers-5.7.2.tgz#3a7deeabbb8c030d4126b24f84e525466145872e" + integrity sha512-wswUsmWo1aOK8rR7DIKiWSw9DbLWe6x98Jrn8wcTflTVvaXhAMaB5zGAXy0GYQEQp9iO1iSHWVyARQm11zUtyg== + dependencies: + "@ethersproject/abi" "5.7.0" + "@ethersproject/abstract-provider" "5.7.0" + "@ethersproject/abstract-signer" "5.7.0" + "@ethersproject/address" "5.7.0" + "@ethersproject/base64" "5.7.0" + "@ethersproject/basex" "5.7.0" + "@ethersproject/bignumber" "5.7.0" + "@ethersproject/bytes" "5.7.0" + "@ethersproject/constants" "5.7.0" + "@ethersproject/contracts" "5.7.0" + "@ethersproject/hash" "5.7.0" + "@ethersproject/hdnode" "5.7.0" + "@ethersproject/json-wallets" "5.7.0" + "@ethersproject/keccak256" "5.7.0" + "@ethersproject/logger" "5.7.0" + "@ethersproject/networks" "5.7.1" + "@ethersproject/pbkdf2" "5.7.0" + "@ethersproject/properties" "5.7.0" + "@ethersproject/providers" "5.7.2" + "@ethersproject/random" "5.7.0" + "@ethersproject/rlp" "5.7.0" + "@ethersproject/sha2" "5.7.0" + "@ethersproject/signing-key" "5.7.0" + "@ethersproject/solidity" "5.7.0" + "@ethersproject/strings" "5.7.0" + "@ethersproject/transactions" "5.7.0" + "@ethersproject/units" "5.7.0" + "@ethersproject/wallet" "5.7.0" + "@ethersproject/web" "5.7.1" + "@ethersproject/wordlists" "5.7.0" + +ethjs-util@0.1.6, ethjs-util@^0.1.6: + version "0.1.6" + resolved "https://registry.yarnpkg.com/ethjs-util/-/ethjs-util-0.1.6.tgz#f308b62f185f9fe6237132fb2a9818866a5cd536" + integrity sha512-CUnVOQq7gSpDHZVVrQW8ExxUETWrnrvXYvYz55wOU8Uj4VCgw56XC2B/fVqQN+f7gmrnRHSLVnFAwsCuNwji8w== + dependencies: + is-hex-prefixed "1.0.0" + strip-hex-prefix "1.0.0" + +evp_bytestokey@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/evp_bytestokey/-/evp_bytestokey-1.0.3.tgz#7fcbdb198dc71959432efe13842684e0525acb02" + integrity sha512-/f2Go4TognH/KvCISP7OUsHn85hT9nUkxxA9BEWxFn+Oj9o8ZNLm/40hdlgSLyuOimsrTKLUMEorQexp/aPQeA== + dependencies: + md5.js "^1.3.4" + safe-buffer "^5.1.1" + +fast-glob@^3.2.12: + version "3.3.1" + resolved "https://registry.yarnpkg.com/fast-glob/-/fast-glob-3.3.1.tgz#784b4e897340f3dbbef17413b3f11acf03c874c4" + integrity sha512-kNFPyjhh5cKjrUltxs+wFx+ZkbRaxxmZ+X0ZU31SOsxCEtP9VPgtq2teZw1DebupL5GmDaNQ6yKMMVcM41iqDg== + dependencies: + "@nodelib/fs.stat" "^2.0.2" + "@nodelib/fs.walk" "^1.2.3" + glob-parent "^5.1.2" + merge2 "^1.3.0" + micromatch "^4.0.4" + +fastq@^1.6.0: + version "1.15.0" + resolved "https://registry.yarnpkg.com/fastq/-/fastq-1.15.0.tgz#d04d07c6a2a68fe4599fea8d2e103a937fae6b3a" + integrity sha512-wBrocU2LCXXa+lWBt8RoIRD89Fi8OdABODa/kEnyeyjS5aZO5/GNvI5sEINADqP/h8M29UHTHUb53sUu5Ihqdw== + dependencies: + reusify "^1.0.4" + +fill-range@^7.0.1: + version "7.0.1" + resolved "https://registry.yarnpkg.com/fill-range/-/fill-range-7.0.1.tgz#1919a6a7c75fe38b2c7c77e5198535da9acdda40" + integrity sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ== + dependencies: + to-regex-range "^5.0.1" + +find-replace@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/find-replace/-/find-replace-3.0.0.tgz#3e7e23d3b05167a76f770c9fbd5258b0def68c38" + integrity sha512-6Tb2myMioCAgv5kfvP5/PkZZ/ntTpVK39fHY7WkWBgvbeE+VHd/tZuZ4mrC+bxh4cfOZeYKVPaJIZtZXV7GNCQ== + dependencies: + array-back "^3.0.1" + +find-up@5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-5.0.0.tgz#4c92819ecb7083561e4f4a240a86be5198f536fc" + integrity sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng== + dependencies: + locate-path "^6.0.0" + path-exists "^4.0.0" + +find-up@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-2.1.0.tgz#45d1b7e506c717ddd482775a2b77920a3c0c57a7" + integrity sha512-NWzkk0jSJtTt08+FBFMvXoeZnOJD+jTtsRmBYbAIzJdX6l7dLgR7CTubCM5/eDdPUBvLCeVasP1brfVR/9/EZQ== + dependencies: + locate-path "^2.0.0" + +flat@^5.0.2: + version "5.0.2" + resolved "https://registry.yarnpkg.com/flat/-/flat-5.0.2.tgz#8ca6fe332069ffa9d324c327198c598259ceb241" + integrity sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ== + +follow-redirects@^1.12.1, follow-redirects@^1.14.0: + version "1.15.2" + resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.15.2.tgz#b460864144ba63f2681096f274c4e57026da2c13" + integrity sha512-VQLG33o04KaQ8uYi2tVNbdrWp1QWxNNea+nmIB4EVM28v0hmP17z7aG1+wAkNzVq4KeXTq3221ye5qTJP91JwA== + +fp-ts@1.19.3: + version "1.19.3" + resolved "https://registry.yarnpkg.com/fp-ts/-/fp-ts-1.19.3.tgz#261a60d1088fbff01f91256f91d21d0caaaaa96f" + integrity sha512-H5KQDspykdHuztLTg+ajGN0Z2qUjcEf3Ybxc6hLt0k7/zPkn29XnKnxlBPyW2XIddWrGaJBzBl4VLYOtk39yZg== + +fp-ts@^1.0.0: + version "1.19.5" + resolved "https://registry.yarnpkg.com/fp-ts/-/fp-ts-1.19.5.tgz#3da865e585dfa1fdfd51785417357ac50afc520a" + integrity sha512-wDNqTimnzs8QqpldiId9OavWK2NptormjXnRJTQecNjzwfyp6P/8s/zG8e4h3ja3oqkKaY72UlTjQYt/1yXf9A== + +fs-constants@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/fs-constants/-/fs-constants-1.0.0.tgz#6be0de9be998ce16af8afc24497b9ee9b7ccd9ad" + integrity sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow== + +fs-extra@^0.30.0: + version "0.30.0" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-0.30.0.tgz#f233ffcc08d4da7d432daa449776989db1df93f0" + integrity sha512-UvSPKyhMn6LEd/WpUaV9C9t3zATuqoqfWc3QdPhPLb58prN9tqYPlPWi8Krxi44loBoUzlobqZ3+8tGpxxSzwA== + dependencies: + graceful-fs "^4.1.2" + jsonfile "^2.1.0" + klaw "^1.0.0" + path-is-absolute "^1.0.0" + rimraf "^2.2.8" + +fs-extra@^11.1.1: + version "11.1.1" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-11.1.1.tgz#da69f7c39f3b002378b0954bb6ae7efdc0876e2d" + integrity sha512-MGIE4HOvQCeUCzmlHs0vXpih4ysz4wg9qiSAu6cd42lVwPbTM1TjV7RusoyQqMmk/95gdQZX72u+YW+c3eEpFQ== + dependencies: + graceful-fs "^4.2.0" + jsonfile "^6.0.1" + universalify "^2.0.0" + +fs-extra@^7.0.0, fs-extra@^7.0.1: + version "7.0.1" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-7.0.1.tgz#4f189c44aa123b895f722804f55ea23eadc348e9" + integrity sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw== + dependencies: + graceful-fs "^4.1.2" + jsonfile "^4.0.0" + universalify "^0.1.0" + +fs-extra@^9.1.0: + version "9.1.0" + resolved "https://registry.yarnpkg.com/fs-extra/-/fs-extra-9.1.0.tgz#5954460c764a8da2094ba3554bf839e6b9a7c86d" + integrity sha512-hcg3ZmepS30/7BSFqRvoo3DOMQu7IjqxO5nCDt+zM9XWjb33Wg7ziNT+Qvqbuc3+gWpzO02JubVyk2G4Zvo1OQ== + dependencies: + at-least-node "^1.0.0" + graceful-fs "^4.2.0" + jsonfile "^6.0.1" + universalify "^2.0.0" + +fs.realpath@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f" + integrity sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw== + +fsevents@~2.3.2: + version "2.3.3" + resolved "https://registry.yarnpkg.com/fsevents/-/fsevents-2.3.3.tgz#cac6407785d03675a2a5e1a5305c697b347d90d6" + integrity sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw== + +function-bind@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/function-bind/-/function-bind-1.1.1.tgz#a56899d3ea3c9bab874bb9773b7c5ede92f4895d" + integrity sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A== + +functional-red-black-tree@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz#1b0ab3bd553b2a0d6399d29c0e3ea0b252078327" + integrity sha512-dsKNQNdj6xA3T+QlADDA7mOSlX0qiMINjn0cgr+eGHGsbSHzTabcIogz2+p/iqP1Xs6EP/sS2SbqH+brGTbq0g== + +get-caller-file@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/get-caller-file/-/get-caller-file-2.0.5.tgz#4f94412a82db32f36e3b0b9741f8a97feb031f7e" + integrity sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg== + +get-func-name@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/get-func-name/-/get-func-name-2.0.0.tgz#ead774abee72e20409433a066366023dd6887a41" + integrity sha512-Hm0ixYtaSZ/V7C8FJrtZIuBBI+iSgL+1Aq82zSu8VQNB4S3Gk8e7Qs3VwBDJAhmRZcFqkl3tQu36g/Foh5I5ig== + +glob-parent@^5.1.2, glob-parent@~5.1.2: + version "5.1.2" + resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-5.1.2.tgz#869832c58034fe68a4093c17dc15e8340d8401c4" + integrity sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow== + dependencies: + is-glob "^4.0.1" + +glob@7.1.7: + version "7.1.7" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.7.tgz#3b193e9233f01d42d0b3f78294bbeeb418f94a90" + integrity sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.0.4" + once "^1.3.0" + path-is-absolute "^1.0.0" + +glob@7.2.0: + version "7.2.0" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.0.tgz#d15535af7732e02e948f4c41628bd910293f6023" + integrity sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.0.4" + once "^1.3.0" + path-is-absolute "^1.0.0" + +glob@^7.1.2, glob@^7.1.3, glob@^7.1.6: + version "7.2.3" + resolved "https://registry.yarnpkg.com/glob/-/glob-7.2.3.tgz#b8df0fb802bbfa8e89bd1d938b4e16578ed44f2b" + integrity sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^3.1.1" + once "^1.3.0" + path-is-absolute "^1.0.0" + +graceful-fs@^4.1.2, graceful-fs@^4.1.6, graceful-fs@^4.1.9, graceful-fs@^4.2.0, graceful-fs@^4.2.4: + version "4.2.11" + resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.11.tgz#4183e4e8bf08bb6e05bbb2f7d2e0c8f712ca40e3" + integrity sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ== + +hardhat@^2.11.0: + version "2.17.3" + resolved "https://registry.yarnpkg.com/hardhat/-/hardhat-2.17.3.tgz#4cb15f2afdea5f108970ed72e5b81e6e53052cfb" + integrity sha512-SFZoYVXW1bWJZrIIKXOA+IgcctfuKXDwENywiYNT2dM3YQc4fXNaTbuk/vpPzHIF50upByx4zW5EqczKYQubsA== + dependencies: + "@ethersproject/abi" "^5.1.2" + "@metamask/eth-sig-util" "^4.0.0" + "@nomicfoundation/ethereumjs-block" "5.0.2" + "@nomicfoundation/ethereumjs-blockchain" "7.0.2" + "@nomicfoundation/ethereumjs-common" "4.0.2" + "@nomicfoundation/ethereumjs-evm" "2.0.2" + "@nomicfoundation/ethereumjs-rlp" "5.0.2" + "@nomicfoundation/ethereumjs-statemanager" "2.0.2" + "@nomicfoundation/ethereumjs-trie" "6.0.2" + "@nomicfoundation/ethereumjs-tx" "5.0.2" + "@nomicfoundation/ethereumjs-util" "9.0.2" + "@nomicfoundation/ethereumjs-vm" "7.0.2" + "@nomicfoundation/solidity-analyzer" "^0.1.0" + "@sentry/node" "^5.18.1" + "@types/bn.js" "^5.1.0" + "@types/lru-cache" "^5.1.0" + adm-zip "^0.4.16" + aggregate-error "^3.0.0" + ansi-escapes "^4.3.0" + chalk "^2.4.2" + chokidar "^3.4.0" + ci-info "^2.0.0" + debug "^4.1.1" + enquirer "^2.3.0" + env-paths "^2.2.0" + ethereum-cryptography "^1.0.3" + ethereumjs-abi "^0.6.8" + find-up "^2.1.0" + fp-ts "1.19.3" + fs-extra "^7.0.1" + glob "7.2.0" + immutable "^4.0.0-rc.12" + io-ts "1.10.4" + keccak "^3.0.2" + lodash "^4.17.11" + mnemonist "^0.38.0" + mocha "^10.0.0" + p-map "^4.0.0" + raw-body "^2.4.1" + resolve "1.17.0" + semver "^6.3.0" + solc "0.7.3" + source-map-support "^0.5.13" + stacktrace-parser "^0.1.10" + tsort "0.0.1" + undici "^5.14.0" + uuid "^8.3.2" + ws "^7.4.6" + +has-flag@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-3.0.0.tgz#b5d454dc2199ae225699f3467e5a07f3b955bafd" + integrity sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw== + +has-flag@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-4.0.0.tgz#944771fd9c81c81265c4d6941860da06bb59479b" + integrity sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ== + +has@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/has/-/has-1.0.3.tgz#722d7cbfc1f6aa8241f16dd814e011e1f41e8796" + integrity sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw== + dependencies: + function-bind "^1.1.1" + +hash-base@^3.0.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/hash-base/-/hash-base-3.1.0.tgz#55c381d9e06e1d2997a883b4a3fddfe7f0d3af33" + integrity sha512-1nmYp/rhMDiE7AYkDw+lLwlAzz0AntGIe51F3RfFfEqyQ3feY2eI/NcwC6umIQVOASPMsWJLJScWKSSvzL9IVA== + dependencies: + inherits "^2.0.4" + readable-stream "^3.6.0" + safe-buffer "^5.2.0" + +hash.js@1.1.7, hash.js@^1.0.0, hash.js@^1.0.3, hash.js@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/hash.js/-/hash.js-1.1.7.tgz#0babca538e8d4ee4a0f8988d68866537a003cf42" + integrity sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA== + dependencies: + inherits "^2.0.3" + minimalistic-assert "^1.0.1" + +he@1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/he/-/he-1.2.0.tgz#84ae65fa7eafb165fddb61566ae14baf05664f0f" + integrity sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw== + +hmac-drbg@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/hmac-drbg/-/hmac-drbg-1.0.1.tgz#d2745701025a6c775a6c545793ed502fc0c649a1" + integrity sha512-Tti3gMqLdZfhOQY1Mzf/AanLiqh1WTiJgEj26ZuYQ9fbkLomzGchCws4FyrSd4VkpBfiNhaE1On+lOz894jvXg== + dependencies: + hash.js "^1.0.3" + minimalistic-assert "^1.0.0" + minimalistic-crypto-utils "^1.0.1" + +http-errors@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/http-errors/-/http-errors-2.0.0.tgz#b7774a1486ef73cf7667ac9ae0858c012c57b9d3" + integrity sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ== + dependencies: + depd "2.0.0" + inherits "2.0.4" + setprototypeof "1.2.0" + statuses "2.0.1" + toidentifier "1.0.1" + +https-proxy-agent@^5.0.0: + version "5.0.1" + resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz#c59ef224a04fe8b754f3db0063a25ea30d0005d6" + integrity sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA== + dependencies: + agent-base "6" + debug "4" + +iconv-lite@0.4.24: + version "0.4.24" + resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.24.tgz#2022b4b25fbddc21d2f524974a474aafe733908b" + integrity sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA== + dependencies: + safer-buffer ">= 2.1.2 < 3" + +ieee754@^1.1.13, ieee754@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/ieee754/-/ieee754-1.2.1.tgz#8eb7a10a63fff25d15a57b001586d177d1b0d352" + integrity sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA== + +immutable@^4.0.0-rc.12: + version "4.3.4" + resolved "https://registry.yarnpkg.com/immutable/-/immutable-4.3.4.tgz#2e07b33837b4bb7662f288c244d1ced1ef65a78f" + integrity sha512-fsXeu4J4i6WNWSikpI88v/PcVflZz+6kMhUfIwc5SY+poQRPnaf5V7qds6SUyUN3cVxEzuCab7QIoLOQ+DQ1wA== + +indent-string@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/indent-string/-/indent-string-4.0.0.tgz#624f8f4497d619b2d9768531d58f4122854d7251" + integrity sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg== + +inflight@^1.0.4: + version "1.0.6" + resolved "https://registry.yarnpkg.com/inflight/-/inflight-1.0.6.tgz#49bd6331d7d02d0c09bc910a1075ba8165b56df9" + integrity sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA== + dependencies: + once "^1.3.0" + wrappy "1" + +inherits@2, inherits@2.0.4, inherits@^2.0.1, inherits@^2.0.3, inherits@^2.0.4, inherits@~2.0.1, inherits@~2.0.3: + version "2.0.4" + resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.4.tgz#0fa2c64f932917c3433a0ded55363aae37416b7c" + integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== + +io-ts@1.10.4: + version "1.10.4" + resolved "https://registry.yarnpkg.com/io-ts/-/io-ts-1.10.4.tgz#cd5401b138de88e4f920adbcb7026e2d1967e6e2" + integrity sha512-b23PteSnYXSONJ6JQXRAlvJhuw8KOtkqa87W4wDtvMrud/DTJd5X+NpOOI+O/zZwVq6v0VLAaJ+1EDViKEuN9g== + dependencies: + fp-ts "^1.0.0" + +is-binary-path@~2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-2.1.0.tgz#ea1f7f3b80f064236e83470f86c09c254fb45b09" + integrity sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw== + dependencies: + binary-extensions "^2.0.0" + +is-buffer@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/is-buffer/-/is-buffer-2.0.5.tgz#ebc252e400d22ff8d77fa09888821a24a658c191" + integrity sha512-i2R6zNFDwgEHJyQUtJEk0XFi1i0dPFn/oqjK3/vPCcDeJvW5NQ83V8QbicfF1SupOaB0h8ntgBC2YiE7dfyctQ== + +is-core-module@^2.13.0: + version "2.13.0" + resolved "https://registry.yarnpkg.com/is-core-module/-/is-core-module-2.13.0.tgz#bb52aa6e2cbd49a30c2ba68c42bf3435ba6072db" + integrity sha512-Z7dk6Qo8pOCp3l4tsX2C5ZVas4V+UxwQodwZhLopL91TX8UyyHEXafPcyoeeWuLrwzHcr3igO78wNLwHJHsMCQ== + dependencies: + has "^1.0.3" + +is-extglob@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2" + integrity sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ== + +is-fullwidth-code-point@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz#f116f8064fe90b3f7844a38997c0b75051269f1d" + integrity sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg== + +is-glob@^4.0.1, is-glob@~4.0.1: + version "4.0.3" + resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-4.0.3.tgz#64f61e42cbbb2eec2071a9dac0b28ba1e65d5084" + integrity sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg== + dependencies: + is-extglob "^2.1.1" + +is-hex-prefixed@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz#7d8d37e6ad77e5d127148913c573e082d777f554" + integrity sha512-WvtOiug1VFrE9v1Cydwm+FnXd3+w9GaeVUss5W4v/SLy3UW00vP+6iNF2SdnfiBoLy4bTqVdkftNGTUeOFVsbA== + +is-number@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/is-number/-/is-number-7.0.0.tgz#7535345b896734d5f80c4d06c50955527a14f12b" + integrity sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng== + +is-plain-obj@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/is-plain-obj/-/is-plain-obj-2.1.0.tgz#45e42e37fccf1f40da8e5f76ee21515840c09287" + integrity sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA== + +is-unicode-supported@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz#3f26c76a809593b52bfa2ecb5710ed2779b522a7" + integrity sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw== + +isarray@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/isarray/-/isarray-0.0.1.tgz#8a18acfca9a8f4177e09abfc6038939b05d1eedf" + integrity sha512-D2S+3GLxWH+uhrNEcoh/fnmYeP8E8/zHl644d/jdA0g2uyXvy3sb0qxotE+ne0LtccHknQzWwZEzhak7oJ0COQ== + +isarray@~1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11" + integrity sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ== + +js-sdsl@^4.1.4: + version "4.4.2" + resolved "https://registry.yarnpkg.com/js-sdsl/-/js-sdsl-4.4.2.tgz#2e3c031b1f47d3aca8b775532e3ebb0818e7f847" + integrity sha512-dwXFwByc/ajSV6m5bcKAPwe4yDDF6D614pxmIi5odytzxRlwqF6nwoiCek80Ixc7Cvma5awClxrzFtxCQvcM8w== + +js-sha3@0.8.0, js-sha3@^0.8.0: + version "0.8.0" + resolved "https://registry.yarnpkg.com/js-sha3/-/js-sha3-0.8.0.tgz#b9b7a5da73afad7dedd0f8c463954cbde6818840" + integrity sha512-gF1cRrHhIzNfToc802P800N8PpXS+evLLXfsVpowqmAFR9uwbi89WvXg2QspOmXL8QL86J4T1EpFu+yUkwJY3Q== + +js-yaml@4.1.0: + version "4.1.0" + resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-4.1.0.tgz#c1fb65f8f5017901cdd2c951864ba18458a10602" + integrity sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA== + dependencies: + argparse "^2.0.1" + +jsonfile@^2.1.0: + version "2.4.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-2.4.0.tgz#3736a2b428b87bbda0cc83b53fa3d633a35c2ae8" + integrity sha512-PKllAqbgLgxHaj8TElYymKCAgrASebJrWpTnEkOaTowt23VKXXN0sUeriJ+eh7y6ufb/CC5ap11pz71/cM0hUw== + optionalDependencies: + graceful-fs "^4.1.6" + +jsonfile@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-4.0.0.tgz#8771aae0799b64076b76640fca058f9c10e33ecb" + integrity sha512-m6F1R3z8jjlf2imQHS2Qez5sjKWQzbuuhuJ/FKYFRZvPE3PuHcSMVZzfsLhGVOkfd20obL5SWEBew5ShlquNxg== + optionalDependencies: + graceful-fs "^4.1.6" + +jsonfile@^6.0.1: + version "6.1.0" + resolved "https://registry.yarnpkg.com/jsonfile/-/jsonfile-6.1.0.tgz#bc55b2634793c679ec6403094eb13698a6ec0aae" + integrity sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ== + dependencies: + universalify "^2.0.0" + optionalDependencies: + graceful-fs "^4.1.6" + +jsonparse@^1.2.0: + version "1.3.1" + resolved "https://registry.yarnpkg.com/jsonparse/-/jsonparse-1.3.1.tgz#3f4dae4a91fac315f71062f8521cc239f1366280" + integrity sha512-POQXvpdL69+CluYsillJ7SUhKvytYjW9vG/GKpnf+xP8UWgYEM/RaMzHHofbALDiKbbP1W8UEYmgGl39WkPZsg== + +keccak@^3.0.0, keccak@^3.0.2: + version "3.0.3" + resolved "https://registry.yarnpkg.com/keccak/-/keccak-3.0.3.tgz#4bc35ad917be1ef54ff246f904c2bbbf9ac61276" + integrity sha512-JZrLIAJWuZxKbCilMpNz5Vj7Vtb4scDG3dMXLOsbzBmQGyjwE61BbW7bJkfKKCShXiQZt3T6sBgALRtmd+nZaQ== + dependencies: + node-addon-api "^2.0.0" + node-gyp-build "^4.2.0" + readable-stream "^3.6.0" + +klaw@^1.0.0: + version "1.3.1" + resolved "https://registry.yarnpkg.com/klaw/-/klaw-1.3.1.tgz#4088433b46b3b1ba259d78785d8e96f73ba02439" + integrity sha512-TED5xi9gGQjGpNnvRWknrwAB1eL5GciPfVFOt3Vk1OJCVDQbzuSfrF3hkUQKlsgKrG1F+0t5W0m+Fje1jIt8rw== + optionalDependencies: + graceful-fs "^4.1.9" + +level-supports@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/level-supports/-/level-supports-4.0.1.tgz#431546f9d81f10ff0fea0e74533a0e875c08c66a" + integrity sha512-PbXpve8rKeNcZ9C1mUicC9auIYFyGpkV9/i6g76tLgANwWhtG2v7I4xNBUlkn3lE2/dZF3Pi0ygYGtLc4RXXdA== + +level-transcoder@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/level-transcoder/-/level-transcoder-1.0.1.tgz#f8cef5990c4f1283d4c86d949e73631b0bc8ba9c" + integrity sha512-t7bFwFtsQeD8cl8NIoQ2iwxA0CL/9IFw7/9gAjOonH0PWTTiRfY7Hq+Ejbsxh86tXobDQ6IOiddjNYIfOBs06w== + dependencies: + buffer "^6.0.3" + module-error "^1.0.1" + +level@^8.0.0: + version "8.0.0" + resolved "https://registry.yarnpkg.com/level/-/level-8.0.0.tgz#41b4c515dabe28212a3e881b61c161ffead14394" + integrity sha512-ypf0jjAk2BWI33yzEaaotpq7fkOPALKAgDBxggO6Q9HGX2MRXn0wbP1Jn/tJv1gtL867+YOjOB49WaUF3UoJNQ== + dependencies: + browser-level "^1.0.1" + classic-level "^1.2.0" + +locate-path@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-2.0.0.tgz#2b568b265eec944c6d9c0de9c3dbbbca0354cd8e" + integrity sha512-NCI2kiDkyR7VeEKm27Kda/iQHyKJe1Bu0FlTbYp3CqJu+9IFe9bLyAjMxf5ZDDbEg+iMPzB5zYyUTSm8wVTKmA== + dependencies: + p-locate "^2.0.0" + path-exists "^3.0.0" + +locate-path@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-6.0.0.tgz#55321eb309febbc59c4801d931a72452a681d286" + integrity sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw== + dependencies: + p-locate "^5.0.0" + +lodash.camelcase@^4.3.0: + version "4.3.0" + resolved "https://registry.yarnpkg.com/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz#b28aa6288a2b9fc651035c7711f65ab6190331a6" + integrity sha512-TwuEnCnxbc3rAvhf/LbG7tJUDzhqXyFnv3dtzLOPgCG/hODL7WFnsbwktkD7yUV0RrreP/l1PALq/YSg6VvjlA== + +lodash@^4.17.11, lodash@^4.17.15: + version "4.17.21" + resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.21.tgz#679591c564c3bffaae8454cf0b3df370c3d6911c" + integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg== + +log-symbols@4.1.0: + version "4.1.0" + resolved "https://registry.yarnpkg.com/log-symbols/-/log-symbols-4.1.0.tgz#3fbdbb95b4683ac9fc785111e792e558d4abd503" + integrity sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg== + dependencies: + chalk "^4.1.0" + is-unicode-supported "^0.1.0" + +loupe@^2.3.1: + version "2.3.6" + resolved "https://registry.yarnpkg.com/loupe/-/loupe-2.3.6.tgz#76e4af498103c532d1ecc9be102036a21f787b53" + integrity sha512-RaPMZKiMy8/JruncMU5Bt6na1eftNoo++R4Y+N2FrxkDVTrGvcyzFTsaGif4QTeKESheMGegbhw6iUAq+5A8zA== + dependencies: + get-func-name "^2.0.0" + +lru-cache@^5.1.1: + version "5.1.1" + resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-5.1.1.tgz#1da27e6710271947695daf6848e847f01d84b920" + integrity sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w== + dependencies: + yallist "^3.0.2" + +lru-cache@^6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/lru-cache/-/lru-cache-6.0.0.tgz#6d6fe6570ebd96aaf90fcad1dafa3b2566db3a94" + integrity sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA== + dependencies: + yallist "^4.0.0" + +lru_map@^0.3.3: + version "0.3.3" + resolved "https://registry.yarnpkg.com/lru_map/-/lru_map-0.3.3.tgz#b5c8351b9464cbd750335a79650a0ec0e56118dd" + integrity sha512-Pn9cox5CsMYngeDbmChANltQl+5pi6XmTrraMSzhPmMBbmgcxmqWry0U3PGapCU1yB4/LqCcom7qhHZiF/jGfQ== + +make-error@^1.1.1: + version "1.3.6" + resolved "https://registry.yarnpkg.com/make-error/-/make-error-1.3.6.tgz#2eb2e37ea9b67c4891f684a1394799af484cf7a2" + integrity sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw== + +mcl-wasm@^0.7.1: + version "0.7.9" + resolved "https://registry.yarnpkg.com/mcl-wasm/-/mcl-wasm-0.7.9.tgz#c1588ce90042a8700c3b60e40efb339fc07ab87f" + integrity sha512-iJIUcQWA88IJB/5L15GnJVnSQJmf/YaxxV6zRavv83HILHaJQb6y0iFyDMdDO0gN8X37tdxmAOrH/P8B6RB8sQ== + +md5.js@^1.3.4: + version "1.3.5" + resolved "https://registry.yarnpkg.com/md5.js/-/md5.js-1.3.5.tgz#b5d07b8e3216e3e27cd728d72f70d1e6a342005f" + integrity sha512-xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg== + dependencies: + hash-base "^3.0.0" + inherits "^2.0.1" + safe-buffer "^5.1.2" + +memory-level@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/memory-level/-/memory-level-1.0.0.tgz#7323c3fd368f9af2f71c3cd76ba403a17ac41692" + integrity sha512-UXzwewuWeHBz5krr7EvehKcmLFNoXxGcvuYhC41tRnkrTbJohtS7kVn9akmgirtRygg+f7Yjsfi8Uu5SGSQ4Og== + dependencies: + abstract-level "^1.0.0" + functional-red-black-tree "^1.0.1" + module-error "^1.0.1" + +memorystream@^0.3.1: + version "0.3.1" + resolved "https://registry.yarnpkg.com/memorystream/-/memorystream-0.3.1.tgz#86d7090b30ce455d63fbae12dda51a47ddcaf9b2" + integrity sha512-S3UwM3yj5mtUSEfP41UZmt/0SCoVYUcU1rkXv+BQ5Ig8ndL4sPoJNBUJERafdPb5jjHJGuMgytgKvKIf58XNBw== + +merge2@^1.3.0: + version "1.4.1" + resolved "https://registry.yarnpkg.com/merge2/-/merge2-1.4.1.tgz#4368892f885e907455a6fd7dc55c0c9d404990ae" + integrity sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg== + +micromatch@^4.0.4: + version "4.0.5" + resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-4.0.5.tgz#bc8999a7cbbf77cdc89f132f6e467051b49090c6" + integrity sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA== + dependencies: + braces "^3.0.2" + picomatch "^2.3.1" + +minimalistic-assert@^1.0.0, minimalistic-assert@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz#2e194de044626d4a10e7f7fbc00ce73e83e4d5c7" + integrity sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A== + +minimalistic-crypto-utils@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz#f6c00c1c0b082246e5c4d99dfb8c7c083b2b582a" + integrity sha512-JIYlbt6g8i5jKfJ3xz7rF0LXmv2TkDxBLUkiBeZ7bAx4GnnNMr8xFpGnOxn6GhTEHx3SjRrZEoU+j04prX1ktg== + +minimatch@5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.0.1.tgz#fb9022f7528125187c92bd9e9b6366be1cf3415b" + integrity sha512-nLDxIFRyhDblz3qMuq+SoRZED4+miJ/G+tdDrjkkkRnjAsBexeGpgjLEQ0blJy7rHhR2b93rhQY4SvyWu9v03g== + dependencies: + brace-expansion "^2.0.1" + +minimatch@^3.0.4, minimatch@^3.1.1: + version "3.1.2" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.1.2.tgz#19cd194bfd3e428f049a70817c038d89ab4be35b" + integrity sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw== + dependencies: + brace-expansion "^1.1.7" + +minimatch@^7.4.3: + version "7.4.6" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-7.4.6.tgz#845d6f254d8f4a5e4fd6baf44d5f10c8448365fb" + integrity sha512-sBz8G/YjVniEz6lKPNpKxXwazJe4c19fEfV2GDMX6AjFz+MX9uDWIZW8XreVhkFW3fkIdTv/gxWr/Kks5FFAVw== + dependencies: + brace-expansion "^2.0.1" + +minimist@^1.2.6: + version "1.2.8" + resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.8.tgz#c1a464e7693302e082a075cee0c057741ac4772c" + integrity sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA== + +mkdirp-classic@^0.5.2: + version "0.5.3" + resolved "https://registry.yarnpkg.com/mkdirp-classic/-/mkdirp-classic-0.5.3.tgz#fa10c9115cc6d8865be221ba47ee9bed78601113" + integrity sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A== + +mkdirp@^0.5.1: + version "0.5.6" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-0.5.6.tgz#7def03d2432dcae4ba1d611445c48396062255f6" + integrity sha512-FP+p8RB8OWpF3YZBCrP5gtADmtXApB5AMLn+vdyA+PyxCjrCs00mjyUozssO33cwDeT3wNGdLxJ5M//YqtHAJw== + dependencies: + minimist "^1.2.6" + +mkdirp@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-1.0.4.tgz#3eb5ed62622756d79a5f0e2a221dfebad75c2f7e" + integrity sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw== + +mkdirp@^2.1.6: + version "2.1.6" + resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-2.1.6.tgz#964fbcb12b2d8c5d6fbc62a963ac95a273e2cc19" + integrity sha512-+hEnITedc8LAtIP9u3HJDFIdcLV2vXP33sqLLIzkv1Db1zO/1OxbvYf0Y1OC/S/Qo5dxHXepofhmxL02PsKe+A== + +mnemonist@^0.38.0: + version "0.38.5" + resolved "https://registry.yarnpkg.com/mnemonist/-/mnemonist-0.38.5.tgz#4adc7f4200491237fe0fa689ac0b86539685cade" + integrity sha512-bZTFT5rrPKtPJxj8KSV0WkPyNxl72vQepqqVUAW2ARUpUSF2qXMB6jZj7hW5/k7C1rtpzqbD/IIbJwLXUjCHeg== + dependencies: + obliterator "^2.0.0" + +mocha@^10.0.0: + version "10.2.0" + resolved "https://registry.yarnpkg.com/mocha/-/mocha-10.2.0.tgz#1fd4a7c32ba5ac372e03a17eef435bd00e5c68b8" + integrity sha512-IDY7fl/BecMwFHzoqF2sg/SHHANeBoMMXFlS9r0OXKDssYE1M5O43wUY/9BVPeIvfH2zmEbBfseqN9gBQZzXkg== + dependencies: + ansi-colors "4.1.1" + browser-stdout "1.3.1" + chokidar "3.5.3" + debug "4.3.4" + diff "5.0.0" + escape-string-regexp "4.0.0" + find-up "5.0.0" + glob "7.2.0" + he "1.2.0" + js-yaml "4.1.0" + log-symbols "4.1.0" + minimatch "5.0.1" + ms "2.1.3" + nanoid "3.3.3" + serialize-javascript "6.0.0" + strip-json-comments "3.1.1" + supports-color "8.1.1" + workerpool "6.2.1" + yargs "16.2.0" + yargs-parser "20.2.4" + yargs-unparser "2.0.0" + +module-error@^1.0.1, module-error@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/module-error/-/module-error-1.0.2.tgz#8d1a48897ca883f47a45816d4fb3e3c6ba404d86" + integrity sha512-0yuvsqSCv8LbaOKhnsQ/T5JhyFlCYLPXK3U2sgV10zoKQwzs/MyfuQUOZQ1V/6OCOJsK/TRgNVrPuPDqtdMFtA== + +ms@2.1.2: + version "2.1.2" + resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.2.tgz#d09d1f357b443f493382a8eb3ccd183872ae6009" + integrity sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w== + +ms@2.1.3, ms@^2.1.1: + version "2.1.3" + resolved "https://registry.yarnpkg.com/ms/-/ms-2.1.3.tgz#574c8138ce1d2b5861f0b44579dbadd60c6615b2" + integrity sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA== + +mz@^2.7.0: + version "2.7.0" + resolved "https://registry.yarnpkg.com/mz/-/mz-2.7.0.tgz#95008057a56cafadc2bc63dde7f9ff6955948e32" + integrity sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q== + dependencies: + any-promise "^1.0.0" + object-assign "^4.0.1" + thenify-all "^1.0.0" + +nan@^2.17.0: + version "2.18.0" + resolved "https://registry.yarnpkg.com/nan/-/nan-2.18.0.tgz#26a6faae7ffbeb293a39660e88a76b82e30b7554" + integrity sha512-W7tfG7vMOGtD30sHoZSSc/JVYiyDPEyQVso/Zz+/uQd0B0L46gtC+pHha5FFMRpil6fm/AoEcRWyOVi4+E/f8w== + +nanoid@3.3.3: + version "3.3.3" + resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.3.3.tgz#fd8e8b7aa761fe807dba2d1b98fb7241bb724a25" + integrity sha512-p1sjXuopFs0xg+fPASzQ28agW1oHD7xDsd9Xkf3T15H3c/cifrFHVwrh74PdoklAPi+i7MdRsE47vm2r6JoB+w== + +napi-macros@^2.2.2: + version "2.2.2" + resolved "https://registry.yarnpkg.com/napi-macros/-/napi-macros-2.2.2.tgz#817fef20c3e0e40a963fbf7b37d1600bd0201044" + integrity sha512-hmEVtAGYzVQpCKdbQea4skABsdXW4RUh5t5mJ2zzqowJS2OyXZTU1KhDVFhx+NlWZ4ap9mqR9TcDO3LTTttd+g== + +node-addon-api@^2.0.0: + version "2.0.2" + resolved "https://registry.yarnpkg.com/node-addon-api/-/node-addon-api-2.0.2.tgz#432cfa82962ce494b132e9d72a15b29f71ff5d32" + integrity sha512-Ntyt4AIXyaLIuMHF6IOoTakB3K+RWxwtsHNRxllEoA6vPwP9o4866g6YWDLUdnucilZhmkxiHwHr11gAENw+QA== + +node-fetch@^2.6.0: + version "2.7.0" + resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.7.0.tgz#d0f0fa6e3e2dc1d27efcd8ad99d550bda94d187d" + integrity sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A== + dependencies: + whatwg-url "^5.0.0" + +node-gyp-build@^4.2.0, node-gyp-build@^4.3.0: + version "4.6.1" + resolved "https://registry.yarnpkg.com/node-gyp-build/-/node-gyp-build-4.6.1.tgz#24b6d075e5e391b8d5539d98c7fc5c210cac8a3e" + integrity sha512-24vnklJmyRS8ViBNI8KbtK/r/DmXQMRiOMXTNz2nrTnAYUwjmEEbnnpB/+kt+yWRv73bPsSPRFddrcIbAxSiMQ== + +normalize-path@^3.0.0, normalize-path@~3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/normalize-path/-/normalize-path-3.0.0.tgz#0dcd69ff23a1c9b11fd0978316644a0388216a65" + integrity sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA== + +object-assign@^4.0.1: + version "4.1.1" + resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863" + integrity sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg== + +obliterator@^2.0.0: + version "2.0.4" + resolved "https://registry.yarnpkg.com/obliterator/-/obliterator-2.0.4.tgz#fa650e019b2d075d745e44f1effeb13a2adbe816" + integrity sha512-lgHwxlxV1qIg1Eap7LgIeoBWIMFibOjbrYPIPJZcI1mmGAI2m3lNYpK12Y+GBdPQ0U1hRwSord7GIaawz962qQ== + +once@^1.3.0, once@^1.3.1, once@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1" + integrity sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w== + dependencies: + wrappy "1" + +os-tmpdir@~1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/os-tmpdir/-/os-tmpdir-1.0.2.tgz#bbe67406c79aa85c5cfec766fe5734555dfa1274" + integrity sha512-D2FR03Vir7FIu45XBY20mTb+/ZSWB00sjU9jdQXt83gDrI4Ztz5Fs7/yy74g2N5SVQY4xY1qDr4rNddwYRVX0g== + +p-limit@^1.1.0: + version "1.3.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-1.3.0.tgz#b86bd5f0c25690911c7590fcbfc2010d54b3ccb8" + integrity sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q== + dependencies: + p-try "^1.0.0" + +p-limit@^3.0.2: + version "3.1.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-3.1.0.tgz#e1daccbe78d0d1388ca18c64fea38e3e57e3706b" + integrity sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ== + dependencies: + yocto-queue "^0.1.0" + +p-limit@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-4.0.0.tgz#914af6544ed32bfa54670b061cafcbd04984b644" + integrity sha512-5b0R4txpzjPWVw/cXXUResoD4hb6U/x9BH08L7nw+GN1sezDzPdxeRvpc9c433fZhBan/wusjbCsqwqm4EIBIQ== + dependencies: + yocto-queue "^1.0.0" + +p-locate@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-2.0.0.tgz#20a0103b222a70c8fd39cc2e580680f3dde5ec43" + integrity sha512-nQja7m7gSKuewoVRen45CtVfODR3crN3goVQ0DDZ9N3yHxgpkuBhZqsaiotSQRrADUrne346peY7kT3TSACykg== + dependencies: + p-limit "^1.1.0" + +p-locate@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-5.0.0.tgz#83c8315c6785005e3bd021839411c9e110e6d834" + integrity sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw== + dependencies: + p-limit "^3.0.2" + +p-map@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/p-map/-/p-map-4.0.0.tgz#bb2f95a5eda2ec168ec9274e06a747c3e2904d2b" + integrity sha512-/bjOqmgETBYB5BoEeGVea8dmvHb2m9GLy1E9W43yeyfP6QQCZGFNa+XRceJEuDB6zqr+gKpIAmlLebMpykw/MQ== + dependencies: + aggregate-error "^3.0.0" + +p-try@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/p-try/-/p-try-1.0.0.tgz#cbc79cdbaf8fd4228e13f621f2b1a237c1b207b3" + integrity sha512-U1etNYuMJoIz3ZXSrrySFjsXQTWOx2/jdi86L+2pRvph/qMKL6sbcCYdH23fqsbm8TH2Gn0OybpT4eSFlCVHww== + +path-browserify@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/path-browserify/-/path-browserify-1.0.1.tgz#d98454a9c3753d5790860f16f68867b9e46be1fd" + integrity sha512-b7uo2UCUOYZcnF/3ID0lulOJi/bafxa1xPe7ZPsammBSpjSWQkjNxlt635YGS2MiR9GjvuXCtz2emr3jbsz98g== + +path-exists@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-3.0.0.tgz#ce0ebeaa5f78cb18925ea7d810d7b59b010fd515" + integrity sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ== + +path-exists@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-4.0.0.tgz#513bdbe2d3b95d7762e8c1137efa195c6c61b5b3" + integrity sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w== + +path-is-absolute@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f" + integrity sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg== + +path-parse@^1.0.6, path-parse@^1.0.7: + version "1.0.7" + resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.7.tgz#fbc114b60ca42b30d9daf5858e4bd68bbedb6735" + integrity sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw== + +pathington@^1.1.7: + version "1.1.7" + resolved "https://registry.yarnpkg.com/pathington/-/pathington-1.1.7.tgz#caf2d2db899a31fea4e81e3657af6acde5171903" + integrity sha512-JxzhUzagDfNIOm4qqwQqP3rWeo7rNNOfIahy4n+3GTEdwXLqw5cJHUR0soSopQtNEv763lzxb6eA2xBllpR8zw== + +pathval@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/pathval/-/pathval-1.1.1.tgz#8534e77a77ce7ac5a2512ea21e0fdb8fcf6c3d8d" + integrity sha512-Dp6zGqpTdETdR63lehJYPeIOqpiNBNtc7BpWSLrOje7UaIsE5aY92r/AunQA7rsXvet3lrJ3JnZX29UPTKXyKQ== + +pbkdf2@^3.0.17: + version "3.1.2" + resolved "https://registry.yarnpkg.com/pbkdf2/-/pbkdf2-3.1.2.tgz#dd822aa0887580e52f1a039dc3eda108efae3075" + integrity sha512-iuh7L6jA7JEGu2WxDwtQP1ddOpaJNC4KlDEFfdQajSGgGPNi4OyDc2R7QnbY2bR9QjBVGwgvTdNJZoE7RaxUMA== + dependencies: + create-hash "^1.1.2" + create-hmac "^1.1.4" + ripemd160 "^2.0.1" + safe-buffer "^5.0.1" + sha.js "^2.4.8" + +picomatch@^2.0.4, picomatch@^2.2.1, picomatch@^2.3.1: + version "2.3.1" + resolved "https://registry.yarnpkg.com/picomatch/-/picomatch-2.3.1.tgz#3ba3833733646d9d3e4995946c1365a67fb07a42" + integrity sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA== + +preprocess@^3.2.0: + version "3.2.0" + resolved "https://registry.yarnpkg.com/preprocess/-/preprocess-3.2.0.tgz#36b3e2c52331fbc6fabb26d4fd5709304b7e3675" + integrity sha512-cO+Rf+Ose/eD+ze8Hxd9p9nS1xT8thYqv8owG/V8+IS/Remd7Z17SvaRK/oJxp08yaM8zb+QTckDKJUul2pk7g== + dependencies: + xregexp "3.1.0" + +prettier-plugin-solidity@^1.0.0-alpha.27: + version "1.1.3" + resolved "https://registry.yarnpkg.com/prettier-plugin-solidity/-/prettier-plugin-solidity-1.1.3.tgz#9a35124f578404caf617634a8cab80862d726cba" + integrity sha512-fQ9yucPi2sBbA2U2Xjh6m4isUTJ7S7QLc/XDDsktqqxYfTwdYKJ0EnnywXHwCGAaYbQNK+HIYPL1OemxuMsgeg== + dependencies: + "@solidity-parser/parser" "^0.16.0" + semver "^7.3.8" + solidity-comments-extractor "^0.0.7" + +prettier@^2.1.2, prettier@^2.3.0, prettier@^2.3.1: + version "2.8.8" + resolved "https://registry.yarnpkg.com/prettier/-/prettier-2.8.8.tgz#e8c5d7e98a4305ffe3de2e1fc4aca1a71c28b1da" + integrity sha512-tdN8qQGvNjw4CHbY+XXk0JgCXn9QiF21a55rBe5LJAU+kDyC4WQn4+awm2Xfk2lQMk5fKup9XgzTZtGkjBdP9Q== + +process-nextick-args@~2.0.0: + version "2.0.1" + resolved "https://registry.yarnpkg.com/process-nextick-args/-/process-nextick-args-2.0.1.tgz#7820d9b16120cc55ca9ae7792680ae7dba6d7fe2" + integrity sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag== + +proper-lockfile@^4.1.2: + version "4.1.2" + resolved "https://registry.yarnpkg.com/proper-lockfile/-/proper-lockfile-4.1.2.tgz#c8b9de2af6b2f1601067f98e01ac66baa223141f" + integrity sha512-TjNPblN4BwAWMXU8s9AEz4JmQxnD1NNL7bNOY/AKUzyamc379FWASUhc/K1pL2noVb+XmZKLL68cjzLsiOAMaA== + dependencies: + graceful-fs "^4.2.4" + retry "^0.12.0" + signal-exit "^3.0.2" + +pump@^1.0.0: + version "1.0.3" + resolved "https://registry.yarnpkg.com/pump/-/pump-1.0.3.tgz#5dfe8311c33bbf6fc18261f9f34702c47c08a954" + integrity sha512-8k0JupWme55+9tCVE+FS5ULT3K6AbgqrGa58lTT49RpyfwwcGedHqaC5LlQNdEAumn/wFsu6aPwkuPMioy8kqw== + dependencies: + end-of-stream "^1.1.0" + once "^1.3.1" + +pump@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/pump/-/pump-3.0.0.tgz#b4a2116815bde2f4e1ea602354e8c75565107a64" + integrity sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww== + dependencies: + end-of-stream "^1.1.0" + once "^1.3.1" + +queue-microtask@^1.2.2, queue-microtask@^1.2.3: + version "1.2.3" + resolved "https://registry.yarnpkg.com/queue-microtask/-/queue-microtask-1.2.3.tgz#4929228bbc724dfac43e0efb058caf7b6cfb6243" + integrity sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A== + +randombytes@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/randombytes/-/randombytes-2.1.0.tgz#df6f84372f0270dc65cdf6291349ab7a473d4f2a" + integrity sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ== + dependencies: + safe-buffer "^5.1.0" + +raw-body@^2.4.1: + version "2.5.2" + resolved "https://registry.yarnpkg.com/raw-body/-/raw-body-2.5.2.tgz#99febd83b90e08975087e8f1f9419a149366b68a" + integrity sha512-8zGqypfENjCIqGhgXToC8aB2r7YrBX+AQAfIPs/Mlk+BtPTztOvTS01NRW/3Eh60J+a48lt8qsCzirQ6loCVfA== + dependencies: + bytes "3.1.2" + http-errors "2.0.0" + iconv-lite "0.4.24" + unpipe "1.0.0" + +readable-stream@^2.2.2, readable-stream@^2.3.0, readable-stream@^2.3.5: + version "2.3.8" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.3.8.tgz#91125e8042bba1b9887f49345f6277027ce8be9b" + integrity sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA== + dependencies: + core-util-is "~1.0.0" + inherits "~2.0.3" + isarray "~1.0.0" + process-nextick-args "~2.0.0" + safe-buffer "~5.1.1" + string_decoder "~1.1.1" + util-deprecate "~1.0.1" + +readable-stream@^3.1.1, readable-stream@^3.4.0, readable-stream@^3.5.0, readable-stream@^3.6.0: + version "3.6.2" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-3.6.2.tgz#56a9b36ea965c00c5a93ef31eb111a0f11056967" + integrity sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA== + dependencies: + inherits "^2.0.3" + string_decoder "^1.1.1" + util-deprecate "^1.0.1" + +readable-stream@~1.0.26-4: + version "1.0.34" + resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-1.0.34.tgz#125820e34bc842d2f2aaafafe4c2916ee32c157c" + integrity sha512-ok1qVCJuRkNmvebYikljxJA/UEsKwLl2nI1OmaqAu4/UE+h0wKCHok4XkL/gvi39OacXvw59RJUOFUkDib2rHg== + dependencies: + core-util-is "~1.0.0" + inherits "~2.0.1" + isarray "0.0.1" + string_decoder "~0.10.x" + +readdirp@~3.6.0: + version "3.6.0" + resolved "https://registry.yarnpkg.com/readdirp/-/readdirp-3.6.0.tgz#74a370bd857116e245b29cc97340cd431a02a6c7" + integrity sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA== + dependencies: + picomatch "^2.2.1" + +reduce-flatten@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/reduce-flatten/-/reduce-flatten-2.0.0.tgz#734fd84e65f375d7ca4465c69798c25c9d10ae27" + integrity sha512-EJ4UNY/U1t2P/2k6oqotuX2Cc3T6nxJwsM0N0asT7dhrtH1ltUxDn4NalSYmPE2rCkVpcf/X6R0wDwcFpzhd4w== + +require-directory@^2.1.1: + version "2.1.1" + resolved "https://registry.yarnpkg.com/require-directory/-/require-directory-2.1.1.tgz#8c64ad5fd30dab1c976e2344ffe7f792a6a6df42" + integrity sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q== + +require-from-string@^2.0.0: + version "2.0.2" + resolved "https://registry.yarnpkg.com/require-from-string/-/require-from-string-2.0.2.tgz#89a7fdd938261267318eafe14f9c32e598c36909" + integrity sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw== + +resolve@1.17.0: + version "1.17.0" + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.17.0.tgz#b25941b54968231cc2d1bb76a79cb7f2c0bf8444" + integrity sha512-ic+7JYiV8Vi2yzQGFWOkiZD5Z9z7O2Zhm9XMaTxdJExKasieFCr+yXZ/WmXsckHiKl12ar0y6XiXDx3m4RHn1w== + dependencies: + path-parse "^1.0.6" + +resolve@^1.10.0, resolve@^1.8.1: + version "1.22.4" + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.22.4.tgz#1dc40df46554cdaf8948a486a10f6ba1e2026c34" + integrity sha512-PXNdCiPqDqeUou+w1C2eTQbNfxKSuMxqTCuvlmmMsk1NWHL5fRrhY6Pl0qEYYc6+QqGClco1Qj8XnjPego4wfg== + dependencies: + is-core-module "^2.13.0" + path-parse "^1.0.7" + supports-preserve-symlinks-flag "^1.0.0" + +retry@^0.12.0: + version "0.12.0" + resolved "https://registry.yarnpkg.com/retry/-/retry-0.12.0.tgz#1b42a6266a21f07421d1b0b54b7dc167b01c013b" + integrity sha512-9LkiTwjUh6rT555DtE9rTX+BKByPfrMzEAtnlEtdEwr3Nkffwiihqe2bWADg+OQRjt9gl6ICdmB/ZFDCGAtSow== + +reusify@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/reusify/-/reusify-1.0.4.tgz#90da382b1e126efc02146e90845a88db12925d76" + integrity sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw== + +rimraf@^2.2.8: + version "2.7.1" + resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.7.1.tgz#35797f13a7fdadc566142c29d4f07ccad483e3ec" + integrity sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w== + dependencies: + glob "^7.1.3" + +ripemd160@^2.0.0, ripemd160@^2.0.1: + version "2.0.2" + resolved "https://registry.yarnpkg.com/ripemd160/-/ripemd160-2.0.2.tgz#a1c1a6f624751577ba5d07914cbc92850585890c" + integrity sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA== + dependencies: + hash-base "^3.0.0" + inherits "^2.0.1" + +rlp@^2.2.3: + version "2.2.7" + resolved "https://registry.yarnpkg.com/rlp/-/rlp-2.2.7.tgz#33f31c4afac81124ac4b283e2bd4d9720b30beaf" + integrity sha512-d5gdPmgQ0Z+AklL2NVXr/IoSjNZFfTVvQWzL/AM2AOcSzYP2xjlb0AC8YyCLc41MSNf6P6QVtjgPdmVtzb+4lQ== + dependencies: + bn.js "^5.2.0" + +run-parallel-limit@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/run-parallel-limit/-/run-parallel-limit-1.1.0.tgz#be80e936f5768623a38a963262d6bef8ff11e7ba" + integrity sha512-jJA7irRNM91jaKc3Hcl1npHsFLOXOoTkPCUL1JEa1R82O2miplXXRaGdjW/KM/98YQWDhJLiSs793CnXfblJUw== + dependencies: + queue-microtask "^1.2.2" + +run-parallel@^1.1.9: + version "1.2.0" + resolved "https://registry.yarnpkg.com/run-parallel/-/run-parallel-1.2.0.tgz#66d1368da7bdf921eb9d95bd1a9229e7f21a43ee" + integrity sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA== + dependencies: + queue-microtask "^1.2.2" + +rustbn.js@~0.2.0: + version "0.2.0" + resolved "https://registry.yarnpkg.com/rustbn.js/-/rustbn.js-0.2.0.tgz#8082cb886e707155fd1cb6f23bd591ab8d55d0ca" + integrity sha512-4VlvkRUuCJvr2J6Y0ImW7NvTCriMi7ErOAqWk1y69vAdoNIzCF3yPmgeNzx+RQTLEDFq5sHfscn1MwHxP9hNfA== + +safe-buffer@^5.0.1, safe-buffer@^5.1.0, safe-buffer@^5.1.1, safe-buffer@^5.1.2, safe-buffer@^5.2.0, safe-buffer@~5.2.0: + version "5.2.1" + resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6" + integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ== + +safe-buffer@~5.1.0, safe-buffer@~5.1.1: + version "5.1.2" + resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.1.2.tgz#991ec69d296e0313747d59bdfd2b745c35f8828d" + integrity sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g== + +"safer-buffer@>= 2.1.2 < 3", safer-buffer@~2.1.0: + version "2.1.2" + resolved "https://registry.yarnpkg.com/safer-buffer/-/safer-buffer-2.1.2.tgz#44fa161b0187b9549dd84bb91802f9bd8385cd6a" + integrity sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg== + +scrypt-js@3.0.1, scrypt-js@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/scrypt-js/-/scrypt-js-3.0.1.tgz#d314a57c2aef69d1ad98a138a21fe9eafa9ee312" + integrity sha512-cdwTTnqPu0Hyvf5in5asVdZocVDTNRmR7XEcJuIzMjJeSHybHl7vpB66AzwTaIg6CLSbtjcxc8fqcySfnTkccA== + +secp256k1@^4.0.1: + version "4.0.3" + resolved "https://registry.yarnpkg.com/secp256k1/-/secp256k1-4.0.3.tgz#c4559ecd1b8d3c1827ed2d1b94190d69ce267303" + integrity sha512-NLZVf+ROMxwtEj3Xa562qgv2BK5e2WNmXPiOdVIPLgs6lyTzMvBq0aWTYMI5XCP9jZMVKOcqZLw/Wc4vDkuxhA== + dependencies: + elliptic "^6.5.4" + node-addon-api "^2.0.0" + node-gyp-build "^4.2.0" + +semver@^5.5.0, semver@^5.6.0: + version "5.7.2" + resolved "https://registry.yarnpkg.com/semver/-/semver-5.7.2.tgz#48d55db737c3287cd4835e17fa13feace1c41ef8" + integrity sha512-cBznnQ9KjJqU67B52RMC65CMarK2600WFnbkcaiwWq3xy/5haFJlshgnpjovMVJ+Hff49d8GEn0b87C5pDQ10g== + +semver@^6.3.0: + version "6.3.1" + resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.1.tgz#556d2ef8689146e46dcea4bfdd095f3434dffcb4" + integrity sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA== + +semver@^7.3.8, semver@^7.5.1: + version "7.5.4" + resolved "https://registry.yarnpkg.com/semver/-/semver-7.5.4.tgz#483986ec4ed38e1c6c48c34894a9182dbff68a6e" + integrity sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA== + dependencies: + lru-cache "^6.0.0" + +serialize-javascript@6.0.0: + version "6.0.0" + resolved "https://registry.yarnpkg.com/serialize-javascript/-/serialize-javascript-6.0.0.tgz#efae5d88f45d7924141da8b5c3a7a7e663fefeb8" + integrity sha512-Qr3TosvguFt8ePWqsvRfrKyQXIiW+nGbYpy8XK24NQHE83caxWt+mIymTT19DGFbNWNLfEwsrkSmN64lVWB9ag== + dependencies: + randombytes "^2.1.0" + +setimmediate@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/setimmediate/-/setimmediate-1.0.5.tgz#290cbb232e306942d7d7ea9b83732ab7856f8285" + integrity sha512-MATJdZp8sLqDl/68LfQmbP8zKPLQNV6BIZoIgrscFDQ+RsvK/BxeDQOgyxKKoh0y/8h3BqVFnCqQ/gd+reiIXA== + +setprototypeof@1.2.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/setprototypeof/-/setprototypeof-1.2.0.tgz#66c9a24a73f9fc28cbe66b09fed3d33dcaf1b424" + integrity sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw== + +sha.js@^2.4.0, sha.js@^2.4.8: + version "2.4.11" + resolved "https://registry.yarnpkg.com/sha.js/-/sha.js-2.4.11.tgz#37a5cf0b81ecbc6943de109ba2960d1b26584ae7" + integrity sha512-QMEp5B7cftE7APOjk5Y6xgrbWu+WkLVQwk8JNjZ8nKRciZaByEW6MubieAiToS7+dwvrjGhH8jRXz3MVd0AYqQ== + dependencies: + inherits "^2.0.1" + safe-buffer "^5.0.1" + +signal-exit@^3.0.2: + version "3.0.7" + resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.7.tgz#a9a1767f8af84155114eaabd73f99273c8f59ad9" + integrity sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ== + +solc@0.7.3: + version "0.7.3" + resolved "https://registry.yarnpkg.com/solc/-/solc-0.7.3.tgz#04646961bd867a744f63d2b4e3c0701ffdc7d78a" + integrity sha512-GAsWNAjGzIDg7VxzP6mPjdurby3IkGCjQcM8GFYZT6RyaoUZKmMU6Y7YwG+tFGhv7dwZ8rmR4iwFDrrD99JwqA== + dependencies: + command-exists "^1.2.8" + commander "3.0.2" + follow-redirects "^1.12.1" + fs-extra "^0.30.0" + js-sha3 "0.8.0" + memorystream "^0.3.1" + require-from-string "^2.0.0" + semver "^5.5.0" + tmp "0.0.33" + +solidity-comments-extractor@^0.0.7: + version "0.0.7" + resolved "https://registry.yarnpkg.com/solidity-comments-extractor/-/solidity-comments-extractor-0.0.7.tgz#99d8f1361438f84019795d928b931f4e5c39ca19" + integrity sha512-wciNMLg/Irp8OKGrh3S2tfvZiZ0NEyILfcRCXCD4mp7SgK/i9gzLfhY2hY7VMCQJ3kH9UB9BzNdibIVMchzyYw== + +solpp@^0.11.5: + version "0.11.5" + resolved "https://registry.yarnpkg.com/solpp/-/solpp-0.11.5.tgz#e5f38b5acc952e1cc2e3871d490fdbed910938dd" + integrity sha512-LjzCGMrTDXtera2C4mbQGZSpBznP+o3/82L2CneAAMNbm+t4xPsvfrgJkIaY+IZ5YLrB8IXn7cYthwHMKvAWnQ== + dependencies: + antlr4 "~4.8.0" + axios "^0.21.1" + bn-str-256 "^1.9.1" + commander "^2.19.0" + ethereumjs-util "^6.0.0" + lodash "^4.17.11" + mz "^2.7.0" + resolve "^1.10.0" + semver "^5.6.0" + +source-map-support@^0.5.13: + version "0.5.21" + resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.5.21.tgz#04fe7c7f9e1ed2d662233c28cb2b35b9f63f6e4f" + integrity sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w== + dependencies: + buffer-from "^1.0.0" + source-map "^0.6.0" + +source-map@^0.6.0: + version "0.6.1" + resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.6.1.tgz#74722af32e9614e9c287a8d0bbde48b5e2f1a263" + integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g== + +split-ca@^1.0.0, split-ca@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/split-ca/-/split-ca-1.0.1.tgz#6c83aff3692fa61256e0cd197e05e9de157691a6" + integrity sha512-Q5thBSxp5t8WPTTJQS59LrGqOZqOsrhDGDVm8azCqIBjSBd7nd9o2PM+mDulQQkh8h//4U6hFZnc/mul8t5pWQ== + +ssh2@^1.11.0: + version "1.14.0" + resolved "https://registry.yarnpkg.com/ssh2/-/ssh2-1.14.0.tgz#8f68440e1b768b66942c9e4e4620b2725b3555bb" + integrity sha512-AqzD1UCqit8tbOKoj6ztDDi1ffJZ2rV2SwlgrVVrHPkV5vWqGJOVp5pmtj18PunkPJAuKQsnInyKV+/Nb2bUnA== + dependencies: + asn1 "^0.2.6" + bcrypt-pbkdf "^1.0.2" + optionalDependencies: + cpu-features "~0.0.8" + nan "^2.17.0" + +stacktrace-parser@^0.1.10: + version "0.1.10" + resolved "https://registry.yarnpkg.com/stacktrace-parser/-/stacktrace-parser-0.1.10.tgz#29fb0cae4e0d0b85155879402857a1639eb6051a" + integrity sha512-KJP1OCML99+8fhOHxwwzyWrlUuVX5GQ0ZpJTd1DFXhdkrvg1szxfHhawXUZ3g9TkXORQd4/WG68jMlQZ2p8wlg== + dependencies: + type-fest "^0.7.1" + +statuses@2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/statuses/-/statuses-2.0.1.tgz#55cb000ccf1d48728bd23c685a063998cf1a1b63" + integrity sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ== + +streamsearch@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/streamsearch/-/streamsearch-1.1.0.tgz#404dd1e2247ca94af554e841a8ef0eaa238da764" + integrity sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg== + +string-format@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/string-format/-/string-format-2.0.0.tgz#f2df2e7097440d3b65de31b6d40d54c96eaffb9b" + integrity sha512-bbEs3scLeYNXLecRRuk6uJxdXUSj6le/8rNPHChIJTn2V79aXVTR1EH2OH5zLKKoz0V02fOUKZZcw01pLUShZA== + +string-width@^4.1.0, string-width@^4.2.0: + version "4.2.3" + resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010" + integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g== + dependencies: + emoji-regex "^8.0.0" + is-fullwidth-code-point "^3.0.0" + strip-ansi "^6.0.1" + +string_decoder@^1.1.1: + version "1.3.0" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.3.0.tgz#42f114594a46cf1a8e30b0a84f56c78c3edac21e" + integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA== + dependencies: + safe-buffer "~5.2.0" + +string_decoder@~0.10.x: + version "0.10.31" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-0.10.31.tgz#62e203bc41766c6c28c9fc84301dab1c5310fa94" + integrity sha512-ev2QzSzWPYmy9GuqfIVildA4OdcGLeFZQrq5ys6RtiuF+RQQiZWr8TZNyAcuVXyQRYfEO+MsoB/1BuQVhOJuoQ== + +string_decoder@~1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.1.1.tgz#9cf1611ba62685d7030ae9e4ba34149c3af03fc8" + integrity sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg== + dependencies: + safe-buffer "~5.1.0" + +strip-ansi@^6.0.0, strip-ansi@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9" + integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A== + dependencies: + ansi-regex "^5.0.1" + +strip-hex-prefix@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/strip-hex-prefix/-/strip-hex-prefix-1.0.0.tgz#0c5f155fef1151373377de9dbb588da05500e36f" + integrity sha512-q8d4ue7JGEiVcypji1bALTos+0pWtyGlivAWyPuTkHzuTCJqrK9sWxYQZUq6Nq3cuyv3bm734IhHvHtGGURU6A== + dependencies: + is-hex-prefixed "1.0.0" + +strip-json-comments@3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-3.1.1.tgz#31f1281b3832630434831c310c01cccda8cbe006" + integrity sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig== + +supports-color@8.1.1: + version "8.1.1" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-8.1.1.tgz#cd6fc17e28500cff56c1b86c0a7fd4a54a73005c" + integrity sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q== + dependencies: + has-flag "^4.0.0" + +supports-color@^5.3.0: + version "5.5.0" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-5.5.0.tgz#e2e69a44ac8772f78a1ec0b35b689df6530efc8f" + integrity sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow== + dependencies: + has-flag "^3.0.0" + +supports-color@^7.1.0: + version "7.2.0" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-7.2.0.tgz#1b7dcdcb32b8138801b3e478ba6a51caa89648da" + integrity sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw== + dependencies: + has-flag "^4.0.0" + +supports-preserve-symlinks-flag@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz#6eda4bd344a3c94aea376d4cc31bc77311039e09" + integrity sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w== + +table-layout@^1.0.2: + version "1.0.2" + resolved "https://registry.yarnpkg.com/table-layout/-/table-layout-1.0.2.tgz#c4038a1853b0136d63365a734b6931cf4fad4a04" + integrity sha512-qd/R7n5rQTRFi+Zf2sk5XVVd9UQl6ZkduPFC3S7WEGJAmetDTjY3qPN50eSKzwuzEyQKy5TN2TiZdkIjos2L6A== + dependencies: + array-back "^4.0.1" + deep-extend "~0.6.0" + typical "^5.2.0" + wordwrapjs "^4.0.0" + +tar-fs@~1.16.3: + version "1.16.3" + resolved "https://registry.yarnpkg.com/tar-fs/-/tar-fs-1.16.3.tgz#966a628841da2c4010406a82167cbd5e0c72d509" + integrity sha512-NvCeXpYx7OsmOh8zIOP/ebG55zZmxLE0etfWRbWok+q2Qo8x/vOR/IJT1taADXPe+jsiu9axDb3X4B+iIgNlKw== + dependencies: + chownr "^1.0.1" + mkdirp "^0.5.1" + pump "^1.0.0" + tar-stream "^1.1.2" + +tar-fs@~2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/tar-fs/-/tar-fs-2.0.1.tgz#e44086c1c60d31a4f0cf893b1c4e155dabfae9e2" + integrity sha512-6tzWDMeroL87uF/+lin46k+Q+46rAJ0SyPGz7OW7wTgblI273hsBqk2C1j0/xNadNLKDTUL9BukSjB7cwgmlPA== + dependencies: + chownr "^1.1.1" + mkdirp-classic "^0.5.2" + pump "^3.0.0" + tar-stream "^2.0.0" + +tar-stream@^1.1.2: + version "1.6.2" + resolved "https://registry.yarnpkg.com/tar-stream/-/tar-stream-1.6.2.tgz#8ea55dab37972253d9a9af90fdcd559ae435c555" + integrity sha512-rzS0heiNf8Xn7/mpdSVVSMAWAoy9bfb1WOTYC78Z0UQKeKa/CWS8FOq0lKGNa8DWKAn9gxjCvMLYc5PGXYlK2A== + dependencies: + bl "^1.0.0" + buffer-alloc "^1.2.0" + end-of-stream "^1.0.0" + fs-constants "^1.0.0" + readable-stream "^2.3.0" + to-buffer "^1.1.1" + xtend "^4.0.0" + +tar-stream@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/tar-stream/-/tar-stream-2.2.0.tgz#acad84c284136b060dc3faa64474aa9aebd77287" + integrity sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ== + dependencies: + bl "^4.0.3" + end-of-stream "^1.4.1" + fs-constants "^1.0.0" + inherits "^2.0.3" + readable-stream "^3.1.1" + +template-file@^6.0.1: + version "6.0.1" + resolved "https://registry.yarnpkg.com/template-file/-/template-file-6.0.1.tgz#ce4d1f48e56d637cc94bb97ec205e6e035bbb2a5" + integrity sha512-02hOa1psJUOsahWfx8w3p40CCulA2/InNFFPh5xLq5rUUm2XTzvmtOn/SXV+KZaq7ylG58SYSnT4yW3y/Smn4w== + dependencies: + "@blakek/deep" "^2.2.0" + glob "^7.1.6" + mkdirp "^1.0.4" + p-limit "^4.0.0" + +thenify-all@^1.0.0: + version "1.6.0" + resolved "https://registry.yarnpkg.com/thenify-all/-/thenify-all-1.6.0.tgz#1a1918d402d8fc3f98fbf234db0bcc8cc10e9726" + integrity sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA== + dependencies: + thenify ">= 3.1.0 < 4" + +"thenify@>= 3.1.0 < 4": + version "3.3.1" + resolved "https://registry.yarnpkg.com/thenify/-/thenify-3.3.1.tgz#8932e686a4066038a016dd9e2ca46add9838a95f" + integrity sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw== + dependencies: + any-promise "^1.0.0" + +"through@>=2.2.7 <3": + version "2.3.8" + resolved "https://registry.yarnpkg.com/through/-/through-2.3.8.tgz#0dd4c9ffaabc357960b1b724115d7e0e86a2e1f5" + integrity sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg== + +tmp@0.0.33: + version "0.0.33" + resolved "https://registry.yarnpkg.com/tmp/-/tmp-0.0.33.tgz#6d34335889768d21b2bcda0aa277ced3b1bfadf9" + integrity sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw== + dependencies: + os-tmpdir "~1.0.2" + +to-buffer@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/to-buffer/-/to-buffer-1.1.1.tgz#493bd48f62d7c43fcded313a03dcadb2e1213a80" + integrity sha512-lx9B5iv7msuFYE3dytT+KE5tap+rNYw+K4jVkb9R/asAb+pbBSM17jtunHplhBe6RRJdZx3Pn2Jph24O32mOVg== + +to-regex-range@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/to-regex-range/-/to-regex-range-5.0.1.tgz#1648c44aae7c8d988a326018ed72f5b4dd0392e4" + integrity sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ== + dependencies: + is-number "^7.0.0" + +toidentifier@1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/toidentifier/-/toidentifier-1.0.1.tgz#3be34321a88a820ed1bd80dfaa33e479fbb8dd35" + integrity sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA== + +tr46@~0.0.3: + version "0.0.3" + resolved "https://registry.yarnpkg.com/tr46/-/tr46-0.0.3.tgz#8184fd347dac9cdc185992f3a6622e14b9d9ab6a" + integrity sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw== + +ts-command-line-args@^2.2.0: + version "2.5.1" + resolved "https://registry.yarnpkg.com/ts-command-line-args/-/ts-command-line-args-2.5.1.tgz#e64456b580d1d4f6d948824c274cf6fa5f45f7f0" + integrity sha512-H69ZwTw3rFHb5WYpQya40YAX2/w7Ut75uUECbgBIsLmM+BNuYnxsltfyyLMxy6sEeKxgijLTnQtLd0nKd6+IYw== + dependencies: + chalk "^4.1.0" + command-line-args "^5.1.1" + command-line-usage "^6.1.0" + string-format "^2.0.0" + +ts-essentials@^1.0.0: + version "1.0.4" + resolved "https://registry.yarnpkg.com/ts-essentials/-/ts-essentials-1.0.4.tgz#ce3b5dade5f5d97cf69889c11bf7d2da8555b15a" + integrity sha512-q3N1xS4vZpRouhYHDPwO0bDW3EZ6SK9CrrDHxi/D6BPReSjpVgWIOpLS2o0gSBZm+7q/wyKp6RVM1AeeW7uyfQ== + +ts-essentials@^7.0.1: + version "7.0.3" + resolved "https://registry.yarnpkg.com/ts-essentials/-/ts-essentials-7.0.3.tgz#686fd155a02133eedcc5362dc8b5056cde3e5a38" + integrity sha512-8+gr5+lqO3G84KdiTSMRLtuyJ+nTBVRKuCrK4lidMPdVeEp0uqC875uE5NMcaA7YYMN7XsNiFQuMvasF8HT/xQ== + +ts-generator@^0.1.1: + version "0.1.1" + resolved "https://registry.yarnpkg.com/ts-generator/-/ts-generator-0.1.1.tgz#af46f2fb88a6db1f9785977e9590e7bcd79220ab" + integrity sha512-N+ahhZxTLYu1HNTQetwWcx3so8hcYbkKBHTr4b4/YgObFTIKkOSSsaa+nal12w8mfrJAyzJfETXawbNjSfP2gQ== + dependencies: + "@types/mkdirp" "^0.5.2" + "@types/prettier" "^2.1.1" + "@types/resolve" "^0.0.8" + chalk "^2.4.1" + glob "^7.1.2" + mkdirp "^0.5.1" + prettier "^2.1.2" + resolve "^1.8.1" + ts-essentials "^1.0.0" + +ts-morph@^19.0.0: + version "19.0.0" + resolved "https://registry.yarnpkg.com/ts-morph/-/ts-morph-19.0.0.tgz#43e95fb0156c3fe3c77c814ac26b7d0be2f93169" + integrity sha512-D6qcpiJdn46tUqV45vr5UGM2dnIEuTGNxVhg0sk5NX11orcouwj6i1bMqZIz2mZTZB1Hcgy7C3oEVhAT+f6mbQ== + dependencies: + "@ts-morph/common" "~0.20.0" + code-block-writer "^12.0.0" + +ts-node@^10.7.0: + version "10.9.1" + resolved "https://registry.yarnpkg.com/ts-node/-/ts-node-10.9.1.tgz#e73de9102958af9e1f0b168a6ff320e25adcff4b" + integrity sha512-NtVysVPkxxrwFGUUxGYhfux8k78pQB3JqYBXlLRZgdGUqTO5wU/UyHop5p70iEbGhB7q5KmiZiU0Y3KlJrScEw== + dependencies: + "@cspotcode/source-map-support" "^0.8.0" + "@tsconfig/node10" "^1.0.7" + "@tsconfig/node12" "^1.0.7" + "@tsconfig/node14" "^1.0.0" + "@tsconfig/node16" "^1.0.2" + acorn "^8.4.1" + acorn-walk "^8.1.1" + arg "^4.1.0" + create-require "^1.1.0" + diff "^4.0.1" + make-error "^1.1.1" + v8-compile-cache-lib "^3.0.1" + yn "3.1.1" + +tslib@^1.9.3: + version "1.14.1" + resolved "https://registry.yarnpkg.com/tslib/-/tslib-1.14.1.tgz#cf2d38bdc34a134bcaf1091c41f6619e2f672d00" + integrity sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg== + +tsort@0.0.1: + version "0.0.1" + resolved "https://registry.yarnpkg.com/tsort/-/tsort-0.0.1.tgz#e2280f5e817f8bf4275657fd0f9aebd44f5a2786" + integrity sha512-Tyrf5mxF8Ofs1tNoxA13lFeZ2Zrbd6cKbuH3V+MQ5sb6DtBj5FjrXVsRWT8YvNAQTqNoz66dz1WsbigI22aEnw== + +tweetnacl-util@^0.15.1: + version "0.15.1" + resolved "https://registry.yarnpkg.com/tweetnacl-util/-/tweetnacl-util-0.15.1.tgz#b80fcdb5c97bcc508be18c44a4be50f022eea00b" + integrity sha512-RKJBIj8lySrShN4w6i/BonWp2Z/uxwC3h4y7xsRrpP59ZboCd0GpEVsOnMDYLMmKBpYhb5TgHzZXy7wTfYFBRw== + +tweetnacl@^0.14.3: + version "0.14.5" + resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-0.14.5.tgz#5ae68177f192d4456269d108afa93ff8743f4f64" + integrity sha512-KXXFFdAbFXY4geFIwoyNK+f5Z1b7swfXABfL7HXCmoIWMKU3dmS26672A4EeQtDzLKy7SXmfBu51JolvEKwtGA== + +tweetnacl@^1.0.3: + version "1.0.3" + resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-1.0.3.tgz#ac0af71680458d8a6378d0d0d050ab1407d35596" + integrity sha512-6rt+RN7aOi1nGMyC4Xa5DdYiukl2UWCbcJft7YhxReBGQD7OAM8Pbxw6YMo4r2diNEA8FEmu32YOn9rhaiE5yw== + +type-detect@^4.0.0, type-detect@^4.0.5: + version "4.0.8" + resolved "https://registry.yarnpkg.com/type-detect/-/type-detect-4.0.8.tgz#7646fb5f18871cfbb7749e69bd39a6388eb7450c" + integrity sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g== + +type-fest@^0.21.3: + version "0.21.3" + resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.21.3.tgz#d260a24b0198436e133fa26a524a6d65fa3b2e37" + integrity sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w== + +type-fest@^0.7.1: + version "0.7.1" + resolved "https://registry.yarnpkg.com/type-fest/-/type-fest-0.7.1.tgz#8dda65feaf03ed78f0a3f9678f1869147f7c5c48" + integrity sha512-Ne2YiiGN8bmrmJJEuTWTLJR32nh/JdL1+PSicowtNb0WFpn59GK8/lfD61bVtzguz7b3PBt74nxpv/Pw5po5Rg== + +typechain@^8.1.1: + version "8.3.1" + resolved "https://registry.yarnpkg.com/typechain/-/typechain-8.3.1.tgz#dccbc839b94877997536c356380eff7325395cfb" + integrity sha512-fA7clol2IP/56yq6vkMTR+4URF1nGjV82Wx6Rf09EsqD4tkzMAvEaqYxVFCavJm/1xaRga/oD55K+4FtuXwQOQ== + dependencies: + "@types/prettier" "^2.1.1" + debug "^4.3.1" + fs-extra "^7.0.0" + glob "7.1.7" + js-sha3 "^0.8.0" + lodash "^4.17.15" + mkdirp "^1.0.4" + prettier "^2.3.1" + ts-command-line-args "^2.2.0" + ts-essentials "^7.0.1" + +typedarray@^0.0.6: + version "0.0.6" + resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777" + integrity sha512-/aCDEGatGvZ2BIk+HmLf4ifCJFwvKFNb9/JeZPMulfgFracn9QFcAf5GO8B/mweUjSoblS5In0cWhqpfs/5PQA== + +typescript@^4.6.4: + version "4.9.5" + resolved "https://registry.yarnpkg.com/typescript/-/typescript-4.9.5.tgz#095979f9bcc0d09da324d58d03ce8f8374cbe65a" + integrity sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g== + +typical@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/typical/-/typical-4.0.0.tgz#cbeaff3b9d7ae1e2bbfaf5a4e6f11eccfde94fc4" + integrity sha512-VAH4IvQ7BDFYglMd7BPRDfLgxZZX4O4TFcRDA6EN5X7erNJJq+McIEp8np9aVtxrCJ6qx4GTYVfOWNjcqwZgRw== + +typical@^5.2.0: + version "5.2.0" + resolved "https://registry.yarnpkg.com/typical/-/typical-5.2.0.tgz#4daaac4f2b5315460804f0acf6cb69c52bb93066" + integrity sha512-dvdQgNDNJo+8B2uBQoqdb11eUCE1JQXhvjC/CZtgvZseVd5TYMXnq0+vuUemXbd/Se29cTaUuPX3YIc2xgbvIg== + +undici@^5.14.0: + version "5.24.0" + resolved "https://registry.yarnpkg.com/undici/-/undici-5.24.0.tgz#6133630372894cfeb3c3dab13b4c23866bd344b5" + integrity sha512-OKlckxBjFl0oXxcj9FU6oB8fDAaiRUq+D8jrFWGmOfI/gIyjk/IeS75LMzgYKUaeHzLUcYvf9bbJGSrUwTfwwQ== + dependencies: + busboy "^1.6.0" + +universalify@^0.1.0: + version "0.1.2" + resolved "https://registry.yarnpkg.com/universalify/-/universalify-0.1.2.tgz#b646f69be3942dabcecc9d6639c80dc105efaa66" + integrity sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg== + +universalify@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/universalify/-/universalify-2.0.0.tgz#75a4984efedc4b08975c5aeb73f530d02df25717" + integrity sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ== + +unpipe@1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/unpipe/-/unpipe-1.0.0.tgz#b2bf4ee8514aae6165b4817829d21b2ef49904ec" + integrity sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ== + +util-deprecate@^1.0.1, util-deprecate@~1.0.1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" + integrity sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw== + +uuid@^8.3.2: + version "8.3.2" + resolved "https://registry.yarnpkg.com/uuid/-/uuid-8.3.2.tgz#80d5b5ced271bb9af6c445f21a1a04c606cefbe2" + integrity sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg== + +v8-compile-cache-lib@^3.0.1: + version "3.0.1" + resolved "https://registry.yarnpkg.com/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz#6336e8d71965cb3d35a1bbb7868445a7c05264bf" + integrity sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg== + +webidl-conversions@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/webidl-conversions/-/webidl-conversions-3.0.1.tgz#24534275e2a7bc6be7bc86611cc16ae0a5654871" + integrity sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ== + +whatwg-url@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/whatwg-url/-/whatwg-url-5.0.0.tgz#966454e8765462e37644d3626f6742ce8b70965d" + integrity sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw== + dependencies: + tr46 "~0.0.3" + webidl-conversions "^3.0.0" + +wordwrapjs@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/wordwrapjs/-/wordwrapjs-4.0.1.tgz#d9790bccfb110a0fc7836b5ebce0937b37a8b98f" + integrity sha512-kKlNACbvHrkpIw6oPeYDSmdCTu2hdMHoyXLTcUKala++lx5Y+wjJ/e474Jqv5abnVmwxw08DiTuHmw69lJGksA== + dependencies: + reduce-flatten "^2.0.0" + typical "^5.2.0" + +workerpool@6.2.1: + version "6.2.1" + resolved "https://registry.yarnpkg.com/workerpool/-/workerpool-6.2.1.tgz#46fc150c17d826b86a008e5a4508656777e9c343" + integrity sha512-ILEIE97kDZvF9Wb9f6h5aXK4swSlKGUcOEGiIYb2OOu/IrDU9iwj0fD//SsA6E5ibwJxpEvhullJY4Sl4GcpAw== + +wrap-ansi@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43" + integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q== + dependencies: + ansi-styles "^4.0.0" + string-width "^4.1.0" + strip-ansi "^6.0.0" + +wrappy@1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" + integrity sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ== + +ws@7.4.6: + version "7.4.6" + resolved "https://registry.yarnpkg.com/ws/-/ws-7.4.6.tgz#5654ca8ecdeee47c33a9a4bf6d28e2be2980377c" + integrity sha512-YmhHDO4MzaDLB+M9ym/mDA5z0naX8j7SIlT8f8z+I0VtzsRbekxEutHSme7NPS2qE8StCYQNUnfWdXta/Yu85A== + +ws@^7.4.6: + version "7.5.9" + resolved "https://registry.yarnpkg.com/ws/-/ws-7.5.9.tgz#54fa7db29f4c7cec68b1ddd3a89de099942bb591" + integrity sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q== + +xregexp@3.1.0: + version "3.1.0" + resolved "https://registry.yarnpkg.com/xregexp/-/xregexp-3.1.0.tgz#14d8461e0bdd38224bfee5039a0898fc42fcd336" + integrity sha512-4Y1x6DyB8xRoxosooa6PlGWqmmSKatbzhrftZ7Purmm4B8R4qIEJG1A2hZsdz5DhmIqS0msC0I7KEq93GphEVg== + +xtend@^4.0.0: + version "4.0.2" + resolved "https://registry.yarnpkg.com/xtend/-/xtend-4.0.2.tgz#bb72779f5fa465186b1f438f674fa347fdb5db54" + integrity sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ== + +y18n@^5.0.5: + version "5.0.8" + resolved "https://registry.yarnpkg.com/y18n/-/y18n-5.0.8.tgz#7f4934d0f7ca8c56f95314939ddcd2dd91ce1d55" + integrity sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA== + +yallist@^3.0.2: + version "3.1.1" + resolved "https://registry.yarnpkg.com/yallist/-/yallist-3.1.1.tgz#dbb7daf9bfd8bac9ab45ebf602b8cbad0d5d08fd" + integrity sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g== + +yallist@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/yallist/-/yallist-4.0.0.tgz#9bb92790d9c0effec63be73519e11a35019a3a72" + integrity sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A== + +yargs-parser@20.2.4: + version "20.2.4" + resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.4.tgz#b42890f14566796f85ae8e3a25290d205f154a54" + integrity sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA== + +yargs-parser@^20.2.2: + version "20.2.9" + resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-20.2.9.tgz#2eb7dc3b0289718fc295f362753845c41a0c94ee" + integrity sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w== + +yargs-unparser@2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/yargs-unparser/-/yargs-unparser-2.0.0.tgz#f131f9226911ae5d9ad38c432fe809366c2325eb" + integrity sha512-7pRTIA9Qc1caZ0bZ6RYRGbHJthJWuakf+WmHK0rVeLkNrrGhfoabBNdue6kdINI6r4if7ocq9aD/n7xwKOdzOA== + dependencies: + camelcase "^6.0.0" + decamelize "^4.0.0" + flat "^5.0.2" + is-plain-obj "^2.1.0" + +yargs@16.2.0: + version "16.2.0" + resolved "https://registry.yarnpkg.com/yargs/-/yargs-16.2.0.tgz#1c82bf0f6b6a66eafce7ef30e376f49a12477f66" + integrity sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw== + dependencies: + cliui "^7.0.2" + escalade "^3.1.1" + get-caller-file "^2.0.5" + require-directory "^2.1.1" + string-width "^4.2.0" + y18n "^5.0.5" + yargs-parser "^20.2.2" + +yn@3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/yn/-/yn-3.1.1.tgz#1e87401a09d767c1d5eab26a6e4c185182d2eb50" + integrity sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q== + +yocto-queue@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-0.1.0.tgz#0294eb3dee05028d31ee1a5fa2c556a6aaf10a1b" + integrity sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q== + +yocto-queue@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-1.0.0.tgz#7f816433fb2cbc511ec8bf7d263c3b58a1a3c251" + integrity sha512-9bnSc/HEW2uRy67wc+T8UwauLuPJVn28jb+GtJY16iiKWyvmYJRXVT4UamsAEGQfPohgr2q4Tq0sQbQlxTfi1g== + +zksync-web3@^0.13.0: + version "0.13.4" + resolved "https://registry.yarnpkg.com/zksync-web3/-/zksync-web3-0.13.4.tgz#1c5b1303436cb4cba1a0873ea07860b19f385331" + integrity sha512-AjCKhn9TRqsk2T9VLKxlod22rnVWOWGOjq+QXppFe2yTxZx9dVaai325OJ0aa7a3m5wx+9yhPqBu23jG2xPo5Q== diff --git a/.test-node-subtree/rust-toolchain.toml b/.test-node-subtree/rust-toolchain.toml new file mode 100644 index 00000000..bc962f33 --- /dev/null +++ b/.test-node-subtree/rust-toolchain.toml @@ -0,0 +1,3 @@ +[toolchain] +channel = "nightly-2023-07-23" +components = ["rustfmt", "clippy"] \ No newline at end of file diff --git a/.test-node-subtree/scripts/execute-e2e-tests.sh b/.test-node-subtree/scripts/execute-e2e-tests.sh new file mode 100755 index 00000000..9fd9fd6d --- /dev/null +++ b/.test-node-subtree/scripts/execute-e2e-tests.sh @@ -0,0 +1,58 @@ +#!/bin/bash +set -e + +# Check if the node is running +MAX_RETRIES=10 +COUNTER=0 +URL="http://localhost:8011" + +# Payload +DATA='{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_chainId", + "params": [] +}' + +while [ $COUNTER -lt $MAX_RETRIES ]; do + # Send eth_chainId request + RESPONSE=$(curl -s -o /dev/null -w "%{http_code}" -X POST -H "content-type: application/json" -d "$DATA" $URL || true) + + # Check if the request was successful + if [ "$RESPONSE" -eq 200 ]; then + echo "Node is running! Starting tests..." + break + else + echo "Node not ready, retrying in 1 second..." + let COUNTER=COUNTER+1 + sleep 1 + fi +done + +if [ $COUNTER -eq $MAX_RETRIES ]; then + echo "Failed to contact node after $MAX_RETRIES attempts. Are you sure the node is running at $URL ?" + exit 1 +fi + +cd e2e-tests + +# Install dependencies +echo "" +echo "============" +echo "Yarn install" +echo "============" +yarn install --frozen-lockfile + +# Compile contracts +echo "" +echo "===================" +echo "Compiling contracts" +echo "===================" +yarn hardhat compile + +# Run tests +echo "" +echo "=================" +echo "Running e2e tests" +echo "=================" +yarn test diff --git a/.test-node-subtree/scripts/refresh_abi_map.py b/.test-node-subtree/scripts/refresh_abi_map.py new file mode 100644 index 00000000..a708ec26 --- /dev/null +++ b/.test-node-subtree/scripts/refresh_abi_map.py @@ -0,0 +1,21 @@ +import glob +import json +from eth_utils import function_abi_to_4byte_selector + +for file_path in glob.glob('*.json'): + with open(file_path, 'r') as file: + json_data = json.load(file) + + for function_abi in json_data["abi"]: + if function_abi["type"] != "function": + continue + function_name = function_abi['name'] + function_signature = function_abi_to_4byte_selector(function_abi).hex() + + inputs = function_abi.get('inputs', []) + arg_types = [input_data['type'] for input_data in inputs] + arg_string = ', '.join(arg_types) + + print( + f"[\"0x{function_signature}\", \"{function_name}({arg_string})\"]," + ) diff --git a/.test-node-subtree/scripts/refresh_contracts.sh b/.test-node-subtree/scripts/refresh_contracts.sh new file mode 100755 index 00000000..990bf5bf --- /dev/null +++ b/.test-node-subtree/scripts/refresh_contracts.sh @@ -0,0 +1,28 @@ +#!/bin/bash +set -xe + +SRC_DIR=etc/system-contracts/artifacts-zk/cache-zk/solpp-generated-contracts +DST_DIR=src/deps/contracts/ + +mkdir -p $DST_DIR + +contracts=("AccountCodeStorage" "BootloaderUtilities" "Compressor" "ComplexUpgrader" "ContractDeployer" "DefaultAccount" "DefaultAccountNoSecurity" "EmptyContract" "ImmutableSimulator" "KnownCodesStorage" "L1Messenger" "L2EthToken" "MsgValueSimulator" "NonceHolder" "SystemContext" ) + +for contract in "${contracts[@]}"; do + cp $SRC_DIR/$contract.sol/$contract.json $DST_DIR +done + +precompiles=("EcAdd" "EcMul" "EcPairing" "Ecrecover" "Keccak256" "ModExp" "P256VERIFY" "SHA256" "secp256k1VERIFY") + +for precompile in "${precompiles[@]}"; do + cp etc/system-contracts/contracts/precompiles/artifacts/$precompile.yul/$precompile.yul.zbin $DST_DIR +done + +cp etc/system-contracts/contracts/artifacts/EventWriter.yul/EventWriter.yul.zbin $DST_DIR + + +bootloaders=("fee_estimate" "gas_test" "playground_batch" "proved_batch" "proved_batch_impersonating" "fee_estimate_impersonating" ) + +for bootloader in "${bootloaders[@]}"; do + cp etc/system-contracts/bootloader/build/artifacts/$bootloader.yul/$bootloader.yul.zbin $DST_DIR +done diff --git a/.test-node-subtree/scripts/refresh_test_contracts.sh b/.test-node-subtree/scripts/refresh_test_contracts.sh new file mode 100755 index 00000000..10359f9c --- /dev/null +++ b/.test-node-subtree/scripts/refresh_test_contracts.sh @@ -0,0 +1,15 @@ +#!/usr/bin/env bash + +set -xe + +TEST_CONTRACT_ARTIFACTS="etc/test-contracts/artifacts-zk/cache-zk/solpp-generated-contracts" +TEST_CONTRACT_TARGET="src/deps/test-contracts" + +echo "Building test contracts" +(cd etc/test-contracts && yarn && yarn build) + +echo "Copying test contracts" +mkdir -p $TEST_CONTRACT_TARGET +find $TEST_CONTRACT_ARTIFACTS -name "*.json" ! -iname "*.dbg.json" -exec cp {} $TEST_CONTRACT_TARGET \; + +echo "Done" diff --git a/.test-node-subtree/src/bootloader_debug.rs b/.test-node-subtree/src/bootloader_debug.rs new file mode 100644 index 00000000..c83b9a80 --- /dev/null +++ b/.test-node-subtree/src/bootloader_debug.rs @@ -0,0 +1,136 @@ +use multivm::interface::{dyn_tracers::vm_1_4_0::DynTracer, tracer::VmExecutionStopReason}; +use std::sync::Arc; + +use multivm::vm_latest::{ + constants::BOOTLOADER_HEAP_PAGE, BootloaderState, HistoryMode, SimpleMemory, VmTracer, + ZkSyncVmState, +}; +use once_cell::sync::OnceCell; +use zksync_basic_types::U256; +use zksync_state::WriteStorage; + +/// Magic value that we put in bootloader.yul at the beginning of the debug section - to detect that +/// debugger was enabled. +const DEBUG_START_SENTINEL: u64 = 1337; + +const MAX_MEMORY_BYTES: usize = usize::pow(2, 24); + +const MAX_TRANSACTIONS: usize = 1024; +const RESULTS_BYTES_OFFSET: usize = MAX_MEMORY_BYTES - MAX_TRANSACTIONS * 32; + +const VM_HOOKS_PARAMS: usize = 2; + +const VM_HOOKS_START: usize = RESULTS_BYTES_OFFSET - (VM_HOOKS_PARAMS + 1) * 32; + +const DEBUG_SLOTS: usize = 32; +const DEBUG_START_BYTE: usize = VM_HOOKS_START - DEBUG_SLOTS * 32; + +const DEBUG_START_SLOT: usize = DEBUG_START_BYTE / 32; + +/// Struct that represents the additional debug information that we can get from bootloader. +/// Bootloader puts them in a special memory region after each transaction, and we can load them with this struct. + +#[derive(Debug, Clone)] +pub struct BootloaderDebug { + /// Amount of gas that user attached to the transaction. + pub total_gas_limit_from_user: U256, + /// If provided more gas than the system can support. (this 'reserved gas' will not be used and simply refunded at the end). + pub reserved_gas: U256, + /// Amount of gas that user has to pay for each pubdata byte. + pub gas_per_pubdata: U256, + /// Amount of gas left after intrinsic (block creation) fees. + pub gas_limit_after_intrinsic: U256, + /// Amount of gas left after account validation. + pub gas_after_validation: U256, + /// Amount of gas spent on actual function execution. + pub gas_spent_on_execution: U256, + + /// Gas spent on factory dependencies and bytecode preparation. + pub gas_spent_on_bytecode_preparation: U256, + + /// Amount of refund computed by the system. + pub refund_computed: U256, + /// Amount of refund provided by the operator (it might be larger than refund computed - for example due to pubdata compression). + pub refund_by_operator: U256, + + /// Fixed amount of gas for each transaction. + pub intrinsic_overhead: U256, + + /// Closing a block has a non-trivial cost for the operator (they have to run the prover, and commit results to L1). + /// That's why we have to judge how much a given transaction is contributing the operator closer to sealing the block. + + /// Cost of the whole block for the operator. + pub total_overhead_for_block: U256, + + /// The maximum amount that operator could have requested. + pub required_overhead: U256, + + /// How much did operator request for the block. + pub operator_overhead: U256, + + /// The amount of the overhead that circuits / gas are responsible for. + pub overhead_for_circuits: U256, + /// The amount of the overhead that transaction length it responsible for. + pub overhead_for_length: U256, + /// The amount of the overhead that simply using a slot of the block is responsible for. + pub overhead_for_slot: U256, +} + +/// The role of this tracer is to read the memory slots directly from bootloader memory at +/// the end of VM execution - and put them into BootloaderDebug object. +pub struct BootloaderDebugTracer { + pub result: Arc>>, +} + +impl DynTracer> for BootloaderDebugTracer {} + +fn load_debug_slot(memory: &SimpleMemory, slot: usize) -> U256 { + memory + .read_slot(BOOTLOADER_HEAP_PAGE as usize, DEBUG_START_SLOT + slot) + .value +} + +impl VmTracer for BootloaderDebugTracer { + fn after_vm_execution( + &mut self, + state: &mut ZkSyncVmState, + _bootloader_state: &BootloaderState, + _stop_reason: VmExecutionStopReason, + ) { + self.result + .set(BootloaderDebug::load_from_memory(&state.memory)) + .unwrap(); + } +} + +impl BootloaderDebug { + pub fn load_from_memory( + memory: &SimpleMemory, + ) -> eyre::Result { + if load_debug_slot(memory, 0) != U256::from(DEBUG_START_SENTINEL) { + Err( + "Debug slot has wrong value. Probably bootloader slot mapping has changed." + .to_owned(), + ) + } else { + Ok(BootloaderDebug { + total_gas_limit_from_user: load_debug_slot(memory, 1), + reserved_gas: load_debug_slot(memory, 2), + gas_per_pubdata: load_debug_slot(memory, 3), + gas_limit_after_intrinsic: load_debug_slot(memory, 4), + gas_after_validation: load_debug_slot(memory, 5), + gas_spent_on_execution: load_debug_slot(memory, 6), + gas_spent_on_bytecode_preparation: load_debug_slot(memory, 7), + refund_computed: load_debug_slot(memory, 8), + refund_by_operator: load_debug_slot(memory, 9), + intrinsic_overhead: load_debug_slot(memory, 10), + operator_overhead: load_debug_slot(memory, 11), + required_overhead: load_debug_slot(memory, 12), + total_overhead_for_block: load_debug_slot(memory, 13), + overhead_for_circuits: load_debug_slot(memory, 14), + overhead_for_length: load_debug_slot(memory, 15), + overhead_for_slot: load_debug_slot(memory, 16), + }) + } + } +} diff --git a/.test-node-subtree/src/cache.rs b/.test-node-subtree/src/cache.rs new file mode 100644 index 00000000..713bc850 --- /dev/null +++ b/.test-node-subtree/src/cache.rs @@ -0,0 +1,669 @@ +use rustc_hash::FxHashMap; +use serde::Serialize; +use std::fs; +use std::fs::File; +use std::io::{BufReader, BufWriter}; +use std::path::Path; +use std::result::Result; +use std::str::FromStr; +use zksync_basic_types::H256; +use zksync_types::api::{Block, BridgeAddresses, Transaction, TransactionVariant}; +use zksync_types::Transaction as RawTransaction; + +/// Caches full blocks by their hashes +const CACHE_TYPE_BLOCKS_FULL: &str = "blocks_full"; +/// Caches minimal blocks by their hashes +const CACHE_TYPE_BLOCKS_MIN: &str = "blocks_min"; +/// Caches raw transactions by their hashes +const CACHE_TYPE_BLOCK_RAW_TRANSACTIONS: &str = "block_raw_transactions"; +/// Caches transactions by their hashes +const CACHE_TYPE_TRANSACTIONS: &str = "transactions"; +/// Caches arbitrary values by their keys +const CACHE_TYPE_KEY_VALUE: &str = "key_value"; + +/// Caching key for bridge addresses +const CACHE_KEY_BRIDGE_ADDRESSES: &str = "bridge_addresses"; + +/// Cache configuration. Can be one of: +/// +/// None : Caching is disabled +/// Memory : Caching is provided in-memory and not persisted across runs +/// Disk : Caching is persisted on disk in the provided directory and can be reset +#[derive(Default, Debug, Clone)] +pub enum CacheConfig { + #[default] + None, + Memory, + Disk { + dir: String, + reset: bool, + }, +} + +/// A general purpose cache. +#[derive(Default, Debug, Clone)] +pub(crate) struct Cache { + config: CacheConfig, + block_hashes: FxHashMap, + blocks_full: FxHashMap>, + blocks_min: FxHashMap>, + block_raw_transactions: FxHashMap>, + transactions: FxHashMap, + bridge_addresses: Option, + confirmed_tokens: FxHashMap<(u32, u8), Vec>, +} + +impl Cache { + /// Creates a new cache with the provided config. + pub(crate) fn new(config: CacheConfig) -> Self { + let mut cache = Cache { + config: config.clone(), + ..Default::default() + }; + + if let CacheConfig::Disk { dir, reset } = &config { + if *reset { + for cache_type in [ + CACHE_TYPE_BLOCKS_FULL, + CACHE_TYPE_BLOCKS_MIN, + CACHE_TYPE_BLOCK_RAW_TRANSACTIONS, + CACHE_TYPE_TRANSACTIONS, + CACHE_TYPE_KEY_VALUE, + ] { + fs::remove_dir_all(Path::new(dir).join(cache_type)).unwrap_or_else(|err| { + tracing::warn!( + "failed removing directory {:?}: {:?}", + Path::new(dir).join(cache_type), + err + ) + }); + } + + fs::remove_dir(Path::new(dir)).unwrap_or_else(|err| { + tracing::warn!("failed removing cache directory: {:?}", err) + }); + } + + for cache_type in [ + CACHE_TYPE_BLOCKS_FULL, + CACHE_TYPE_BLOCKS_MIN, + CACHE_TYPE_BLOCK_RAW_TRANSACTIONS, + CACHE_TYPE_TRANSACTIONS, + CACHE_TYPE_KEY_VALUE, + ] { + fs::create_dir_all(Path::new(dir).join(cache_type)).unwrap_or_else(|err| { + panic!("failed creating directory {}: {:?}", cache_type, err) + }); + } + cache + .read_all_from_disk(dir) + .unwrap_or_else(|err| tracing::error!("failed reading cache from disk: {:?}", err)); + } + + cache + } + + /// Returns the cached full/minimal block for the provided hash. + pub(crate) fn get_block( + &self, + hash: &H256, + full_transactions: bool, + ) -> Option<&Block> { + if matches!(self.config, CacheConfig::None) { + return None; + } + + if full_transactions { + self.blocks_full.get(hash) + } else { + self.blocks_min.get(hash) + } + } + + /// Cache a full/minimal block for the provided hash. + pub(crate) fn insert_block( + &mut self, + hash: H256, + full_transactions: bool, + block: Block, + ) { + if matches!(self.config, CacheConfig::None) { + return; + } + + self.block_hashes.insert(block.number.as_u64(), block.hash); + if full_transactions { + self.write_to_disk(CACHE_TYPE_BLOCKS_FULL, format!("{:#x}", hash), &block); + self.blocks_full.insert(hash, block); + } else { + self.write_to_disk(CACHE_TYPE_BLOCKS_MIN, format!("{:#x}", hash), &block); + self.blocks_min.insert(hash, block); + } + } + + /// Returns the cached full/minimal block for the provided hash. + pub(crate) fn get_block_hash(&self, number: &u64) -> Option<&H256> { + if matches!(self.config, CacheConfig::None) { + return None; + } + + self.block_hashes.get(number) + } + + /// Returns the cached raw transactions for the provided block number. + pub(crate) fn get_block_raw_transactions(&self, number: &u64) -> Option<&Vec> { + if matches!(self.config, CacheConfig::None) { + return None; + } + + self.block_raw_transactions.get(number) + } + + /// Returns the cached confirmed tokens. + pub(crate) fn get_confirmed_tokens( + &self, + from: u32, + limit: u8, + ) -> Option<&Vec> { + if matches!(self.config, CacheConfig::None) { + return None; + } + self.confirmed_tokens.get(&(from, limit)) + } + + /// Cache confirmed tokens + pub(crate) fn set_confirmed_tokens( + &mut self, + from: u32, + limit: u8, + confirmed_tokens: Vec, + ) { + if matches!(self.config, CacheConfig::None) { + return; + } + self.confirmed_tokens + .insert((from, limit), confirmed_tokens); + } + + /// Cache the raw transactions for the provided block number. + pub(crate) fn insert_block_raw_transactions( + &mut self, + number: u64, + transactions: Vec, + ) { + if matches!(self.config, CacheConfig::None) { + return; + } + + self.write_to_disk( + CACHE_TYPE_BLOCK_RAW_TRANSACTIONS, + format!("{}", number), + &transactions, + ); + self.block_raw_transactions.insert(number, transactions); + } + + /// Returns the cached transaction for the provided hash. + pub(crate) fn get_transaction(&self, hash: &H256) -> Option<&Transaction> { + if matches!(self.config, CacheConfig::None) { + return None; + } + + self.transactions.get(hash) + } + + /// Cache a transaction for the provided hash. + pub(crate) fn insert_transaction(&mut self, hash: H256, transaction: Transaction) { + if matches!(self.config, CacheConfig::None) { + return; + } + + self.write_to_disk( + CACHE_TYPE_TRANSACTIONS, + format!("{:#x}", hash), + &transaction, + ); + self.transactions.insert(hash, transaction); + } + + /// Returns the cached bridge addresses for the provided hash. + pub(crate) fn get_bridge_addresses(&self) -> Option<&BridgeAddresses> { + if matches!(self.config, CacheConfig::None) { + return None; + } + + self.bridge_addresses.as_ref() + } + + /// Cache default bridge addresses. + pub(crate) fn set_bridge_addresses(&mut self, bridge_addresses: BridgeAddresses) { + if matches!(self.config, CacheConfig::None) { + return; + } + + self.write_to_disk( + CACHE_TYPE_KEY_VALUE, + String::from(CACHE_KEY_BRIDGE_ADDRESSES), + &bridge_addresses, + ); + self.bridge_addresses = Some(bridge_addresses); + } + + /// Reads the cache contents from the disk, if available. + fn read_all_from_disk(&mut self, dir: &str) -> Result<(), String> { + for cache_type in [ + CACHE_TYPE_BLOCKS_FULL, + CACHE_TYPE_BLOCKS_MIN, + CACHE_TYPE_BLOCK_RAW_TRANSACTIONS, + CACHE_TYPE_TRANSACTIONS, + CACHE_TYPE_KEY_VALUE, + ] { + let cache_dir = Path::new(dir).join(cache_type); + let dir_listing = fs::read_dir(cache_dir.clone()) + .map_err(|err| format!("failed reading dir '{:?}': {:?}", cache_dir, err))? + .flatten(); + for file in dir_listing { + let key = file + .file_name() + .to_str() + .ok_or_else(|| String::from("failed converting filename to string"))? + .to_string(); + + let cache_file = File::open(file.path()).map_err(|err| { + format!("failed reading file: '{:?}': {:?}", file.path(), err) + })?; + let reader = BufReader::new(cache_file); + match cache_type { + CACHE_TYPE_BLOCKS_FULL => { + let key = H256::from_str(&key).map_err(|err| { + format!("invalid key for cache file '{:?}': {:?}", key, err) + })?; + let block: Block = serde_json::from_reader(reader) + .map_err(|err| { + format!("failed parsing json for cache file '{:?}': {:?}", key, err) + })?; + self.block_hashes.insert(block.number.as_u64(), block.hash); + self.blocks_full.insert(key, block); + } + CACHE_TYPE_BLOCKS_MIN => { + let key = H256::from_str(&key).map_err(|err| { + format!("invalid key for cache file '{:?}': {:?}", key, err) + })?; + let block: Block = serde_json::from_reader(reader) + .map_err(|err| { + format!("failed parsing json for cache file '{:?}': {:?}", key, err) + })?; + self.block_hashes.insert(block.number.as_u64(), block.hash); + self.blocks_min.insert(key, block); + } + CACHE_TYPE_BLOCK_RAW_TRANSACTIONS => { + let key = key.parse::().map_err(|err| { + format!("invalid key for cache file '{:?}': {:?}", key, err) + })?; + let transactions: Vec = serde_json::from_reader(reader) + .map_err(|err| { + format!("failed parsing json for cache file '{:?}': {:?}", key, err) + })?; + self.block_raw_transactions.insert(key, transactions); + } + CACHE_TYPE_TRANSACTIONS => { + let key = H256::from_str(&key).map_err(|err| { + format!("invalid key for cache file '{:?}': {:?}", key, err) + })?; + let transaction: Transaction = + serde_json::from_reader(reader).map_err(|err| { + format!("failed parsing json for cache file '{:?}': {:?}", key, err) + })?; + self.transactions.insert(key, transaction); + } + CACHE_TYPE_KEY_VALUE => match key.as_str() { + CACHE_KEY_BRIDGE_ADDRESSES => { + self.bridge_addresses = + Some(serde_json::from_reader(reader).map_err(|err| { + format!( + "failed parsing json for cache file '{:?}': {:?}", + key, err + ) + })?); + } + _ => return Err(format!("invalid cache_type_value key {}", cache_type)), + }, + _ => return Err(format!("invalid cache_type {}", cache_type)), + } + } + } + + Ok(()) + } + + /// Writes the cache contents to disk, if supported. + fn write_to_disk(&self, cache_type: &'static str, key: String, data: &T) { + if let CacheConfig::Disk { dir, .. } = &self.config { + let file = Path::new(&dir).join(cache_type).join(key); + + tracing::debug!("writing cache {:?}", file); + match File::create(file.clone()) { + Ok(cache_file) => { + let writer = BufWriter::new(cache_file); + if let Err(err) = serde_json::to_writer(writer, data) { + tracing::error!("failed writing to cache '{:?}': {:?}", file, err); + } + } + Err(err) => tracing::error!("failed creating file: '{:?}': {:?}", file, err), + } + } + } +} + +#[cfg(test)] +mod tests { + use tempdir::TempDir; + use zksync_basic_types::{H160, U64}; + use zksync_types::{Execute, ExecuteTransactionCommon}; + + use crate::testing; + + use super::*; + + #[test] + fn test_cache_config_none_disables_cache() { + let mut cache = Cache::new(CacheConfig::None); + + cache.insert_block(H256::zero(), true, Default::default()); + assert_eq!(None, cache.get_block(&H256::zero(), true)); + assert_eq!(None, cache.get_block_hash(&0)); + + cache.insert_block(H256::zero(), false, Default::default()); + assert_eq!(None, cache.get_block(&H256::zero(), false)); + assert_eq!(None, cache.get_block_hash(&0)); + + cache.insert_block_raw_transactions(0, Default::default()); + assert_eq!(None, cache.get_block_raw_transactions(&0)); + + cache.insert_transaction(H256::zero(), Default::default()); + assert_eq!(None, cache.get_transaction(&H256::zero())); + } + + #[test] + fn test_cache_config_memory_enables_cache() { + let block_full = Block:: { + hash: H256::repeat_byte(0x1), + number: U64::from(1), + ..Default::default() + }; + let block_min = Block:: { + hash: H256::repeat_byte(0x2), + number: U64::from(2), + ..Default::default() + }; + let transaction = Transaction::default(); + let raw_transactions = vec![RawTransaction { + common_data: ExecuteTransactionCommon::L1(Default::default()), + execute: Execute { + calldata: Default::default(), + contract_address: Default::default(), + factory_deps: None, + value: Default::default(), + }, + received_timestamp_ms: 0, + raw_bytes: None, + }]; + let bridge_addresses = BridgeAddresses { + l1_erc20_default_bridge: H160::repeat_byte(0x1), + l2_erc20_default_bridge: H160::repeat_byte(0x2), + l1_weth_bridge: Some(H160::repeat_byte(0x3)), + l2_weth_bridge: Some(H160::repeat_byte(0x4)), + }; + + let mut cache = Cache::new(CacheConfig::Memory); + + cache.insert_block(block_full.hash, true, block_full.clone()); + assert_eq!( + Some(&block_full), + cache.get_block(&H256::repeat_byte(0x1), true) + ); + assert_eq!(Some(&H256::repeat_byte(0x1)), cache.get_block_hash(&1)); + + cache.insert_block(block_min.hash, false, block_min.clone()); + assert_eq!( + Some(&block_min), + cache.get_block(&H256::repeat_byte(0x2), false) + ); + assert_eq!(Some(&H256::repeat_byte(0x2)), cache.get_block_hash(&2)); + + cache.insert_block_raw_transactions(0, raw_transactions.clone()); + assert_eq!( + Some(&raw_transactions), + cache.get_block_raw_transactions(&0) + ); + + cache.insert_transaction(H256::zero(), transaction.clone()); + assert_eq!(Some(&transaction), cache.get_transaction(&H256::zero())); + + cache.set_bridge_addresses(bridge_addresses.clone()); + testing::assert_bridge_addresses_eq( + &bridge_addresses, + cache.get_bridge_addresses().expect("expected addresses"), + ); + } + + #[test] + fn test_cache_config_disk_enables_cache_and_preserves_it_to_disk() { + let block_full = Block:: { + hash: H256::repeat_byte(0x1), + number: U64::from(1), + ..Default::default() + }; + let block_min = Block:: { + hash: H256::repeat_byte(0x2), + number: U64::from(2), + ..Default::default() + }; + let transaction = Transaction::default(); + let raw_transactions = vec![RawTransaction { + common_data: ExecuteTransactionCommon::L1(Default::default()), + execute: Execute { + calldata: Default::default(), + contract_address: Default::default(), + factory_deps: None, + value: Default::default(), + }, + received_timestamp_ms: 0, + raw_bytes: None, + }]; + let bridge_addresses = BridgeAddresses { + l1_erc20_default_bridge: H160::repeat_byte(0x1), + l2_erc20_default_bridge: H160::repeat_byte(0x2), + l1_weth_bridge: Some(H160::repeat_byte(0x3)), + l2_weth_bridge: Some(H160::repeat_byte(0x4)), + }; + + let cache_dir = TempDir::new("cache-test").expect("failed creating temporary dir"); + let cache_dir_path = cache_dir + .path() + .to_str() + .expect("invalid dir name") + .to_string(); + let mut cache = Cache::new(CacheConfig::Disk { + dir: cache_dir_path.clone(), + reset: true, + }); + + cache.insert_block(block_full.hash, true, block_full.clone()); + assert_eq!( + Some(&block_full), + cache.get_block(&H256::repeat_byte(0x1), true) + ); + assert_eq!(Some(&H256::repeat_byte(0x1)), cache.get_block_hash(&1)); + + cache.insert_block(block_min.hash, false, block_min.clone()); + assert_eq!( + Some(&block_min), + cache.get_block(&H256::repeat_byte(0x2), false) + ); + assert_eq!(Some(&H256::repeat_byte(0x2)), cache.get_block_hash(&2)); + + cache.insert_block_raw_transactions(0, raw_transactions.clone()); + assert_eq!( + Some(&raw_transactions), + cache.get_block_raw_transactions(&0) + ); + + cache.insert_transaction(H256::zero(), transaction.clone()); + assert_eq!(Some(&transaction), cache.get_transaction(&H256::zero())); + + cache.set_bridge_addresses(bridge_addresses.clone()); + testing::assert_bridge_addresses_eq( + &bridge_addresses, + cache.get_bridge_addresses().expect("expected addresses"), + ); + + let new_cache = Cache::new(CacheConfig::Disk { + dir: cache_dir_path, + reset: false, + }); + assert_eq!( + Some(&block_full), + new_cache.get_block(&H256::repeat_byte(0x1), true) + ); + assert_eq!(Some(&H256::repeat_byte(0x1)), new_cache.get_block_hash(&1)); + assert_eq!( + Some(&block_min), + new_cache.get_block(&H256::repeat_byte(0x2), false) + ); + assert_eq!(Some(&H256::repeat_byte(0x2)), new_cache.get_block_hash(&2)); + assert_eq!( + Some(&raw_transactions), + new_cache.get_block_raw_transactions(&0) + ); + assert_eq!(Some(&transaction), new_cache.get_transaction(&H256::zero())); + testing::assert_bridge_addresses_eq( + &bridge_addresses, + new_cache + .get_bridge_addresses() + .expect("expected addresses"), + ); + } + + #[test] + fn test_cache_config_disk_enables_cache_and_can_reset_data_on_disk() { + let block_full = Block:: { + hash: H256::repeat_byte(0x1), + number: U64::from(1), + ..Default::default() + }; + let block_min = Block:: { + hash: H256::repeat_byte(0x2), + number: U64::from(2), + ..Default::default() + }; + let transaction = Transaction::default(); + let raw_transactions = vec![RawTransaction { + common_data: ExecuteTransactionCommon::L1(Default::default()), + execute: Execute { + calldata: Default::default(), + contract_address: Default::default(), + factory_deps: None, + value: Default::default(), + }, + received_timestamp_ms: 0, + raw_bytes: None, + }]; + let bridge_addresses = BridgeAddresses { + l1_erc20_default_bridge: H160::repeat_byte(0x1), + l2_erc20_default_bridge: H160::repeat_byte(0x2), + l1_weth_bridge: Some(H160::repeat_byte(0x3)), + l2_weth_bridge: Some(H160::repeat_byte(0x4)), + }; + + let cache_dir = TempDir::new("cache-test").expect("failed creating temporary dir"); + let cache_dir_path = cache_dir + .path() + .to_str() + .expect("invalid dir name") + .to_string(); + let mut cache = Cache::new(CacheConfig::Disk { + dir: cache_dir_path.clone(), + reset: true, + }); + + cache.insert_block(block_full.hash, true, block_full.clone()); + assert_eq!( + Some(&block_full), + cache.get_block(&H256::repeat_byte(0x1), true) + ); + assert_eq!(Some(&H256::repeat_byte(0x1)), cache.get_block_hash(&1)); + + cache.insert_block(block_min.hash, false, block_min.clone()); + assert_eq!( + Some(&block_min), + cache.get_block(&H256::repeat_byte(0x2), false) + ); + assert_eq!(Some(&H256::repeat_byte(0x2)), cache.get_block_hash(&2)); + + cache.insert_block_raw_transactions(0, raw_transactions.clone()); + assert_eq!( + Some(&raw_transactions), + cache.get_block_raw_transactions(&0) + ); + + cache.insert_transaction(H256::zero(), transaction.clone()); + assert_eq!(Some(&transaction), cache.get_transaction(&H256::zero())); + + cache.set_bridge_addresses(bridge_addresses.clone()); + testing::assert_bridge_addresses_eq( + &bridge_addresses, + cache.get_bridge_addresses().expect("expected addresses"), + ); + + let new_cache = Cache::new(CacheConfig::Disk { + dir: cache_dir_path, + reset: true, + }); + assert_eq!(None, new_cache.get_block(&H256::zero(), true)); + assert_eq!(None, new_cache.get_block_hash(&1)); + assert_eq!(None, new_cache.get_block(&H256::zero(), false)); + assert_eq!(None, new_cache.get_block_hash(&2)); + assert_eq!(None, new_cache.get_block_raw_transactions(&0)); + assert_eq!(None, new_cache.get_transaction(&H256::zero())); + assert!(new_cache.get_bridge_addresses().is_none()); + } + + #[test] + fn test_cache_config_disk_only_resets_created_data_on_disk() { + let cache_dir = TempDir::new("cache-test").expect("failed creating temporary dir"); + let cache_dir_path = cache_dir + .path() + .to_str() + .expect("invalid dir name") + .to_string(); + let mut cache = Cache::new(CacheConfig::Disk { + dir: cache_dir_path.clone(), + reset: true, + }); + + cache.insert_transaction(H256::zero(), Default::default()); + let cached_tx_file = cache_dir + .path() + .join(CACHE_TYPE_TRANSACTIONS) + .join(format!("{:#x}", H256::zero())); + assert!( + cached_tx_file.exists(), + "cached transaction did not exist on disk" + ); + + let random_file_path = cache_dir.path().join("foobar.txt"); + _ = File::create(&random_file_path).expect("failed creating random file"); + + Cache::new(CacheConfig::Disk { + dir: cache_dir_path, + reset: true, + }); + + assert!( + !cached_tx_file.exists(), + "cached transaction was not reset on disk" + ); + assert!(random_file_path.exists(), "random file was reset from disk"); + } +} diff --git a/.test-node-subtree/src/console_log.rs b/.test-node-subtree/src/console_log.rs new file mode 100644 index 00000000..b6ef9bfc --- /dev/null +++ b/.test-node-subtree/src/console_log.rs @@ -0,0 +1,492 @@ +use std::{collections::HashMap, str::FromStr}; + +use colored::Colorize; +use ethabi::param_type::Reader; +use ethabi::{Function, Param, StateMutability}; +use itertools::Itertools; +use zksync_types::vm_trace::Call; +use zksync_types::H160; + +/// ConsoleLogHandler is responsible for printing the logs, that are created when contract calls 'console.log' method. +/// This is a popular debugging method used by hardhat and foundry. +/// When user wants to log something, these tools are doing a call to a contract at a given (fake) address. +/// The ConsoleLogHandler is catching this call, and printing it out -- but only if TRACE level log is enabled for 'console' target. +#[derive(Debug, Clone)] +pub struct ConsoleLogHandler { + /// Map from the 4-byte function signature to function itself. + // This contract has many 'log' methods (depending on argument type) - so we have a map here, to be able to parse the arguments. + signature_map: HashMap<[u8; 4], Function>, + /// The 'fake' hardcoded contract, whose calls with have to log. + target_contract: H160, +} + +pub const CONSOLE_ADDRESS: &str = "0x000000000000000000636f6e736f6c652e6c6f67"; + +impl Default for ConsoleLogHandler { + fn default() -> Self { + Self { + signature_map: get_log_functions() + .into_iter() + .map(|func| (func.short_signature(), func)) + .collect::>(), + target_contract: H160::from_str(CONSOLE_ADDRESS).unwrap(), + } + } +} + +impl ConsoleLogHandler { + pub fn handle_call_recursive(&self, current_call: &Call) { + self.handle_call(current_call); + for call in ¤t_call.calls { + self.handle_call_recursive(call); + } + } + pub fn handle_call(&self, current_call: &Call) { + if current_call.to != self.target_contract { + return; + } + if current_call.input.len() < 4 { + return; + } + let signature = ¤t_call.input[..4]; + let message = + self.signature_map + .get(signature) + .map_or("Unknown log call.".to_owned(), |func| { + let tokens = func.decode_input(¤t_call.input.as_slice()[4..]); + + tokens.map_or("Failed to parse inputs for log.".to_owned(), |tokens| { + tokens.iter().map(|t| format!("{}", t)).join(" ") + }) + }); + tracing::info!("{}", message.cyan()); + } +} + +/// Returns the well-known log [Function]s. +fn get_log_functions() -> Vec { + LOG_FUNCTIONS + .iter() + .map(|func_decl| { + let (name, params) = func_decl + .trim_end_matches(')') + .split_once('(') + .unwrap_or_else(|| panic!("unable to obtain function name for '{}'", func_decl)); + + #[allow(deprecated)] // for deprecated field `constant` + Function { + name: String::from(name), + inputs: params + .split(',') + .enumerate() + .map(|(index, param)| Param { + name: format!("p{index}"), + kind: Reader::read(param).unwrap_or_else(|err| { + panic!( + "failed deserializing type '{}' for '{}' : {:?}", + param, func_decl, err + ) + }), + internal_type: Some(String::from(param)), + }) + .collect(), + outputs: vec![], + constant: false, + state_mutability: StateMutability::View, + } + }) + .collect() +} + +/// Represents the common log functions. +/// See https://github.com/NomicFoundation/hardhat/blob/main/packages/hardhat-core/console.sol +const LOG_FUNCTIONS: [&str; 378] = [ + "log(int256)", + "log(uint256)", + "log(string)", + "log(bool)", + "log(address)", + "log(bytes)", + "log(bytes1)", + "log(bytes2)", + "log(bytes3)", + "log(bytes4)", + "log(bytes5)", + "log(bytes6)", + "log(bytes7)", + "log(bytes8)", + "log(bytes9)", + "log(bytes10)", + "log(bytes11)", + "log(bytes12)", + "log(bytes13)", + "log(bytes14)", + "log(bytes15)", + "log(bytes16)", + "log(bytes17)", + "log(bytes18)", + "log(bytes19)", + "log(bytes20)", + "log(bytes21)", + "log(bytes22)", + "log(bytes23)", + "log(bytes24)", + "log(bytes25)", + "log(bytes26)", + "log(bytes27)", + "log(bytes28)", + "log(bytes29)", + "log(bytes30)", + "log(bytes31)", + "log(bytes32)", + "log(uint256)", + "log(string)", + "log(bool)", + "log(address)", + "log(uint256,uint256)", + "log(uint256,string)", + "log(uint256,bool)", + "log(uint256,address)", + "log(string,uint256)", + "log(string,string)", + "log(string,bool)", + "log(string,address)", + "log(bool,uint256)", + "log(bool,string)", + "log(bool,bool)", + "log(bool,address)", + "log(address,uint256)", + "log(address,string)", + "log(address,bool)", + "log(address,address)", + "log(uint256,uint256,uint256)", + "log(uint256,uint256,string)", + "log(uint256,uint256,bool)", + "log(uint256,uint256,address)", + "log(uint256,string,uint256)", + "log(uint256,string,string)", + "log(uint256,string,bool)", + "log(uint256,string,address)", + "log(uint256,bool,uint256)", + "log(uint256,bool,string)", + "log(uint256,bool,bool)", + "log(uint256,bool,address)", + "log(uint256,address,uint256)", + "log(uint256,address,string)", + "log(uint256,address,bool)", + "log(uint256,address,address)", + "log(string,uint256,uint256)", + "log(string,uint256,string)", + "log(string,uint256,bool)", + "log(string,uint256,address)", + "log(string,string,uint256)", + "log(string,string,string)", + "log(string,string,bool)", + "log(string,string,address)", + "log(string,bool,uint256)", + "log(string,bool,string)", + "log(string,bool,bool)", + "log(string,bool,address)", + "log(string,address,uint256)", + "log(string,address,string)", + "log(string,address,bool)", + "log(string,address,address)", + "log(bool,uint256,uint256)", + "log(bool,uint256,string)", + "log(bool,uint256,bool)", + "log(bool,uint256,address)", + "log(bool,string,uint256)", + "log(bool,string,string)", + "log(bool,string,bool)", + "log(bool,string,address)", + "log(bool,bool,uint256)", + "log(bool,bool,string)", + "log(bool,bool,bool)", + "log(bool,bool,address)", + "log(bool,address,uint256)", + "log(bool,address,string)", + "log(bool,address,bool)", + "log(bool,address,address)", + "log(address,uint256,uint256)", + "log(address,uint256,string)", + "log(address,uint256,bool)", + "log(address,uint256,address)", + "log(address,string,uint256)", + "log(address,string,string)", + "log(address,string,bool)", + "log(address,string,address)", + "log(address,bool,uint256)", + "log(address,bool,string)", + "log(address,bool,bool)", + "log(address,bool,address)", + "log(address,address,uint256)", + "log(address,address,string)", + "log(address,address,bool)", + "log(address,address,address)", + "log(uint256,uint256,uint256,uint256)", + "log(uint256,uint256,uint256,string)", + "log(uint256,uint256,uint256,bool)", + "log(uint256,uint256,uint256,address)", + "log(uint256,uint256,string,uint256)", + "log(uint256,uint256,string,string)", + "log(uint256,uint256,string,bool)", + "log(uint256,uint256,string,address)", + "log(uint256,uint256,bool,uint256)", + "log(uint256,uint256,bool,string)", + "log(uint256,uint256,bool,bool)", + "log(uint256,uint256,bool,address)", + "log(uint256,uint256,address,uint256)", + "log(uint256,uint256,address,string)", + "log(uint256,uint256,address,bool)", + "log(uint256,uint256,address,address)", + "log(uint256,string,uint256,uint256)", + "log(uint256,string,uint256,string)", + "log(uint256,string,uint256,bool)", + "log(uint256,string,uint256,address)", + "log(uint256,string,string,uint256)", + "log(uint256,string,string,string)", + "log(uint256,string,string,bool)", + "log(uint256,string,string,address)", + "log(uint256,string,bool,uint256)", + "log(uint256,string,bool,string)", + "log(uint256,string,bool,bool)", + "log(uint256,string,bool,address)", + "log(uint256,string,address,uint256)", + "log(uint256,string,address,string)", + "log(uint256,string,address,bool)", + "log(uint256,string,address,address)", + "log(uint256,bool,uint256,uint256)", + "log(uint256,bool,uint256,string)", + "log(uint256,bool,uint256,bool)", + "log(uint256,bool,uint256,address)", + "log(uint256,bool,string,uint256)", + "log(uint256,bool,string,string)", + "log(uint256,bool,string,bool)", + "log(uint256,bool,string,address)", + "log(uint256,bool,bool,uint256)", + "log(uint256,bool,bool,string)", + "log(uint256,bool,bool,bool)", + "log(uint256,bool,bool,address)", + "log(uint256,bool,address,uint256)", + "log(uint256,bool,address,string)", + "log(uint256,bool,address,bool)", + "log(uint256,bool,address,address)", + "log(uint256,address,uint256,uint256)", + "log(uint256,address,uint256,string)", + "log(uint256,address,uint256,bool)", + "log(uint256,address,uint256,address)", + "log(uint256,address,string,uint256)", + "log(uint256,address,string,string)", + "log(uint256,address,string,bool)", + "log(uint256,address,string,address)", + "log(uint256,address,bool,uint256)", + "log(uint256,address,bool,string)", + "log(uint256,address,bool,bool)", + "log(uint256,address,bool,address)", + "log(uint256,address,address,uint256)", + "log(uint256,address,address,string)", + "log(uint256,address,address,bool)", + "log(uint256,address,address,address)", + "log(string,uint256,uint256,uint256)", + "log(string,uint256,uint256,string)", + "log(string,uint256,uint256,bool)", + "log(string,uint256,uint256,address)", + "log(string,uint256,string,uint256)", + "log(string,uint256,string,string)", + "log(string,uint256,string,bool)", + "log(string,uint256,string,address)", + "log(string,uint256,bool,uint256)", + "log(string,uint256,bool,string)", + "log(string,uint256,bool,bool)", + "log(string,uint256,bool,address)", + "log(string,uint256,address,uint256)", + "log(string,uint256,address,string)", + "log(string,uint256,address,bool)", + "log(string,uint256,address,address)", + "log(string,string,uint256,uint256)", + "log(string,string,uint256,string)", + "log(string,string,uint256,bool)", + "log(string,string,uint256,address)", + "log(string,string,string,uint256)", + "log(string,string,string,string)", + "log(string,string,string,bool)", + "log(string,string,string,address)", + "log(string,string,bool,uint256)", + "log(string,string,bool,string)", + "log(string,string,bool,bool)", + "log(string,string,bool,address)", + "log(string,string,address,uint256)", + "log(string,string,address,string)", + "log(string,string,address,bool)", + "log(string,string,address,address)", + "log(string,bool,uint256,uint256)", + "log(string,bool,uint256,string)", + "log(string,bool,uint256,bool)", + "log(string,bool,uint256,address)", + "log(string,bool,string,uint256)", + "log(string,bool,string,string)", + "log(string,bool,string,bool)", + "log(string,bool,string,address)", + "log(string,bool,bool,uint256)", + "log(string,bool,bool,string)", + "log(string,bool,bool,bool)", + "log(string,bool,bool,address)", + "log(string,bool,address,uint256)", + "log(string,bool,address,string)", + "log(string,bool,address,bool)", + "log(string,bool,address,address)", + "log(string,address,uint256,uint256)", + "log(string,address,uint256,string)", + "log(string,address,uint256,bool)", + "log(string,address,uint256,address)", + "log(string,address,string,uint256)", + "log(string,address,string,string)", + "log(string,address,string,bool)", + "log(string,address,string,address)", + "log(string,address,bool,uint256)", + "log(string,address,bool,string)", + "log(string,address,bool,bool)", + "log(string,address,bool,address)", + "log(string,address,address,uint256)", + "log(string,address,address,string)", + "log(string,address,address,bool)", + "log(string,address,address,address)", + "log(bool,uint256,uint256,uint256)", + "log(bool,uint256,uint256,string)", + "log(bool,uint256,uint256,bool)", + "log(bool,uint256,uint256,address)", + "log(bool,uint256,string,uint256)", + "log(bool,uint256,string,string)", + "log(bool,uint256,string,bool)", + "log(bool,uint256,string,address)", + "log(bool,uint256,bool,uint256)", + "log(bool,uint256,bool,string)", + "log(bool,uint256,bool,bool)", + "log(bool,uint256,bool,address)", + "log(bool,uint256,address,uint256)", + "log(bool,uint256,address,string)", + "log(bool,uint256,address,bool)", + "log(bool,uint256,address,address)", + "log(bool,string,uint256,uint256)", + "log(bool,string,uint256,string)", + "log(bool,string,uint256,bool)", + "log(bool,string,uint256,address)", + "log(bool,string,string,uint256)", + "log(bool,string,string,string)", + "log(bool,string,string,bool)", + "log(bool,string,string,address)", + "log(bool,string,bool,uint256)", + "log(bool,string,bool,string)", + "log(bool,string,bool,bool)", + "log(bool,string,bool,address)", + "log(bool,string,address,uint256)", + "log(bool,string,address,string)", + "log(bool,string,address,bool)", + "log(bool,string,address,address)", + "log(bool,bool,uint256,uint256)", + "log(bool,bool,uint256,string)", + "log(bool,bool,uint256,bool)", + "log(bool,bool,uint256,address)", + "log(bool,bool,string,uint256)", + "log(bool,bool,string,string)", + "log(bool,bool,string,bool)", + "log(bool,bool,string,address)", + "log(bool,bool,bool,uint256)", + "log(bool,bool,bool,string)", + "log(bool,bool,bool,bool)", + "log(bool,bool,bool,address)", + "log(bool,bool,address,uint256)", + "log(bool,bool,address,string)", + "log(bool,bool,address,bool)", + "log(bool,bool,address,address)", + "log(bool,address,uint256,uint256)", + "log(bool,address,uint256,string)", + "log(bool,address,uint256,bool)", + "log(bool,address,uint256,address)", + "log(bool,address,string,uint256)", + "log(bool,address,string,string)", + "log(bool,address,string,bool)", + "log(bool,address,string,address)", + "log(bool,address,bool,uint256)", + "log(bool,address,bool,string)", + "log(bool,address,bool,bool)", + "log(bool,address,bool,address)", + "log(bool,address,address,uint256)", + "log(bool,address,address,string)", + "log(bool,address,address,bool)", + "log(bool,address,address,address)", + "log(address,uint256,uint256,uint256)", + "log(address,uint256,uint256,string)", + "log(address,uint256,uint256,bool)", + "log(address,uint256,uint256,address)", + "log(address,uint256,string,uint256)", + "log(address,uint256,string,string)", + "log(address,uint256,string,bool)", + "log(address,uint256,string,address)", + "log(address,uint256,bool,uint256)", + "log(address,uint256,bool,string)", + "log(address,uint256,bool,bool)", + "log(address,uint256,bool,address)", + "log(address,uint256,address,uint256)", + "log(address,uint256,address,string)", + "log(address,uint256,address,bool)", + "log(address,uint256,address,address)", + "log(address,string,uint256,uint256)", + "log(address,string,uint256,string)", + "log(address,string,uint256,bool)", + "log(address,string,uint256,address)", + "log(address,string,string,uint256)", + "log(address,string,string,string)", + "log(address,string,string,bool)", + "log(address,string,string,address)", + "log(address,string,bool,uint256)", + "log(address,string,bool,string)", + "log(address,string,bool,bool)", + "log(address,string,bool,address)", + "log(address,string,address,uint256)", + "log(address,string,address,string)", + "log(address,string,address,bool)", + "log(address,string,address,address)", + "log(address,bool,uint256,uint256)", + "log(address,bool,uint256,string)", + "log(address,bool,uint256,bool)", + "log(address,bool,uint256,address)", + "log(address,bool,string,uint256)", + "log(address,bool,string,string)", + "log(address,bool,string,bool)", + "log(address,bool,string,address)", + "log(address,bool,bool,uint256)", + "log(address,bool,bool,string)", + "log(address,bool,bool,bool)", + "log(address,bool,bool,address)", + "log(address,bool,address,uint256)", + "log(address,bool,address,string)", + "log(address,bool,address,bool)", + "log(address,bool,address,address)", + "log(address,address,uint256,uint256)", + "log(address,address,uint256,string)", + "log(address,address,uint256,bool)", + "log(address,address,uint256,address)", + "log(address,address,string,uint256)", + "log(address,address,string,string)", + "log(address,address,string,bool)", + "log(address,address,string,address)", + "log(address,address,bool,uint256)", + "log(address,address,bool,string)", + "log(address,address,bool,bool)", + "log(address,address,bool,address)", + "log(address,address,address,uint256)", + "log(address,address,address,string)", + "log(address,address,address,bool)", + "log(address,address,address,address)", +]; + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn test_get_log_functions_compiles() { + assert_eq!(378, get_log_functions().len()); + } +} diff --git a/.test-node-subtree/src/data/abi_map.json b/.test-node-subtree/src/data/abi_map.json new file mode 100644 index 00000000..c8c58f34 --- /dev/null +++ b/.test-node-subtree/src/data/abi_map.json @@ -0,0 +1,394 @@ +[ + [ + "0x00000000", + "0x00000000" + ], + [ + "0x310ab089", + "getImmutable(address, uint256)" + ], + [ + "0xad7e232e", + "setImmutables(address, tuple[])" + ], + [ + "0xdf9c1589", + "executeTransaction(bytes32, bytes32, tuple)" + ], + [ + "0xeeb8cb09", + "executeTransactionFromOutside(tuple)" + ], + [ + "0xe2f318e3", + "payForTransaction(bytes32, bytes32, tuple)" + ], + [ + "0xa28c1aee", + "prepareForPaymaster(bytes32, bytes32, tuple)" + ], + [ + "0x202bcce7", + "validateTransaction(bytes32, bytes32, tuple)" + ], + [ + "0x9c4d535b", + "create(bytes32, bytes32, bytes)" + ], + [ + "0x3cda3351", + "create2(bytes32, bytes32, bytes)" + ], + [ + "0x5d382700", + "create2Account(bytes32, bytes32, bytes, uint8)" + ], + [ + "0xecf95b8a", + "createAccount(bytes32, bytes32, bytes, uint8)" + ], + [ + "0xbb0fd610", + "extendedAccountVersion(address)" + ], + [ + "0xf3385fb6", + "forceDeployOnAddress(tuple, address)" + ], + [ + "0xe9f18c17", + "forceDeployOnAddresses(tuple[])" + ], + [ + "0x7b510fe8", + "getAccountInfo(address)" + ], + [ + "0x187598a5", + "getNewAddressCreate(address, uint256)" + ], + [ + "0x84da1fb4", + "getNewAddressCreate2(address, bytes32, bytes32, bytes)" + ], + [ + "0x57180981", + "updateAccountVersion(uint8)" + ], + [ + "0xec8067c7", + "updateNonceOrdering(uint8)" + ], + [ + "0x62f84b24", + "sendToL1(bytes)" + ], + [ + "0xfb1a9a57", + "getDeploymentNonce(address)" + ], + [ + "0x896909dc", + "getMinNonce(address)" + ], + [ + "0x5aa9b6b5", + "getRawNonce(address)" + ], + [ + "0x55d35d18", + "getValueUnderNonce(uint256)" + ], + [ + "0x38a78092", + "increaseMinNonce(uint256)" + ], + [ + "0x306395c6", + "incrementDeploymentNonce(address)" + ], + [ + "0xe1239cd8", + "incrementMinNonceIfEquals(uint256)" + ], + [ + "0xcab7e8eb", + "isNonceUsed(address, uint256)" + ], + [ + "0x155fd27a", + "setValueUnderNonce(uint256, uint256)" + ], + [ + "0x6ee1dc20", + "validateNonceUsage(address, uint256, bool)" + ], + [ + "0x9cc7f708", + "balanceOf(uint256)" + ], + [ + "0x313ce567", + "decimals()" + ], + [ + "0x40c10f19", + "mint(address, uint256)" + ], + [ + "0x06fdde03", + "name()" + ], + [ + "0x95d89b41", + "symbol()" + ], + [ + "0x18160ddd", + "totalSupply()" + ], + [ + "0x579952fc", + "transferFromTo(address, address, uint256)" + ], + [ + "0x51cff8d9", + "withdraw(address)" + ], + [ + "0xebe4a3d7", + "getTransactionHashes(tuple)" + ], + [ + "0x6ef25c3a", + "baseFee()" + ], + [ + "0x7877a797", + "blockGasLimit()" + ], + [ + "0x85df51fd", + "blockHash(uint256)" + ], + [ + "0x9a8a0592", + "chainId()" + ], + [ + "0xa6ae0aac", + "coinbase()" + ], + [ + "0xa0803ef7", + "currentBlockInfo()" + ], + [ + "0x19cae462", + "difficulty()" + ], + [ + "0xfe173b97", + "gasPrice()" + ], + [ + "0x80b41246", + "getBlockHashEVM(uint256)" + ], + [ + "0x42cbb15c", + "getBlockNumber()" + ], + [ + "0xd4a4ca0d", + "getBlockNumberAndTimestamp()" + ], + [ + "0x796b89b9", + "getBlockTimestamp()" + ], + [ + "0x938b5f32", + "origin()" + ], + [ + "0xbf1fe420", + "setGasPrice(uint256)" + ], + [ + "0x9e830ad3", + "setNewBlock(bytes32, uint256, uint256, uint256)" + ], + [ + "0xa851ae78", + "setTxOrigin(address)" + ], + [ + "0x4d59979f", + "unsafeOverrideBlock(uint256, uint256, uint256)" + ], + [ + "0xe03fe177", + "getCodeHash(uint256)" + ], + [ + "0x1806aa18", + "getCodeSize(uint256)" + ], + [ + "0x4de2e468", + "getRawCodeHash(address)" + ], + [ + "0xc2e4ff97", + "markAccountCodeHashAsConstructed(address)" + ], + [ + "0x0d4651aa", + "storeAccountConstructedCodeHash(address, bytes32)" + ], + [ + "0x4f1e1be0", + "storeAccountConstructingCodeHash(address, bytes32)" + ], + [ + "0xf5e69a47", + "publishCompressedBytecode(bytes, bytes)" + ], + [ + "0x1c9d7eb3", + "log(uint256, bool)" + ], + [ + "0x2a110e83", + "log(bool, bool)" + ], + [ + "0x2c2ecbc2", + "log(address)" + ], + [ + "0x319af333", + "log(string, address)" + ], + [ + "0x32458eed", + "log(bool)" + ], + [ + "0x399174d3", + "log(bool, uint256)" + ], + [ + "0x41304fac", + "log(string)" + ], + [ + "0x4b5c4277", + "log(string, string)" + ], + [ + "0x51973ec9", + "log()" + ], + [ + "0x643fd0df", + "log(uint256, string)" + ], + [ + "0x69276c86", + "log(uint256, address)" + ], + [ + "0x759f86bb", + "log(address, string)" + ], + [ + "0x75b605d3", + "log(address, bool)" + ], + [ + "0x8309e8a8", + "log(address, uint256)" + ], + [ + "0x853c4849", + "log(bool, address)" + ], + [ + "0x8feac525", + "log(bool, string)" + ], + [ + "0xb60e72cc", + "log(string, uint256)" + ], + [ + "0xc3b55635", + "log(string, bool)" + ], + [ + "0xdaf0d4aa", + "log(address, address)" + ], + [ + "0xf666715a", + "log(uint256, uint256)" + ], + [ + "0xf82c50f1", + "log(uint256)" + ], + [ + "0x5f91b0af", + "logAddress(address)" + ], + [ + "0xba7ab84e", + "logBool(bool)" + ], + [ + "0xe17bf956", + "logBytes(bytes)" + ], + [ + "0x6f4171c9", + "logBytes1(bytes1)" + ], + [ + "0x9b5e943e", + "logBytes2(bytes2)" + ], + [ + "0x7782fa2d", + "logBytes3(bytes3)" + ], + [ + "0xfba3ad39", + "logBytes4(bytes4)" + ], + [ + "0x6525b5f5", + "logInt(int256)" + ], + [ + "0x0bb563d6", + "logString(string)" + ], + [ + "0x9905b744", + "logUint(uint256)" + ], + [ + "0x4c6314f0", + "getMarker(bytes32)" + ], + [ + "0x24a55db9", + "markBytecodeAsPublished(bytes32, bytes32, uint256)" + ], + [ + "0xe516761e", + "markFactoryDeps(bool, bytes32[])" + ] +] \ No newline at end of file diff --git a/.test-node-subtree/src/data/address_map.json b/.test-node-subtree/src/data/address_map.json new file mode 100644 index 00000000..edc9a5fe --- /dev/null +++ b/.test-node-subtree/src/data/address_map.json @@ -0,0 +1,82 @@ +[ + [ + "0x0000000000000000000000000000000000008001", + "bootloader", + "System" + ], + [ + "0x0000000000000000000000000000000000008002", + "Account Code Storage", + "System" + ], + [ + "0x0000000000000000000000000000000000008003", + "Nonce Holder", + "System" + ], + [ + "0x0000000000000000000000000000000000008004", + "Known code storage", + "System" + ], + [ + "0x0000000000000000000000000000000000008005", + "ImmutableSimulator", + "System" + ], + [ + "0x0000000000000000000000000000000000008006", + "L2 deployer", + "System" + ], + [ + "0x0000000000000000000000000000000000008007", + "Force L2 deployer", + "System" + ], + [ + "0x0000000000000000000000000000000000008008", + "L1 messenger", + "System" + ], + [ + "0x0000000000000000000000000000000000008009", + "Msg Value System Contract", + "System" + ], + [ + "0x000000000000000000000000000000000000800a", + "EthToken System Contract", + "System" + ], + [ + "0x000000000000000000000000000000000000800b", + "System context", + "System" + ], + [ + "0x000000000000000000000000000000000000800c", + "Bootloader utilities", + "System" + ], + [ + "0x000000000000000000000000000000000000800d", + "Event writer", + "System" + ], + [ + "0x000000000000000000000000000000000000800e", + "Compressor", + "System" + ], + [ + "0x0000000000000000000000000000000000008010", + "Keccak", + "Precompile" + ], + [ + "0x000000000000000000636f6e736f6c652e6c6f67", + "Console log", + "Precompile" + ] +] \ No newline at end of file diff --git a/.test-node-subtree/src/deps/contracts/AccountCodeStorage.json b/.test-node-subtree/src/deps/contracts/AccountCodeStorage.json new file mode 100644 index 00000000..0303447b --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/AccountCodeStorage.json @@ -0,0 +1,118 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "AccountCodeStorage", + "sourceName": "cache-zk/solpp-generated-contracts/AccountCodeStorage.sol", + "abi": [ + { + "inputs": [ + { + "internalType": "uint256", + "name": "_input", + "type": "uint256" + } + ], + "name": "getCodeHash", + "outputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_input", + "type": "uint256" + } + ], + "name": "getCodeSize", + "outputs": [ + { + "internalType": "uint256", + "name": "codeSize", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + } + ], + "name": "getRawCodeHash", + "outputs": [ + { + "internalType": "bytes32", + "name": "codeHash", + "type": "bytes32" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + } + ], + "name": "markAccountCodeHashAsConstructed", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + }, + { + "internalType": "bytes32", + "name": "_hash", + "type": "bytes32" + } + ], + "name": "storeAccountConstructedCodeHash", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + }, + { + "internalType": "bytes32", + "name": "_hash", + "type": "bytes32" + } + ], + "name": "storeAccountConstructingCodeHash", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "bytecode": "0x00020000000000020000008004000039000000400040043f0000000003010019000000600330027000000057033001970000000102200190000000200000c13d000000040230008c000000db0000413d000000000201043b000000e002200270000000590520009c000000280000213d0000005d0420009c000000800000613d0000005e0420009c0000009b0000613d0000005f0220009c000000db0000c13d0000000002000416000000000202004b000000db0000c13d000000040230008a000000200220008c000000db0000413d0000000401100370000000000101043b000000610210009c000000db0000213d000000000101041a000000b20000013d0000000001000416000000000101004b000000db0000c13d0000002001000039000001000010044300000120000004430000005801000041000001560001042e0000005a0520009c000000b50000613d0000005b0520009c000000d10000613d0000005c0220009c000000db0000c13d0000000002000416000000000202004b000000db0000c13d000000040230008a000000200220008c000000db0000413d00000060030000410000000401100370000000000101043b0000006101100197000001000210008c0000007c0000413d0000008004000039000000000501041a000000000205004b000000780000c13d000200000005001d0000006202000041000000800020043f000000840010043f00000057010000410000000002000414000000570320009c0000000002018019000000c00120021000000063011001c70000800302000039015501500000040f000000000301001900000060033002700000005703300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000005c0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000000540000413d000000000705004b0000006b0000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000000fd0000613d0000001f01400039000000600110018f00000080041001bf000000400040043f000000200130008c000000db0000413d000000800100043d000000000101004b000000600300004100000002050000290000007c0000c13d00000064015001970000006003000041000000650110009c000000000305c0190000000000340435000000400140021000000066011001c7000001560001042e0000000002000416000000000202004b000000db0000c13d000000040230008a000000400220008c000000db0000413d0000000402100370000000000202043b000000610320009c000000db0000213d0000002401100370000000000101043b0000000003000411000080060330008c000000f10000c13d0000006403100198000000ee0000613d0000006a01000041000000800010043f0000002001000039000000840010043f0000002b01000039000000a40010043f0000006e01000041000000c40010043f0000006f01000041000000fa0000013d0000000002000416000000000202004b000000db0000c13d000000040230008a000000200220008c000000db0000413d0000000401100370000000000101043b0000006101100197000001000210008c00000000020000190000000102004039000000000101041a000000000301004b00000001022061bf0000006403100197000000650330009c0000000003000019000000010300603900000000023201a0000000db011002700000006901100197000000000100c019000000800010043f0000006801000041000001560001042e0000000002000416000000000202004b000000db0000c13d000000040230008a000000400220008c000000db0000413d0000000402100370000000000302043b000000610230009c000000db0000213d0000002401100370000000000101043b000200000001001d0000000001000411000080060110008c00000000010000190000000101006039000100000003001d015501200000040f00000002010000290000006401100197000000650110009c00000000010000190000000101006039015501380000040f00000002010000290000000102000029000000ee0000013d0000000002000416000000000202004b000000db0000c13d000000040230008a000000200220008c000000db0000413d0000000401100370000000000201043b000000610120009c000000dd0000a13d000000000100001900000157000104300000000001000411000080060110008c00000000010000190000000101006039000200000002001d015501200000040f0000000201000029000000000101041a000100000001001d0000006401100197000000650110009c00000000010000190000000101006039015501380000040f000000010100002900000067011001970000000202000029000000000012041b0000000001000019000001560001042e0000006a01000041000000800010043f0000002001000039000000840010043f0000002d01000039000000a40010043f0000006b01000041000000c40010043f0000006c01000041000000e40010043f0000006d010000410000015700010430000000400200043d0000001f0430018f00000005053002720000010a0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000001020000413d000000000604004b000001190000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f00000000001504350000005701000041000000570420009c000000000201801900000040012002100000006002300210000000000121019f0000015700010430000000000101004b000001230000613d000000000001042d000000400100043d00000064021000390000006c03000041000000000032043500000044021000390000006b03000041000000000032043500000024021000390000002d0300003900000000003204350000006a0200004100000000002104350000000402100039000000200300003900000000003204350000005702000041000000570310009c0000000001028019000000400110021000000070011001c70000015700010430000000000101004b0000013b0000613d000000000001042d000000400100043d00000064021000390000007103000041000000000032043500000044021000390000007203000041000000000032043500000024021000390000002e0300003900000000003204350000006a0200004100000000002104350000000402100039000000200300003900000000003204350000005702000041000000570310009c0000000001028019000000400110021000000070011001c7000001570001043000000153002104230000000102000039000000000001042d0000000002000019000000000001042d0000015500000432000001560001042e0000015700010430000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000000000000000000000000000000000000000000000000000000000004f1e1bdf000000000000000000000000000000000000000000000000000000004f1e1be000000000000000000000000000000000000000000000000000000000c2e4ff9700000000000000000000000000000000000000000000000000000000e03fe177000000000000000000000000000000000000000000000000000000000d4651aa000000000000000000000000000000000000000000000000000000001806aa18000000000000000000000000000000000000000000000000000000004de2e468c5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470000000000000000000000000ffffffffffffffffffffffffffffffffffffffff5aa9b6b500000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000080000000000000000000ff00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000ff00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff000000000000000000000000000000000000002000000080000000000000000000000000000000000000000000000000000000000000000000000000001fffe008c379a00000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c7920627920746865206465706c6f7965722073797374656d20636f6e7472616374000000000000000000000000000000000000000000000000000000000000000000000000000084000000800000000000000000436f64652068617368206973206e6f7420666f72206120636f6e737472756374656420636f6e747261637400000000000000000000000000000000000000000000000000000000000000000000000000000000840000000000000000000000006f6e20636f6e7374727563746f72000000000000000000000000000000000000436f64652068617368206973206e6f7420666f72206120636f6e7472616374200000000000000000000000000000000000000000000000000000000000000000d52566de1e8c8c6e03eb6c15dde493485a8e2b09b9ccbc7aec9dc580a7f2195a", + "deployedBytecode": "0x00020000000000020000008004000039000000400040043f0000000003010019000000600330027000000057033001970000000102200190000000200000c13d000000040230008c000000db0000413d000000000201043b000000e002200270000000590520009c000000280000213d0000005d0420009c000000800000613d0000005e0420009c0000009b0000613d0000005f0220009c000000db0000c13d0000000002000416000000000202004b000000db0000c13d000000040230008a000000200220008c000000db0000413d0000000401100370000000000101043b000000610210009c000000db0000213d000000000101041a000000b20000013d0000000001000416000000000101004b000000db0000c13d0000002001000039000001000010044300000120000004430000005801000041000001560001042e0000005a0520009c000000b50000613d0000005b0520009c000000d10000613d0000005c0220009c000000db0000c13d0000000002000416000000000202004b000000db0000c13d000000040230008a000000200220008c000000db0000413d00000060030000410000000401100370000000000101043b0000006101100197000001000210008c0000007c0000413d0000008004000039000000000501041a000000000205004b000000780000c13d000200000005001d0000006202000041000000800020043f000000840010043f00000057010000410000000002000414000000570320009c0000000002018019000000c00120021000000063011001c70000800302000039015501500000040f000000000301001900000060033002700000005703300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000005c0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000000540000413d000000000705004b0000006b0000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000000fd0000613d0000001f01400039000000600110018f00000080041001bf000000400040043f000000200130008c000000db0000413d000000800100043d000000000101004b000000600300004100000002050000290000007c0000c13d00000064015001970000006003000041000000650110009c000000000305c0190000000000340435000000400140021000000066011001c7000001560001042e0000000002000416000000000202004b000000db0000c13d000000040230008a000000400220008c000000db0000413d0000000402100370000000000202043b000000610320009c000000db0000213d0000002401100370000000000101043b0000000003000411000080060330008c000000f10000c13d0000006403100198000000ee0000613d0000006a01000041000000800010043f0000002001000039000000840010043f0000002b01000039000000a40010043f0000006e01000041000000c40010043f0000006f01000041000000fa0000013d0000000002000416000000000202004b000000db0000c13d000000040230008a000000200220008c000000db0000413d0000000401100370000000000101043b0000006101100197000001000210008c00000000020000190000000102004039000000000101041a000000000301004b00000001022061bf0000006403100197000000650330009c0000000003000019000000010300603900000000023201a0000000db011002700000006901100197000000000100c019000000800010043f0000006801000041000001560001042e0000000002000416000000000202004b000000db0000c13d000000040230008a000000400220008c000000db0000413d0000000402100370000000000302043b000000610230009c000000db0000213d0000002401100370000000000101043b000200000001001d0000000001000411000080060110008c00000000010000190000000101006039000100000003001d015501200000040f00000002010000290000006401100197000000650110009c00000000010000190000000101006039015501380000040f00000002010000290000000102000029000000ee0000013d0000000002000416000000000202004b000000db0000c13d000000040230008a000000200220008c000000db0000413d0000000401100370000000000201043b000000610120009c000000dd0000a13d000000000100001900000157000104300000000001000411000080060110008c00000000010000190000000101006039000200000002001d015501200000040f0000000201000029000000000101041a000100000001001d0000006401100197000000650110009c00000000010000190000000101006039015501380000040f000000010100002900000067011001970000000202000029000000000012041b0000000001000019000001560001042e0000006a01000041000000800010043f0000002001000039000000840010043f0000002d01000039000000a40010043f0000006b01000041000000c40010043f0000006c01000041000000e40010043f0000006d010000410000015700010430000000400200043d0000001f0430018f00000005053002720000010a0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000001020000413d000000000604004b000001190000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f00000000001504350000005701000041000000570420009c000000000201801900000040012002100000006002300210000000000121019f0000015700010430000000000101004b000001230000613d000000000001042d000000400100043d00000064021000390000006c03000041000000000032043500000044021000390000006b03000041000000000032043500000024021000390000002d0300003900000000003204350000006a0200004100000000002104350000000402100039000000200300003900000000003204350000005702000041000000570310009c0000000001028019000000400110021000000070011001c70000015700010430000000000101004b0000013b0000613d000000000001042d000000400100043d00000064021000390000007103000041000000000032043500000044021000390000007203000041000000000032043500000024021000390000002e0300003900000000003204350000006a0200004100000000002104350000000402100039000000200300003900000000003204350000005702000041000000570310009c0000000001028019000000400110021000000070011001c7000001570001043000000153002104230000000102000039000000000001042d0000000002000019000000000001042d0000015500000432000001560001042e0000015700010430000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000000000000000000000000000000000000000000000000000000000004f1e1bdf000000000000000000000000000000000000000000000000000000004f1e1be000000000000000000000000000000000000000000000000000000000c2e4ff9700000000000000000000000000000000000000000000000000000000e03fe177000000000000000000000000000000000000000000000000000000000d4651aa000000000000000000000000000000000000000000000000000000001806aa18000000000000000000000000000000000000000000000000000000004de2e468c5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470000000000000000000000000ffffffffffffffffffffffffffffffffffffffff5aa9b6b500000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000080000000000000000000ff00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000ff00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff000000000000000000000000000000000000002000000080000000000000000000000000000000000000000000000000000000000000000000000000001fffe008c379a00000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c7920627920746865206465706c6f7965722073797374656d20636f6e7472616374000000000000000000000000000000000000000000000000000000000000000000000000000084000000800000000000000000436f64652068617368206973206e6f7420666f72206120636f6e737472756374656420636f6e747261637400000000000000000000000000000000000000000000000000000000000000000000000000000000840000000000000000000000006f6e20636f6e7374727563746f72000000000000000000000000000000000000436f64652068617368206973206e6f7420666f72206120636f6e7472616374200000000000000000000000000000000000000000000000000000000000000000d52566de1e8c8c6e03eb6c15dde493485a8e2b09b9ccbc7aec9dc580a7f2195a", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/BootloaderUtilities.json b/.test-node-subtree/src/deps/contracts/BootloaderUtilities.json new file mode 100644 index 00000000..4754f059 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/BootloaderUtilities.json @@ -0,0 +1,118 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "BootloaderUtilities", + "sourceName": "cache-zk/solpp-generated-contracts/BootloaderUtilities.sol", + "abi": [ + { + "inputs": [ + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "getTransactionHashes", + "outputs": [ + { + "internalType": "bytes32", + "name": "txHash", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "signedTxHash", + "type": "bytes32" + } + ], + "stateMutability": "view", + "type": "function" + } + ], + "bytecode": "0x00020000000000020011000000000002000100000001035500000000030100190000006005300270000007ae0050019d0000008004000039000000400040043f000007ae0350019700000001022001900000008a0000c13d000000040230008c000000bc0000413d000000000201043b000007b002200197000007b10220009c000000bc0000c13d0000000002000416000000000202004b000000bc0000c13d000000040230008a000000200620008c000000bc0000413d0000000406100370000000000d06043b000007b206d0009c000000bc0000213d0000000002d20049000007b306000041000002600720008c00000000070000190000000007064019000007b302200197000000000802004b000000000600a019000007b30220009c000000000607c019000000000206004b000000bc0000c13d000000040cd000390000000002c1034f000000000202043b000000010620008c000000920000213d000000000402004b000000c80000613d000000010120008c000000be0000c13d000c0000000d001d000b0000000c001d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000400300043d000000000401043b000000800140008c0000021b0000413d0000008001400270000007b80240009c000000000104a019000007b80240009c0000000002000019000000100200203900000008052001bf000007b20610009c000000000502a0190000004002100270000007b20610009c000000000201a01900000004015001bf000007ae0620009c000000000105a0190000002006200270000007ae0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000007b20610009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000000020150003900000000061304360000000101000367000000000200003100000021075000390000000507700272000000780000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000000700000413d000000000700004b0000007a0000613d0000000007030433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c000000000400201900000021053000390000022e0000013d0000000001000416000000000101004b000000bc0000c13d000000200100003900000100001004430000012000000443000007af0100004100001eb30001042e000000020620008c0000010b0000613d000000710220008c000000be0000c13d000001c402d00039000000000221034f0000000006d30049000000230660008a000000000202043b000007b307000041000000000862004b00000000080000190000000008078019000007b306600197000007b309200197000000000a69004b0000000007008019000000000669013f000007b30660009c000000000708c019000000000607004b000000bc0000c13d0000000002c20019000000000621034f000000000606043b000007b20760009c000000bc0000213d00000000076300490000002002200039000007b308000041000000000972004b00000000090000190000000009082019000007b307700197000007b30a200197000000000b7a004b000000000800801900000000077a013f000007b30770009c000000000809c019000000000708004b000002dd0000613d000000000100001900001eb400010430000007c601000041000000800010043f0000002001000039000000840010043f0000001701000039000000a40010043f000007d801000041000000c40010043f000007d90100004100001eb400010430000000000231034f0000010005c00039000000000451034f000000000404043b000000800640008c000001650000413d0000008006400270000007b80740009c000000000604a019000007b80740009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a000000c108600039000000000778016f000000400070043f0000000207600039000000800070043f00000021076000390000000507700272000000f90000613d00000000080000190000000509800210000000000a92034f000000000a0a043b000000a0099000390000000000a904350000000108800039000000000978004b000000f10000413d000000000700004b000000fb0000613d000000800700043d000000000707004b000004e80000613d000000a00700043d000007b707700197000000f808600210000000000778019f000007b907700041000000a00070043f0000000306600210000000f80660008900000000046401cf000000ff0660008c0000000004002019000000a10040043f000001720000013d000c0000000d001d000b0000000c001d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000400300043d000000000401043b000000800140008c0000027c0000413d0000008001400270000007b80240009c000000000104a019000007b80240009c0000000002000019000000100200203900000008052001bf000007b20610009c000000000502a0190000004002100270000007b20610009c000000000201a01900000004015001bf000007ae0620009c000000000105a0190000002006200270000007ae0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000007b20610009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000000020150003900000000061304360000000101000367000000000200003100000021075000390000000507700272000001530000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b0000014b0000413d000000000700004b000001550000613d0000000007030433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c000000000400201900000021053000390000028f0000013d000000f806400210000007b307000041000000000404004b000000000706c019000000c004000039000000400040043f0000000104000039000000800040043f0000000004200350000000000404043b000007b704400197000000000474019f000000a00040043f000c0000000d001d000b0000000c001d000000400400043d000000600550008a000000000651034f000000000606043b000000800760008c000001bf0000413d0000008007600270000007b80860009c000000000706a019000007b80860009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008840019000000000948004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f0000000208700039000000000884043600000021097000390000000509900272000001ad0000613d000000000a000019000000050ba00210000000000cb80019000000000bb2034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000001a50000413d000000000900004b000001af0000613d0000000009040433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c00000000060020190000002107400039000001cf0000013d000007b60740009c000003fa0000213d0000004007400039000000400070043f000000010700003a00000000077404360000000008200350000000000808043b0000000000870435000004e80000613d000000f809600210000007b30a000041000000000606004b000000000a09c019000007b7068001970000000006a6019f0000000000670435000000400550008a000000000651034f000000400500043d000000000606043b000000800760008c000002fb0000413d0000008007600270000007b80860009c000000000706a019000007b80860009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008850019000000000958004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f0000000208700039000000000885043600000021097000390000000509900272000002090000613d000000000a000019000000050ba00210000000000cb80019000000000bb2034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000002010000413d000000000900004b0000020b0000613d0000000009050433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c000000000600201900000021075000390000030b0000013d000007b60130009c000003fa0000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000101000367000000000621034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807400210000007b308000041000000000404004b000000000807c019000007b704600197000000000484019f0000000000450435000000400400043d0000000c050000290000010406500039000000000561034f000000000505043b000000800750008c0000039a0000413d0000008007500270000007b80850009c000000000705a019000007b80850009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008840019000000000948004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f00000002087000390000000008840436000000210970003900000005099002720000026a0000613d000000000a21034f000000000b000019000000050cb00210000000000dc80019000000000cca034f000000000c0c043b0000000000cd0435000000010bb00039000000000c9b004b000002620000413d000000000900004b0000026c0000613d0000000009040433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000057501cf000000ff0770008c00000000050020190000002107400039000003ab0000013d000007b60130009c000003fa0000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000101000367000000000621034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807400210000007b308000041000000000404004b000000000807c019000007b704600197000000000484019f0000000000450435000000400400043d0000000c050000290000010406500039000000000561034f000000000505043b000000800750008c000003f80000413d0000008007500270000007b80850009c000000000705a019000007b80850009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008840019000000000948004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f0000000208700039000000000884043600000021097000390000000509900272000002cb0000613d000000000a21034f000000000b000019000000050cb00210000000000dc80019000000000cca034f000000000c0c043b0000000000cd0435000000010bb00039000000000c9b004b000002c30000413d000000000900004b000002cd0000613d0000000009040433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000057501cf000000ff0770008c000000000500201900000021074000390000056d0000013d00000000070004140000000008260019000000000668004b0000000006000019000000010600403900000001066001900000190f0000c13d000000000383004b0000190f0000413d000c0000000d001d000b0000000c001d000007c00370009c000003fe0000413d0000004401400039000007d0020000410000000000210435000000240140003900000008020000390000000000210435000007c6010000410000000000140435000000040140003900000020020000390000000000210435000007ae01000041000007ae0240009c00000000040180190000004001400210000007c7011001c700001eb400010430000007b60750009c000003fa0000213d0000004007500039000000400070043f000000010700003a00000000077504360000000008200350000000000808043b0000000000870435000004e80000613d000000f809600210000007b30a000041000000000606004b000000000a09c019000007b7068001970000000006a6019f0000000000670435000000400600043d000a00000006001d00000020066000390000000007040433000000000807004b0000031a0000613d000000000800001900000000096800190000002008800039000000000a480019000000000a0a04330000000000a90435000000000978004b000003130000413d000000000467001900000000000404350000000006050433000000000706004b000003270000613d000000000700001900000000084700190000002007700039000000000957001900000000090904330000000000980435000000000867004b000003200000413d000000000446001900000000000404350000000a060000290000000004640049000000200540008a00000000005604350000001f044000390008002000000092000000080440017f0000000005640019000000000445004b00000000040000190000000104004039000900000005001d000007b20550009c000003fa0000213d0000000104400190000003fa0000c13d0000000904000029000000400040043f000007b60440009c000003fa0000213d0000000c070000290000004404700039000000000441034f000000000404043b00000009080000290000004005800039000000400050043f0000002005800039000007ba060000410000000000650435000000150500003900000000005804350000006004400210000000210580003900000000004504350000012404700039000000000541034f000000400600043d000700000006001d000000000505043b000000800650008c000006180000413d0000008006500270000007b80750009c000000000605a019000007b80750009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c00000001066020390000004107600039000000080770017f0000000707700029000000070870006c00000000080000190000000108004039000007b20970009c000003fa0000213d0000000108800190000003fa0000c13d000000400070043f00000002076000390000000708000029000000000778043600000021086000390000000508800272000003860000613d0000000009000019000000050a900210000000000ba70019000000000aa2034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b0000037e0000413d000000000800004b000003880000613d00000007080000290000000008080433000000000808004b000004e80000613d0000000008070433000007b708800197000000f809600210000000000889019f000007b90880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c0000000005002019000000070600002900000021066000390000062a0000013d000007b60740009c000003fa0000213d0000004007400039000000400070043f000000000821034f000000010700003a00000000077404360000000008800350000000000808043b0000000000870435000004e80000613d000000f809500210000007b30a000041000000000505004b000000000a09c019000007b7058001970000000005a5019f0000000000570435000000400500043d000000600660008a000000000761034f000000000707043b000000800870008c000004ee0000413d0000008008700270000007b80970009c000000000807a019000007b80970009c00000000090000190000001009002039000000080a9001bf000007b20b80009c000000000a09a0190000004009800270000007b20b80009c000000000908a019000000040ba001bf000007ae0890009c000000000b0aa019000000200a900270000007ae0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000007b20b90009c000003fa0000213d000000010aa00190000003fa0000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa00272000003e60000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000003de0000413d000000000a00004b000003e80000613d000000000a050433000000000a0a004b000004e80000613d000000000a090433000007b70aa00197000000f80b800210000000000aab019f000007b90aa000410000000000a904350000000308800210000000f80880008900000000078701cf000000ff0880008c00000000070020190000002108500039000004ff0000013d000007b60740009c000004df0000a13d000007d30100004100000000001004350000004101000039000004eb0000013d000007ae02200197000000000121034f0000000002850049000007ae0220019700000000012103df000000c002700210000007c102200197000007c2022001c700000000012103af00008010020000391eb21ead0000040f00000000030100190000006003300270000007ae0530019700000001022001900000054c0000613d0000003f02500039000007c302200197000000400600043d0000000002260019000000000362004b00000000030000190000000103004039000007b20420009c000003fa0000213d0000000103300190000003fa0000c13d000000400020043f0000000004560436000000010200036700000000030000310000001f0750003900000005077002720000042a0000613d000000000832034f0000000009000019000000050a900210000000000ba40019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000004220000413d000000000700004b0000042c0000613d0000001f0750018f0000000505500272000004380000613d00000000080000190000000509800210000000000a940019000000000991034f000000000909043b00000000009a04350000000108800039000000000958004b000004300000413d000000000807004b000004470000613d0000000505500210000000000151034f00000000055400190000000307700210000000000805043300000000087801cf000000000878022f000000000101043b0000010007700089000000000171022f00000000017101cf000000000181019f00000000001504350000000001060433000000200110008c00000c980000c13d0000000c060000290000000001630049000000230510008a000a02040060003d0000000a01200360000000000101043b000007b306000041000000000751004b00000000070000190000000007068019000007b305500197000007b308100197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000506004b0000000b05000029000000bc0000c13d0000000004040433000900000004001d0000000001510019000000000412034f000000000504043b000007b20450009c000000bc0000213d000000050450021000000000034300490000002006100039000007b301000041000000000736004b00000000070000190000000007012019000007b303300197000007b308600197000000000938004b0000000001008019000000000338013f000007b30330009c000000000107c019000000000101004b000000bc0000c13d000000400100043d0000002003100039000007c405500198000004830000613d000000000262034f000000000600001900000005076002100000000008730019000000000772034f000000000707043b00000000007804350000000106600039000000000756004b0000047b0000413d000000000200004b000004850000613d00000000004104350000003f02400039000000200400008a000000000242016f0000000002210019000000000412004b00000000040000190000000104004039000007b20520009c000003fa0000213d0000000104400190000003fa0000c13d000000400020043f000007ae02000041000007ae0430009c000000000302801900000040033002100000000001010433000007ae0410009c00000000010280190000006001100210000000000131019f0000000003000414000007ae0430009c0000000003028019000000c002300210000000000112019f000007bf011001c700008010020000391eb21ea80000040f00000001022001900000000b0a0000290000000c03000029000000bc0000613d00000000020000310000000003320049000000230530008a0000000a0300002900000020043000390000000103000367000000000443034f000000000404043b000007b306000041000000000754004b00000000070000190000000007068019000007b305500197000007b308400197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000101043b000a00000001001d000000000106004b000000bc0000c13d0000000001a40019000000000413034f000000000404043b000007b20540009c000000bc0000213d00000000054200490000002001100039000007b306000041000000000751004b00000000070000190000000007062019000007b305500197000007b308100197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000506004b000000bc0000c13d00000000050004140000000006140019000000000446004b0000000004000019000000010400403900000001044001900000190f0000c13d000000000462004b0000190f0000413d000007c00450009c00000ba00000413d000000400400043d000002ea0000013d0000004007400039000000400070043f000000000821034f000000010700003a00000000077404360000000008800350000000000808043b0000000000870435000005670000c13d000007d30100004100000000001004350000003201000039000000040010043f000007d40100004100001eb400010430000007b60850009c000003fa0000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a700210000007b30b000041000000000707004b000000000b0ac019000007b7079001970000000007b7019f0000000000780435000000400700043d000000400660008a000000000861034f000000000808043b000000800980008c000006710000413d0000008009800270000007b80a80009c000000000908a019000007b80a80009c000000000a000019000000100a002039000000080ba001bf000007b20c90009c000000000b0aa019000000400a900270000007b20c90009c000000000a09a019000000040cb001bf000007ae09a0009c000000000c0ba019000000200ba00270000007ae09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa70019000000000b7a004b000000000b000019000000010b004039000007b20ca0009c000003fa0000213d000000010bb00190000003fa0000c13d0000004000a0043f000000020a900039000000000aa70436000000210b900039000000050bb002720000053a0000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b000005320000413d000000000b00004b0000053c0000613d000000000b070433000000000b0b004b000004e80000613d000000000b0a0433000007b70bb00197000000f80c900210000000000bbc019f000007b90bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c00000000080020190000002109700039000006820000013d0000001f0350018f0000000502500272000005570000613d00000000040000190000000506400210000000000761034f000000000707043b00000000007604350000000104400039000000000624004b000005500000413d000000000403004b000005650000613d00000003033002100000000502200210000000000402043300000000043401cf000000000434022f000000000121034f000000000101043b0000010003300089000000000131022f00000000013101cf000000000141019f0000000000120435000000600150021000001eb400010430000000f809500210000007b30a000041000000000505004b000000000a09c019000007b7058001970000000005a5019f0000000000570435000000400500043d000000400760008a000000000671034f000000000606043b000000800860008c000005ba0000413d0000008008600270000007b80960009c000000000806a019000007b80960009c00000000090000190000001009002039000000080a9001bf000007b20b80009c000000000a09a0190000004009800270000007b20b80009c000000000908a019000000040ba001bf000007ae0890009c000000000b0aa019000000200a900270000007ae0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000007b20b90009c000003fa0000213d000000010aa00190000003fa0000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa00272000005a80000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000005a00000413d000000000a00004b000005aa0000613d000000000a050433000000000a0a004b000004e80000613d000000000a090433000007b70aa00197000000f80b800210000000000aab019f000007b90aa000410000000000a904350000000308800210000000f80880008900000000068601cf000000ff0880008c00000000060020190000002108500039000005cb0000013d000007b60850009c000003fa0000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a600210000007b30b000041000000000606004b000000000b0ac019000007b7069001970000000006b6019f0000000000680435000000400600043d000000200770008a000000000871034f000000000808043b000000800980008c000006e20000413d0000008009800270000007b80a80009c000000000908a019000007b80a80009c000000000a000019000000100a002039000000080ba001bf000007b20c90009c000000000b0aa019000000400a900270000007b20c90009c000000000a09a019000000040cb001bf000007ae09a0009c000000000c0ba019000000200ba00270000007ae09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa60019000000000b6a004b000000000b000019000000010b004039000007b20ca0009c000003fa0000213d000000010bb00190000003fa0000c13d0000004000a0043f000000020a900039000000000aa60436000000210b900039000000050bb00272000006060000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b000005fe0000413d000000000b00004b000006080000613d000000000b060433000000000b0b004b000004e80000613d000000000b0a0433000007b70bb00197000000f80c900210000000000bbc019f000007b90bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c00000000080020190000002109600039000006f30000013d0000000706000029000007b60660009c000003fa0000213d00000007070000290000004006700039000000400060043f000000010600003a00000000066704360000000007200350000000000707043b0000000000760435000004e80000613d000000f808500210000007b309000041000000000505004b000000000908c019000007b705700197000000000595019f00000000005604350000000b0b0000290000000005b30049000000a006400039000000000461034f000000000404043b0000001f0550008a000007b307500197000007b308400197000007b309000041000000000a78004b000000000a000019000000000a094019000000000778013f000000000854004b0000000009004019000007b30770009c000000000a09c01900000000070a004b000000bc0000c13d0000000008b40019000000000781034f000000000707043b000007b20970009c000000bc0000213d00000000097300490000002008800039000007b30a000041000000000b98004b000000000b000019000000000b0a2019000007b309900197000007b30c800197000000000d9c004b000000000a00801900000000099c013f000007b30990009c000000000a0bc01900000000090a004b000000bc0000c13d000000010970008c0000086d0000c13d000000000281034f000000000202043b000000010700008a000007b308000041000000000772004b00000000070000190000000007082019000007b302200197000007b30920009c0000000008008019000007b302200167000007b30220009c000000000807c019000600600000003d000000000208004b0000096d0000c13d000000400200043d000600000002001d000007b60220009c000003fa0000213d00000006080000290000004002800039000000400020043f0000002002800039000007b9070000410000000000720435000000010200003900000000002804350000096d0000013d000007b60970009c000003fa0000213d0000004009700039000000400090043f000000000a21034f000000010900003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000000f80b800210000007b30c000041000000000808004b000000000c0bc019000007b708a001970000000008c8019f0000000000890435000000400900043d000007b60890009c000003fa0000213d000000200860008a000000000881034f000000000808043b000000400a9000390000004000a0043f000000200a900039000007ba0b0000410000000000ba0435000000150a0000390000000000a904350000006008800210000000210a90003900000000008a0435000000c006600039000000000661034f000000400800043d000000000606043b000a00000006001d000000800a60008c000007b60000413d0000000a06000029000000800a600270000007b80b60009c000000000a06a019000007b80b60009c000000000b000019000000100b002039000000080cb001bf000007b20da0009c000000000c0ba019000000400ba00270000007b20da0009c000000000b0aa019000000040dc001bf000007ae0ab0009c000000000d0ca019000000200cb00270000007ae0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000007b20db0009c000003fa0000213d000000010cc00190000003fa0000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc00272000006cf0000613d000000000d21034f000000000e000019000000050fe002100000000006fb0019000000000ffd034f000000000f0f043b0000000000f60435000000010ee000390000000006ce004b000006c70000413d000000000600004b000006d10000613d0000000006080433000000000606004b000004e80000613d00000000060b0433000007b706600197000000f80ca0021000000000066c019f000007b90660004100000000006b04350000000306a00210000000f8066000890000000a0a6001ef000000ff0660008c000000000a00201900000021068000390000000000a60435000007c90000013d000007b60960009c000003fa0000213d0000004009600039000000400090043f000000000a21034f000000010900003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000000f80b800210000007b30c000041000000000808004b000000000c0bc019000007b708a001970000000008c8019f0000000000890435000000400800043d000a0040007000920000000a09100360000000000909043b000000800a90008c000007410000413d000000800a900270000007b80b90009c000000000a09a019000007b80b90009c000000000b000019000000100b002039000000080cb001bf000007b20da0009c000000000c0ba019000000400ba00270000007b20da0009c000000000b0aa019000000040dc001bf000007ae0ab0009c000000000d0ca019000000200cb00270000007ae0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000007b20db0009c000003fa0000213d000000010cc00190000003fa0000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc002720000072e0000613d000000000d21034f000000000e000019000000050fe002100000000007fb0019000000000ffd034f000000000f0f043b0000000000f70435000000010ee000390000000007ce004b000007260000413d000000000700004b000007300000613d0000000007080433000000000707004b000004e80000613d00000000070b0433000007b707700197000000f80ca0021000000000077c019f000007b90770004100000000007b04350000000307a00210000000f80770008900000000097901cf000000ff0770008c000000000900201900000021078000390000000000970435000007530000013d000007b60780009c000003fa0000213d0000004007800039000000400070043f000000000721034f000000010a00003a000000000aa804360000000007700350000000000b07043b0000000000ba0435000004e80000613d000000f807900210000007b30c000041000000000909004b000000000c07c019000007b707b001970000000007c7019f00000000007a0435000000400a00043d000007b607a0009c000003fa0000213d0000000a0c0000290000002007c0008a000000000771034f000000000707043b0000004009a00039000000400090043f0000002009a00039000007ba0b0000410000000000b90435000000150900003900000000009a043500000060077002100000002109a000390000000000790435000000c007c00039000000000771034f000000400900043d000000000707043b000a00000007001d000000800b70008c000008980000413d0000000a07000029000000800b700270000007b80c70009c000000000b07a019000007b80c70009c000000000c000019000000100c002039000000080dc001bf000007b20eb0009c000000000d0ca019000000400cb00270000007b20eb0009c000000000c0ba019000000040ed001bf000007ae0bc0009c000000000e0da019000000200dc00270000007ae0bc0009c000000000d0ca0190000000207e001bf0000ffff0cd0008c00000000070ea019000000100cd00270000000000c0da019000000ff0cc0008c0000000107702039000000200c00008a000900000007001d000000410d700039000000000ccd016f000000000cc90019000000000d9c004b000000000d000019000000010d004039000007b20ec0009c000003fa0000213d000000010dd00190000003fa0000c13d0000004000c0043f0000000907000029000000020c700039000000000cc90436000000210d700039000000050dd00272000007a20000613d000000000e21034f000000000f0000190000000507f00210000000000b7c001900000000077e034f000000000707043b00000000007b0435000000010ff000390000000007df004b0000079a0000413d000000000700004b000007a40000613d0000000007090433000000000707004b000004e80000613d00000000070c0433000007b707700197000000090d000029000000f80bd0021000000000077b019f000007b90770004100000000007c04350000000307d00210000000f8077000890000000a0b7001ef000000ff0770008c000000000b00201900000021079000390000000000b70435000008ab0000013d000007b60680009c000003fa0000213d0000004006800039000000400060043f000000000621034f000000010a00003a000000000aa804360000000006600350000000000b06043b0000000000ba0435000004e80000613d0000000a0d000029000000f806d00210000007b30c000041000000000d0d004b000000000c06c019000007b706b001970000000006c6019f00000000006a0435000000400600043d000000200a600039000000000b030433000000000c0b004b000007d60000613d000000000c000019000000000dac0019000000200cc00039000000000e3c0019000000000e0e04330000000000ed0435000000000dbc004b000007cf0000413d0000000003ab00190000000000030435000000000a040433000000000b0a004b000007e30000613d000000000b000019000000000c3b0019000000200bb00039000000000d4b0019000000000d0d04330000000000dc0435000000000cab004b000007dc0000413d00000000033a001900000000000304350000000004050433000000000a04004b000007f00000613d000000000a000019000000000b3a0019000000200aa00039000000000c5a0019000000000c0c04330000000000cb0435000000000b4a004b000007e90000413d000000000334001900000000000304350000000004070433000000000504004b000007fd0000613d0000000005000019000000000a3500190000002005500039000000000b750019000000000b0b04330000000000ba0435000000000a45004b000007f60000413d000000000334001900000000000304350000000004090433000000000504004b0000080a0000613d000000000500001900000000073500190000002005500039000000000a950019000000000a0a04330000000000a70435000000000745004b000008030000413d000000000334001900000000000304350000000004080433000000000504004b000008170000613d000000000500001900000000073500190000002005500039000000000985001900000000090904330000000000970435000000000745004b000008100000413d000000000334001900000000000304350000000003630049000000200430008a00000000004604350000001f04300039000000200300008a000000000434016f0000000007640019000000000447004b00000000040000190000000104004039000007b20570009c000003fa0000213d0000000104400190000003fa0000c13d000000400070043f0000000c05000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b000007b308000041000000000954004b00000000090000190000000009088019000007b305500197000007b30a400197000000000b5a004b000000000800801900000000055a013f000007b30550009c000000000809c019000000000508004b0000000b05000029000000bc0000c13d0000000005540019000000000451034f000000000404043b000007b20840009c000000bc0000213d00000000084200490000002005500039000007b309000041000000000a85004b000000000a000019000000000a092019000007b308800197000007b30b500197000000000c8b004b000000000900801900000000088b013f000007b30880009c00000000090ac019000000000809004b000000bc0000c13d000000010840008c00000a5e0000c13d000000000851034f000000000808043b000000010900008a000007b30a000041000000000998004b000000000900001900000000090a2019000007b308800197000007b30b80009c000000000a008019000007b308800167000007b30880009c000000000a09c019000000600800003900000000090a004b00000cbb0000c13d000007b60870009c000003fa0000213d0000004008700039000000400080043f0000002008700039000007b909000041000000000098043500000001080000390000000000870435000000000807001900000cbb0000013d000000400800043d000600000008001d000000380870008c0000095c0000413d0000002009700270000007ae0870009c000000000907a019000007ae0870009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000000060a000029000007b60aa0009c000003fa0000213d000000000898019f000000060a0000290000004009a00039000000400090043f000000020980003a00000000099a04360000000002200350000000000202043b0000000000290435000004e80000613d000007b702200197000000f80a80021000000000022a019f000007bb022001c700000000002904350000000302800210000000f80220015f00000000022701cf0000000607000029000000210770003900000000002704350000096d0000013d000007b60790009c000003fa0000213d0000004007900039000000400070043f000000000721034f000000010b00003a000000000bb904360000000007700350000000000c07043b0000000000cb0435000004e80000613d0000000a0e000029000000f807e00210000007b30d000041000000000e0e004b000000000d07c019000007b707c001970000000007d7019f00000000007b0435000000400700043d000000200b700039000000000c030433000000000d0c004b000008b80000613d000000000d000019000000000ebd0019000000200dd00039000000000f3d0019000000000f0f04330000000000fe0435000000000ecd004b000008b10000413d0000000003bc00190000000000030435000000000b040433000000000c0b004b000008c50000613d000000000c000019000000000d3c0019000000200cc00039000000000e4c0019000000000e0e04330000000000ed0435000000000dbc004b000008be0000413d00000000033b001900000000000304350000000004050433000000000b04004b000008d20000613d000000000b000019000000000c3b0019000000200bb00039000000000d5b0019000000000d0d04330000000000dc0435000000000c4b004b000008cb0000413d000000000334001900000000000304350000000004060433000000000504004b000008df0000613d0000000005000019000000000b3500190000002005500039000000000c650019000000000c0c04330000000000cb0435000000000b45004b000008d80000413d000000000334001900000000000304350000000004080433000000000504004b000008ec0000613d000000000500001900000000063500190000002005500039000000000b850019000000000b0b04330000000000b60435000000000645004b000008e50000413d0000000003340019000000000003043500000000040a0433000000000504004b000008f90000613d0000000005000019000000000635001900000020055000390000000008a5001900000000080804330000000000860435000000000645004b000008f20000413d000000000334001900000000000304350000000004090433000000000504004b000009060000613d000000000500001900000000063500190000002005500039000000000895001900000000080804330000000000860435000000000645004b000008ff0000413d000000000334001900000000000304350000000003730049000000200430008a00000000004704350000001f04300039000000200300008a000000000434016f0000000006740019000000000446004b00000000040000190000000104004039000007b20560009c000003fa0000213d0000000104400190000003fa0000c13d000000400060043f0000000c05000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b000007b308000041000000000954004b00000000090000190000000009088019000007b305500197000007b30a400197000000000b5a004b000000000800801900000000055a013f000007b30550009c000000000809c019000000000508004b0000000b05000029000000bc0000c13d0000000005540019000000000451034f000000000404043b000007b20840009c000000bc0000213d00000000084200490000002005500039000007b309000041000000000a85004b000000000a000019000000000a092019000007b308800197000007b30b500197000000000c8b004b000000000900801900000000088b013f000007b30880009c00000000090ac019000000000809004b000000bc0000c13d000000010840008c00000cf60000c13d000000000851034f000000000808043b000000010900008a000007b30a000041000000000998004b000000000900001900000000090a2019000007b308800197000007b30b80009c000000000a008019000007b308800167000007b30880009c000000000a09c019000000600800003900000000090a004b00000dc60000c13d000007b60860009c000003fa0000213d0000004008600039000000400080043f0000002008600039000007b909000041000000000098043500000001080000390000000000860435000000000806001900000dc60000013d0000000608000029000007b60880009c000003fa0000213d00000006090000290000004008900039000000400080043f000000010800003a00000000088904360000000002200350000000000202043b0000000000280435000004e80000613d000000f807700210000007b702200197000000000272019f000007b3022001670000000000280435000000800260008a000000000621034f0000006002000039000000000606043b000000000606004b000009ce0000c13d000007b306000041000000000754004b00000000070000190000000007068019000007b305500197000007b308400197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000506004b0000000b05000029000000bc0000c13d0000000a060000290000000006060433000000800700043d0000000908000029000000000808043300000007090000290000000009090433000000060a000029000000000a0a04330000000005540019000000000451034f000000000404043b000007b20b40009c000000bc0000213d000000000b4300490000002005500039000007b30c000041000000000db5004b000000000d000019000000000d0c2019000007b30bb00197000007b30e500197000000000fbe004b000000000c008019000000000bbe013f000007b30bb0009c000000000c0dc019000000000b0c004b000000bc0000c13d0000000006760019000000000686001900000000069600190000000006a60019000000000646001900000000070204330000000006760019000000400700043d000007b206600197000000380860008c00000a860000413d0000002009600270000007ae0860009c000000000906a019000007ae0860009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000007b60a70009c000003fa0000213d000000000898019f0000004009700039000000400090043f000000000931034f000000020380003a00000000033704360000000009900350000000000909043b0000000000930435000004e80000613d000007b709900197000000f80a80021000000000099a019f000007bd099001c700000000009304350000000303800210000000f80330015f00000000033601cf0000002106700039000000000036043500000a960000013d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000400400043d000000000201043b000000800120008c00000a250000413d0000008001200270000007b80320009c000000000102a019000007b80320009c0000000003000019000000100300203900000008053001bf000007b20610009c000000000503a0190000004003100270000007b20610009c000000000301a01900000004015001bf000007ae0630009c000000000105a0190000002006300270000007ae0530009c000000000603a01900000002051001bf0000ffff0360008c000000000501a0190000001001600270000000000106a019000000ff0110008c00000001055020390000004101500039000000080110017f0000000001140019000000000341004b00000000030000190000000103004039000007b20610009c000003fa0000213d0000000103300190000003fa0000c13d000000400010043f00000002015000390000000006140436000000010100036700000000030000310000002107500039000000050770027200000a130000613d000000000831034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000a0b0000413d000000000700004b00000a150000613d0000000007040433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000025201cf000000ff0550008c0000000002002019000000210540003900000a380000013d000007b60140009c000003fa0000213d0000004001400039000000400010043f000000010100003a000000000514043600000000030000310000000101000367000000000631034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807200210000007b308000041000000000202004b000000000807c019000007b702600197000000000282019f0000000000250435000000400200043d00000020052000390000000006040433000000000706004b00000a460000613d000000000700001900000000085700190000002007700039000000000947001900000000090904330000000000980435000000000867004b00000a3f0000413d0000000004560019000007d105000041000000000054043500000000042400490000001e0540008a00000000005204350000002104400039000000080540017f0000000004250019000000000554004b00000000050000190000000105004039000007b20640009c000003fa0000213d0000000105500190000003fa0000c13d0000000c06000029000001c405600039000000400040043f000000000451034f0000000005630049000000230550008a000000000404043b000009730000013d000000380840008c00000caa0000413d0000002009400270000007ae0840009c000000000904a019000007ae0840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000007b60a70009c000003fa0000213d000000000898019f0000004009700039000000400090043f000000000a21034f000000020980003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000007b70aa00197000000f80b800210000000000aab019f000007bb0aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf00000021097000390000000000890435000000000807001900000cbb0000013d000007b60870009c000003fa0000213d0000004008700039000000400080043f000000000831034f000000010300003a00000000033704360000000008800350000000000808043b0000000000830435000004e80000613d000007b708800197000000f806600210000000000686019f000007bc066000410000000000630435000000400300043d00000020063000390000000008070433000000000908004b00000aa30000613d0000000009000019000000000a6900190000002009900039000000000b790019000000000b0b04330000000000ba0435000000000a89004b00000a9c0000413d00000000076800190000000000070435000000800800043d000000000908004b00000ab00000613d0000000009000019000000000a790019000000a00b900039000000000b0b04330000000000ba04350000002009900039000000000a89004b00000aa90000413d000000000778001900000000000704350000000a0c00002900000000080c0433000000000908004b00000abe0000613d0000000009000019000000000a7900190000002009900039000000000bc90019000000000b0b04330000000000ba0435000000000a89004b00000ab70000413d00000000077800190000000000070435000000090c00002900000000080c0433000000000908004b00000acc0000613d0000000009000019000000000a7900190000002009900039000000000bc90019000000000b0b04330000000000ba0435000000000a89004b00000ac50000413d00000000077800190000000000070435000000070c00002900000000080c0433000000000908004b00000ada0000613d0000000009000019000000000a7900190000002009900039000000000bc90019000000000b0b04330000000000ba0435000000000a89004b00000ad30000413d00000000077800190000000000070435000000060c00002900000000080c0433000000000908004b00000ae80000613d0000000009000019000000000a7900190000002009900039000000000bc90019000000000b0b04330000000000ba0435000000000a89004b00000ae10000413d000000000551034f00000000017800190000001f0740018f0000000000010435000000050840027200000af70000613d0000000009000019000000050a900210000000000ba10019000000000aa5034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b00000aef0000413d000000000907004b00000b060000613d0000000508800210000000000585034f00000000088100190000000307700210000000000908043300000000097901cf000000000979022f000000000505043b0000010007700089000000000575022f00000000057501cf000000000595019f0000000000580435000000000141001900000000000104350000000004020433000000000504004b00000b130000613d000000000500001900000000071500190000002005500039000000000825001900000000080804330000000000870435000000000745004b00000b0c0000413d000000000114001900000000000104350000000001310049000000200210008a00000000002304350000001f01100039000000080210017f0000000001320019000000000221004b00000000020000190000000102004039000007b20410009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000007ae01000041000007ae0260009c000000000601801900000040026002100000000003030433000007ae0430009c00000000030180190000006003300210000000000223019f0000000003000414000007ae0430009c0000000003018019000000c001300210000000000121019f000007bf011001c700008010020000391eb21ea80000040f00000001022001900000000b030000290000000c02000029000000bc0000613d000c00000002001d0000000102000367000b00000003001d000000000332034f000000000101043b000a00000001001d001100000001001d000000000103043b000000010310008c00000e010000213d000000000301004b00000eca0000613d000000010110008c00000f760000c13d0000000001000415000a00000001001d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000400300043d000000000401043b000000800140008c00000fde0000413d0000008001400270000007b80240009c000000000104a019000007b80240009c0000000002000019000000100200203900000008052001bf000007b20610009c000000000502a0190000004002100270000007b20610009c000000000201a01900000004015001bf000007ae0620009c000000000105a0190000002006200270000007ae0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000007b20610009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f00000002015000390000000006130436000000010100036700000000020000310000002107500039000000050770027200000b8e0000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000b860000413d000000000700004b00000b900000613d0000000007030433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c0000000004002019000000210530003900000ff10000013d000007ae01100197000000000113034f0000000002620049000007ae0220019700000000012103df000000c002500210000007c102200197000007c2022001c700000000012103af00008010020000391eb21ead0000040f00000000030100190000006003300270000007ae04300197000000010220019000000d1e0000613d0000003f02400039000007c302200197000000400500043d0000000002250019000000000352004b00000000030000190000000103004039000007b20620009c000003fa0000213d0000000103300190000003fa0000c13d000000400020043f000000000245043600000001030003670000001f06400039000000050660027200000bcb0000613d000000000730036800000000080000190000000509800210000000000a920019000000000997034f000000000909043b00000000009a04350000000108800039000000000968004b00000bc30000413d000000000600004b00000bcd0000613d0000001f0640018f000000050440027200000bd90000613d000000000700001900000005087002100000000009820019000000000881034f000000000808043b00000000008904350000000107700039000000000847004b00000bd10000413d000000000706004b00000be80000613d0000000504400210000000000141034f00000000044200190000000306600210000000000704043300000000076701cf000000000767022f000000000101043b0000010006600089000000000161022f00000000016101cf000000000171019f00000000001404350000000001050433000000200110008c00000c980000c13d0000000c0b0000290000006401b00039000000000113034f0000004404b00039000000000543034f0000002404b00039000000000443034f0000012406b00039000000000663034f0000010407b00039000000000773034f000000e408b00039000000000883034f000000c409b00039000000000993034f000000a40ab00039000000000aa3034f000000840bb00039000000000bb3034f0000000b03300360000000000303043b000000000404043b000000000505043b000000000c01043b000000000b0b043b000000000a0a043b000000000909043b000000000808043b000000000707043b000000000606043b0000000002020433000000400100043d000001c00d10003900000000002d0435000001a0021000390000000a0d0000290000000000d204350000018002100039000000090d0000290000000000d2043500000160021000390000000000620435000001400210003900000000007204350000012002100039000000000082043500000100021000390000000000920435000000e0021000390000000000a20435000000c0021000390000000000b20435000000a0021000390000000000c204350000008002100039000000000052043500000060021000390000000000420435000000400210003900000000003204350000002002100039000007c8030000410000000000320435000001c0030000390000000000310435000007c90310009c000003fa0000213d000001e003100039000000400030043f000007ae04000041000007ae0320009c000000000204801900000040022002100000000001010433000007ae0310009c00000000010480190000006001100210000000000121019f0000000002000414000007ae0320009c0000000002048019000000c002200210000000000112019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d000000000101043b000900000001001d000000400100043d000a00000001001d000007b40100004100000000001004390000000001000414000007ae0210009c000007ae01008041000000c001100210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d0000000a040000290000002002400039000000000101043b000007ca030000410000000000320435000000800340003900000000001304350000006001400039000007cb0300004100000000003104350000004001400039000007cc03000041000000000031043500000080010000390000000000140435000007cd0140009c000003fa0000213d0000000a04000029000000a001400039000000400010043f000007ae01000041000007ae0320009c000000000201801900000040022002100000000003040433000007ae0430009c00000000030180190000006003300210000000000223019f0000000003000414000007ae0430009c0000000003018019000000c001300210000000000121019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d000000000301043b000000400100043d0000004202100039000000090400002900000000004204350000002002100039000007ce0400004100000000004204350000002204100039000000000034043500000042030000390000000000310435000007cf0310009c000003fa0000213d0000008003100039000000400030043f000007ae03000041000007ae0420009c000000000203801900000040022002100000000001010433000007ae0410009c00000000010380190000006001100210000000000121019f0000000002000414000007ae0420009c0000000002038019000000c002200210000000000112019f00000b310000013d000000400100043d0000004402100039000007c503000041000000000032043500000024021000390000001f030000390000000000320435000007c6020000410000000000210435000000040210003900000020030000390000000000320435000007ae02000041000007ae0310009c00000000010280190000004001100210000007c7011001c700001eb400010430000007b60870009c000003fa0000213d0000004008700039000000400080043f000000000921034f000000010800003a00000000088704360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a400210000007b7099001970000000009a9019f000007b30990016700000000009804350000000008070019000000400700043d000007b60970009c000003fa0000213d0000004009700039000000400090043f000000000221034f000000010c00003a0000000009c704360000000002200350000000000b02043b0000000000b90435000004e80000613d000007b702b00197000007bc0a2001c70000000000a9043500000000090604330000000009490019000000000a0804330000000009a90019000000000a0704330000000009a90019000000400a00043d000007b209900197000000380d90008c00000d390000413d000000200d900270000007ae0c90009c000000000d09a019000007ae0c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d002039000007b60ea0009c000003fa0000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000004e80000613d000000f80bc0021000000000022b019f000007bd022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a00039000000000029043500000d460000013d000000380840008c00000db50000413d0000002009400270000007ae0840009c000000000904a019000007ae0840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000007b60a60009c000003fa0000213d000000000898019f0000004009600039000000400090043f000000000a21034f000000020980003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000007b70aa00197000000f80b800210000000000aab019f000007bb0aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf00000021096000390000000000890435000000000806001900000dc60000013d0000001f0340018f000000050240027200000d290000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b00000d220000413d000000000503004b00000d370000613d00000003033002100000000502200210000000000502043300000000053501cf000000000535022f000000000121034f000000000101043b0000010003300089000000000131022f00000000013101cf000000000151019f0000000000120435000000600140021000001eb400010430000007b60da0009c000003fa0000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000004e80000613d000000f809900210000000000229019f000007bc0220004100000000002d0435000000400200043d0000002009200039000007be0b0000410000000000b90435000000210b200039000000000c0a0433000000000d0c004b00000d560000613d000000000d000019000000000ebd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ecd004b00000d4f0000413d000000000abc001900000000000a0435000000000b060433000000000c0b004b00000d630000613d000000000c000019000000000dac0019000000200cc00039000000000e6c0019000000000e0e04330000000000ed0435000000000dbc004b00000d5c0000413d0000000006ab00190000000000060435000000000a080433000000000b0a004b00000d700000613d000000000b000019000000000c6b0019000000200bb00039000000000d8b0019000000000d0d04330000000000dc0435000000000cab004b00000d690000413d000000000551034f00000000016a00190000001f0640018f0000000000010435000000050840027200000d7f0000613d000000000a000019000000050ba00210000000000cb10019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b00000d770000413d000000000a06004b00000d8e0000613d0000000508800210000000000585034f00000000088100190000000306600210000000000a080433000000000a6a01cf000000000a6a022f000000000505043b0000010006600089000000000565022f00000000056501cf0000000005a5019f0000000000580435000000000141001900000000000104350000000004070433000000000504004b00000d9b0000613d000000000500001900000000061500190000002005500039000000000875001900000000080804330000000000860435000000000645004b00000d940000413d000000000114001900000000000104350000000001210049000000200410008a00000000004204350000001f01100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000007b20410009c000003fa0000213d0000000103300190000003fa0000c13d000000400010043f000007ae01000041000007ae0390009c000000000901801900000040039002100000000002020433000007ae0420009c00000000020180190000006002200210000000000232019f00000b2c0000013d000007b60860009c000003fa0000213d0000004008600039000000400080043f000000000921034f000000010800003a00000000088604360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a400210000007b7099001970000000009a9019f000007b30990016700000000009804350000000008060019000000400600043d000007b60960009c000003fa0000213d0000004009600039000000400090043f000000000221034f000000010c00003a0000000009c604360000000002200350000000000b02043b0000000000b90435000004e80000613d000007b702b00197000007bc0a2001c70000000000a9043500000000090704330000000009490019000000000a0804330000000009a90019000000000a0604330000000009a90019000000400a00043d000007b209900197000000380d90008c00000e580000413d000000200d900270000007ae0c90009c000000000d09a019000007ae0c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d002039000007b60ea0009c000003fa0000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000004e80000613d000000f80bc0021000000000022b019f000007bd022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a00039000000000029043500000e650000013d000000020310008c00000f1c0000613d000000710110008c00000f760000c13d0000000b09000029000001e001900039000000000312034f00000000010000310000000c0410006a000000230440008a000000000303043b000007b305000041000000000643004b00000000060000190000000006058019000007b304400197000007b307300197000000000847004b0000000005008019000000000447013f000007b30440009c000000000506c019000000000405004b000000bc0000c13d0000000003930019000000000232034f000000000202043b000007b20420009c000000bc0000213d00000000042100490000002001300039000007b303000041000000000541004b00000000050000190000000005032019000007b304400197000007b306100197000000000746004b0000000003008019000000000446013f000007b30440009c000000000305c019000000000303004b000000bc0000c13d1eb21e100000040f000000400200043d00000040032000390000000000130435000000400100003900000000011204360000000a030000290000000000310435000007d50320009c000003fa0000213d0000006003200039000000400030043f000007ae03000041000007ae0410009c000000000103801900000040011002100000000002020433000007ae0420009c00000000020380190000006002200210000000000112019f0000000002000414000007ae0420009c0000000002038019000000c002200210000000000112019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d000000000101043b000000400200043d0000002003200039000000110400002900000000004304350000000000120435000007ae01000041000007ae0320009c00000000020180190000004001200210000007d6011001c700001eb30001042e000007b60da0009c000003fa0000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000004e80000613d000000f809900210000000000229019f000007bc0220004100000000002d0435000000400200043d0000002009200039000007bf0b0000410000000000b90435000000210b200039000000000c0a0433000000000d0c004b00000e750000613d000000000d000019000000000ebd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ecd004b00000e6e0000413d000000000abc001900000000000a0435000000000b070433000000000c0b004b00000e820000613d000000000c000019000000000dac0019000000200cc00039000000000e7c0019000000000e0e04330000000000ed0435000000000dbc004b00000e7b0000413d0000000007ab00190000000000070435000000000a080433000000000b0a004b00000e8f0000613d000000000b000019000000000c7b0019000000200bb00039000000000d8b0019000000000d0d04330000000000dc0435000000000cab004b00000e880000413d000000000551034f00000000017a00190000001f0740018f0000000000010435000000050840027200000e9e0000613d000000000a000019000000050ba00210000000000cb10019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b00000e960000413d000000000a07004b00000ead0000613d0000000508800210000000000585034f00000000088100190000000307700210000000000a080433000000000a7a01cf000000000a7a022f000000000505043b0000010007700089000000000575022f00000000057501cf0000000005a5019f0000000000580435000000000141001900000000000104350000000004060433000000000504004b00000eba0000613d000000000500001900000000071500190000002005500039000000000865001900000000080804330000000000870435000000000745004b00000eb30000413d000000000114001900000000000104350000000001210049000000200410008a00000000004204350000001f01100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000007b20410009c000003fa0000213d0000000103300190000003fa0000c13d00000daa0000013d000000400100043d000a00000001001d0000000b010000290000010004100039000000000142034f000000000301043b000000800130008c00000f7d0000413d0000008001300270000007b80530009c000000000103a019000007b80530009c0000000005000019000000100500203900000008065001bf000007b20710009c000000000605a0190000004005100270000007b20710009c000000000501a01900000004016001bf000007ae0750009c000000000106a0190000002006500270000007ae0750009c000000000605a01900000002051001bf0000ffff0760008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004106500039000000000116016f0000000a011000290000000a0610006c00000000060000190000000106004039000007b20710009c000003fa0000213d0000000106600190000003fa0000c13d000000400010043f00000002015000390000000a06000029000000000616043600000000010000310000002107500039000000050770027200000f080000613d000000000812034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000f000000413d000000000700004b00000f0a0000613d0000000a070000290000000007070433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000035301cf000000ff0550008c00000000030020190000000a05000029000000210550003900000f910000013d0000000001000415000a00000001001d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000400300043d000000000401043b000000800140008c0000103f0000413d0000008001400270000007b80240009c000000000104a019000007b80240009c0000000002000019000000100200203900000008052001bf000007b20610009c000000000502a0190000004002100270000007b20610009c000000000201a01900000004015001bf000007ae0620009c000000000105a0190000002006200270000007ae0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000007b20610009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f00000002015000390000000006130436000000010100036700000000020000310000002107500039000000050770027200000f640000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000f5c0000413d000000000700004b00000f660000613d0000000007030433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c00000000040020190000002105300039000010520000013d000000400100043d0000004402100039000007d70300004100000000003204350000002402100039000000130300003900000c9e0000013d0000000a01000029000007b60110009c000003fa0000213d0000000a050000290000004001500039000000400010043f000000010100003a00000000051504360000000001000031000000000612034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807300210000007b308000041000000000303004b000000000807c019000007b703600197000000000383019f0000000000350435000000400300043d000000600440008a000000000542034f000000000505043b000000800650008c000010a00000413d0000008006500270000007b80750009c000000000605a019000007b80750009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007730019000000000837004b00000000080000190000000108004039000007b20970009c000003fa0000213d0000000108800190000003fa0000c13d000000400070043f000000020760003900000000077304360000002108600039000000050880027200000fcc0000613d000000000912034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b00000fc40000413d000000000800004b00000fce0000613d0000000008030433000000000808004b000004e80000613d0000000008070433000007b708800197000000f809600210000000000889019f000007b90880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106300039000010b10000013d000007b60130009c000003fa0000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000101000367000000000621034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807400210000007b308000041000000000404004b000000000807c019000007b704600197000000000484019f0000000000450435000000400500043d0000000c040000290000010404400039000000000641034f000000000606043b000000800760008c000010fe0000413d0000008007600270000007b80860009c000000000706a019000007b80860009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008850019000000000958004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f00000002087000390000000008850436000000210970003900000005099002720000102d0000613d000000000a21034f000000000b000019000000050cb00210000000000dc80019000000000cca034f000000000c0c043b0000000000cd0435000000010bb00039000000000c9b004b000010250000413d000000000900004b0000102f0000613d0000000009050433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c000000000600201900000021075000390000110f0000013d000007b60130009c000003fa0000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000101000367000000000621034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807400210000007b308000041000000000404004b000000000807c019000007b704600197000000000484019f0000000000450435000000400500043d0000000c040000290000010404400039000000000641034f000000000606043b000000800760008c0000115c0000413d0000008007600270000007b80860009c000000000706a019000007b80860009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008850019000000000958004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f00000002087000390000000008850436000000210970003900000005099002720000108e0000613d000000000a21034f000000000b000019000000050cb00210000000000dc80019000000000cca034f000000000c0c043b0000000000cd0435000000010bb00039000000000c9b004b000010860000413d000000000900004b000010900000613d0000000009050433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c000000000600201900000021075000390000116d0000013d000007b60630009c000003fa0000213d0000004006300039000000400060043f000000000712034f000000010600003a00000000066304360000000007700350000000000707043b0000000000760435000004e80000613d000000f808500210000007b309000041000000000505004b000000000908c019000007b705700197000000000595019f0000000000560435000000400440008a000000000542034f000000400400043d000000000505043b000000800650008c000011ba0000413d0000008006500270000007b80750009c000000000605a019000007b80750009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007740019000000000847004b00000000080000190000000108004039000007b20970009c000003fa0000213d0000000108800190000003fa0000c13d000000400070043f0000000207600039000000000774043600000021086000390000000508800272000010ec0000613d000000000912034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b000010e40000413d000000000800004b000010ee0000613d0000000008040433000000000808004b000004e80000613d0000000008070433000007b708800197000000f809600210000000000889019f000007b90880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106400039000011cb0000013d000007b60750009c000003fa0000213d0000004007500039000000400070043f000000000821034f000000010700003a00000000077504360000000008800350000000000808043b0000000000870435000004e80000613d000000f809600210000007b30a000041000000000606004b000000000a09c019000007b7068001970000000006a6019f0000000000670435000000400600043d000000600440008a000000000741034f000000000707043b000000800870008c0000125b0000413d0000008008700270000007b80970009c000000000807a019000007b80970009c00000000090000190000001009002039000000080a9001bf000007b20b80009c000000000a09a0190000004009800270000007b20b80009c000000000908a019000000040ba001bf000007ae0890009c000000000b0aa019000000200a900270000007ae0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009960019000000000a69004b000000000a000019000000010a004039000007b20b90009c000003fa0000213d000000010aa00190000003fa0000c13d000000400090043f00000002098000390000000009960436000000210a800039000000050aa002720000114a0000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000011420000413d000000000a00004b0000114c0000613d000000000a060433000000000a0a004b000004e80000613d000000000a090433000007b70aa00197000000f80b800210000000000aab019f000007b90aa000410000000000a904350000000308800210000000f80880008900000000078701cf000000ff0880008c000000000700201900000021086000390000126c0000013d000007b60750009c000003fa0000213d0000004007500039000000400070043f000000000821034f000000010700003a00000000077504360000000008800350000000000808043b0000000000870435000004e80000613d000000f809600210000007b30a000041000000000606004b000000000a09c019000007b7068001970000000006a6019f0000000000670435000000400600043d000000400440008a000000000741034f000000000707043b000000800870008c000012b90000413d0000008008700270000007b80970009c000000000807a019000007b80970009c00000000090000190000001009002039000000080a9001bf000007b20b80009c000000000a09a0190000004009800270000007b20b80009c000000000908a019000000040ba001bf000007ae0890009c000000000b0aa019000000200a900270000007ae0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009960019000000000a69004b000000000a000019000000010a004039000007b20b90009c000003fa0000213d000000010aa00190000003fa0000c13d000000400090043f00000002098000390000000009960436000000210a800039000000050aa00272000011a80000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000011a00000413d000000000a00004b000011aa0000613d000000000a060433000000000a0a004b000004e80000613d000000000a090433000007b70aa00197000000f80b800210000000000aab019f000007b90aa000410000000000a904350000000308800210000000f80880008900000000078701cf000000ff0880008c00000000070020190000002108600039000012ca0000013d000007b60640009c000003fa0000213d0000004006400039000000400060043f000000000712034f000000010600003a00000000066404360000000007700350000000000707043b0000000000760435000004e80000613d000000f808500210000007b309000041000000000505004b000000000908c019000007b705700197000000000595019f0000000000560435000000400500043d000900000005001d00000020055000390000000006030433000000000706004b000011da0000613d000000000700001900000000085700190000002007700039000000000937001900000000090904330000000000980435000000000867004b000011d30000413d000000000356001900000000000304350000000005040433000000000605004b000011e70000613d000000000600001900000000073600190000002006600039000000000846001900000000080804330000000000870435000000000756004b000011e00000413d0000000003350019000000000003043500000009050000290000000003530049000000200430008a00000000004504350000001f033000390007002000000092000000070330017f0000000004530019000000000334004b00000000030000190000000103004039000800000004001d000007b20440009c000003fa0000213d0000000103300190000003fa0000c13d0000000803000029000000400030043f000007b60330009c000003fa0000213d0000000c060000290000004403600039000000000332034f000000000303043b00000008070000290000004004700039000000400040043f0000002004700039000007ba050000410000000000540435000000150400003900000000004704350000006003300210000000210470003900000000003404350000012403600039000000000432034f000000400500043d000600000005001d000000000404043b000000800540008c000013e70000413d0000008005400270000007b80640009c000000000504a019000007b80640009c0000000006000019000000100600203900000008076001bf000007b20850009c000000000706a0190000004006500270000007b20850009c000000000605a01900000004087001bf000007ae0560009c000000000807a0190000002007600270000007ae0560009c000000000706a01900000002058001bf0000ffff0670008c000000000508a0190000001006700270000000000607a019000000ff0660008c00000001055020390000004106500039000000070660017f0000000606600029000000060760006c00000000070000190000000107004039000007b20860009c000003fa0000213d0000000107700190000003fa0000c13d000000400060043f00000002065000390000000607000029000000000667043600000021075000390000000507700272000012470000613d000000000812034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b0000123f0000413d000000000700004b000012490000613d00000006070000290000000007070433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c000000000400201900000006050000290000002105500039000013fa0000013d000007b60860009c000003fa0000213d0000004008600039000000400080043f000000000921034f000000010800003a00000000088604360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a700210000007b30b000041000000000707004b000000000b0ac019000007b7079001970000000007b7019f0000000000780435000000400700043d000000400440008a000000000841034f000000000808043b000000800980008c000013170000413d0000008009800270000007b80a80009c000000000908a019000007b80a80009c000000000a000019000000100a002039000000080ba001bf000007b20c90009c000000000b0aa019000000400a900270000007b20c90009c000000000a09a019000000040cb001bf000007ae09a0009c000000000c0ba019000000200ba00270000007ae09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa70019000000000b7a004b000000000b000019000000010b004039000007b20ca0009c000003fa0000213d000000010bb00190000003fa0000c13d0000004000a0043f000000020a900039000000000aa70436000000210b900039000000050bb00272000012a70000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b0000129f0000413d000000000b00004b000012a90000613d000000000b070433000000000b0b004b000004e80000613d000000000b0a0433000007b70bb00197000000f80c900210000000000bbc019f000007b90bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c00000000080020190000002109700039000013280000013d000007b60860009c000003fa0000213d0000004008600039000000400080043f000000000921034f000000010800003a00000000088604360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a700210000007b30b000041000000000707004b000000000b0ac019000007b7079001970000000007b7019f0000000000780435000000400700043d000000200440008a000000000841034f000000000808043b000000800980008c000013880000413d0000008009800270000007b80a80009c000000000908a019000007b80a80009c000000000a000019000000100a002039000000080ba001bf000007b20c90009c000000000b0aa019000000400a900270000007b20c90009c000000000a09a019000000040cb001bf000007ae09a0009c000000000c0ba019000000200ba00270000007ae09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa70019000000000b7a004b000000000b000019000000010b004039000007b20ca0009c000003fa0000213d000000010bb00190000003fa0000c13d0000004000a0043f000000020a900039000000000aa70436000000210b900039000000050bb00272000013050000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b000012fd0000413d000000000b00004b000013070000613d000000000b070433000000000b0b004b000004e80000613d000000000b0a0433000007b70bb00197000000f80c900210000000000bbc019f000007b90bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c00000000080020190000002109700039000013990000013d000007b60970009c000003fa0000213d0000004009700039000000400090043f000000000a21034f000000010900003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000000f80b800210000007b30c000041000000000808004b000000000c0bc019000007b708a001970000000008c8019f0000000000890435000000400900043d000007b60890009c000003fa0000213d000000200840008a000000000881034f000000000808043b000000400a9000390000004000a0043f000000200a900039000007ba0b0000410000000000ba0435000000150a0000390000000000a904350000006008800210000000210a90003900000000008a0435000000c004400039000000000441034f000000400800043d000000000404043b000900000004001d000000800a40008c000014b60000413d0000000904000029000000800a400270000007b80b40009c000000000a04a019000007b80b40009c000000000b000019000000100b002039000000080cb001bf000007b20da0009c000000000c0ba019000000400ba00270000007b20da0009c000000000b0aa019000000040dc001bf000007ae0ab0009c000000000d0ca019000000200cb00270000007ae0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000007b20db0009c000003fa0000213d000000010cc00190000003fa0000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc00272000013750000613d000000000d21034f000000000e000019000000050fe002100000000004fb0019000000000ffd034f000000000f0f043b0000000000f40435000000010ee000390000000004ce004b0000136d0000413d000000000400004b000013770000613d0000000004080433000000000404004b000004e80000613d00000000040b0433000007b704400197000000f80ca0021000000000044c019f000007b90440004100000000004b04350000000304a00210000000f804400089000000090a4001ef000000ff0440008c000000000a00201900000021048000390000000000a40435000014c90000013d000007b60970009c000003fa0000213d0000004009700039000000400090043f000000000a21034f000000010900003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000000f80b800210000007b30c000041000000000808004b000000000c0bc019000007b708a001970000000008c8019f0000000000890435000000400800043d00090040004000920000000909100360000000000909043b000000800a90008c000014410000413d000000800a900270000007b80b90009c000000000a09a019000007b80b90009c000000000b000019000000100b002039000000080cb001bf000007b20da0009c000000000c0ba019000000400ba00270000007b20da0009c000000000b0aa019000000040dc001bf000007ae0ab0009c000000000d0ca019000000200cb00270000007ae0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000007b20db0009c000003fa0000213d000000010cc00190000003fa0000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc00272000013d40000613d000000000d21034f000000000e000019000000050fe002100000000004fb0019000000000ffd034f000000000f0f043b0000000000f40435000000010ee000390000000004ce004b000013cc0000413d000000000400004b000013d60000613d0000000004080433000000000404004b000004e80000613d00000000040b0433000007b704400197000000f80ca0021000000000044c019f000007b90440004100000000004b04350000000304a00210000000f80440008900000000094901cf000000ff0440008c000000000900201900000021048000390000000000940435000014530000013d0000000605000029000007b60550009c000003fa0000213d00000006070000290000004005700039000000400050043f000000000612034f000000010500003a00000000055704360000000006600350000000000606043b0000000000650435000004e80000613d000000f807400210000007b308000041000000000404004b000000000807c019000007b704600197000000000484019f00000000004504350000000b0a0000290000000006a10049000000a004300039000000000342034f000000000503043b0000001f0360008a000007b306300197000007b307500197000007b308000041000000000967004b00000000090000190000000009084019000000000667013f000000000735004b0000000008004019000007b30660009c000000000908c019000000000609004b000000bc0000c13d0000000006a50019000000000562034f000000000505043b000007b20750009c000000bc0000213d00000000075100490000002006600039000007b308000041000000000976004b00000000090000190000000009082019000007b307700197000007b30a600197000000000b7a004b000000000800801900000000077a013f000007b30770009c000000000809c019000000000708004b000000bc0000c13d000000010750008c000016330000c13d000000000562034f000000000505043b000000010600008a000007b307000041000000000665004b00000000060000190000000006072019000007b305500197000007b30850009c0000000007008019000007b305500167000007b30550009c000000000706c019000500600000003d000000000507004b000016710000c13d000000400500043d000500000005001d000007b60550009c000003fa0000213d00000005070000290000004005700039000000400050043f0000002005700039000007b906000041000000000065043500000001050000390000000000570435000016710000013d000007b60480009c000003fa0000213d0000004004800039000000400040043f000000000421034f000000010a00003a000000000aa804360000000004400350000000000b04043b0000000000ba0435000004e80000613d000000f804900210000007b30c000041000000000909004b000000000c04c019000007b704b001970000000004c4019f00000000004a0435000000400a00043d000007b604a0009c000003fa0000213d000000090c0000290000002004c0008a000000000441034f000000000404043b0000004009a00039000000400090043f0000002009a00039000007ba0b0000410000000000b90435000000150900003900000000009a043500000060044002100000002109a000390000000000490435000000c004c00039000000000441034f000000400900043d000000000404043b000900000004001d000000800b40008c0000156e0000413d0000000904000029000000800b400270000007b80c40009c000000000b04a019000007b80c40009c000000000c000019000000100c002039000000080dc001bf000007b20eb0009c000000000d0ca019000000400cb00270000007b20eb0009c000000000c0ba019000000040ed001bf000007ae0bc0009c000000000e0da019000000200dc00270000007ae0bc0009c000000000d0ca0190000000204e001bf0000ffff0cd0008c00000000040ea019000000100cd00270000000000c0da019000000ff0cc0008c0000000104402039000000200c00008a000800000004001d000000410d400039000000000ccd016f000000000cc90019000000000d9c004b000000000d000019000000010d004039000007b20ec0009c000003fa0000213d000000010dd00190000003fa0000c13d0000004000c0043f0000000804000029000000020c400039000000000cc90436000000210d400039000000050dd00272000014a20000613d000000000e21034f000000000f0000190000000504f00210000000000b4c001900000000044e034f000000000404043b00000000004b0435000000010ff000390000000004df004b0000149a0000413d000000000400004b000014a40000613d0000000004090433000000000404004b000004e80000613d00000000040c0433000007b704400197000000080d000029000000f80bd0021000000000044b019f000007b90440004100000000004c04350000000304d00210000000f804400089000000090b4001ef000000ff0440008c000000000b00201900000021049000390000000000b40435000015810000013d000007b60480009c000003fa0000213d0000004004800039000000400040043f000000000421034f000000010a00003a000000000aa804360000000004400350000000000b04043b0000000000ba0435000004e80000613d000000090d000029000000f804d00210000007b30c000041000000000d0d004b000000000c04c019000007b704b001970000000004c4019f00000000004a0435000000400400043d000000200a400039000000000b030433000000000c0b004b000014d60000613d000000000c000019000000000dac0019000000200cc00039000000000e3c0019000000000e0e04330000000000ed0435000000000dbc004b000014cf0000413d0000000003ab00190000000000030435000000000a050433000000000b0a004b000014e30000613d000000000b000019000000000c3b0019000000200bb00039000000000d5b0019000000000d0d04330000000000dc0435000000000cab004b000014dc0000413d00000000033a001900000000000304350000000005060433000000000a05004b000014f00000613d000000000a000019000000000b3a0019000000200aa00039000000000c6a0019000000000c0c04330000000000cb0435000000000b5a004b000014e90000413d000000000335001900000000000304350000000005070433000000000605004b000014fd0000613d0000000006000019000000000a3600190000002006600039000000000b760019000000000b0b04330000000000ba0435000000000a56004b000014f60000413d000000000335001900000000000304350000000005090433000000000605004b0000150a0000613d000000000600001900000000073600190000002006600039000000000a960019000000000a0a04330000000000a70435000000000756004b000015030000413d000000000335001900000000000304350000000005080433000000000605004b000015170000613d000000000600001900000000073600190000002006600039000000000986001900000000090904330000000000970435000000000756004b000015100000413d000000000335001900000000000304350000000003430049000000200530008a00000000005404350000001f05300039000000200300008a000000000535016f0000000007450019000000000557004b00000000050000190000000105004039000007b20670009c000003fa0000213d0000000105500190000003fa0000c13d000000400070043f0000000b0d0000290000000006d200490000000c05000029000001c40c5000390000000005c1034f000000000505043b0000001f0960008a000007b306900197000007b308500197000007b30a000041000000000b68004b000000000b000019000000000b0a4019000000000668013f000000000895004b000000000a004019000007b30660009c000000000b0ac01900000000060b004b000000bc0000c13d0000000006d50019000000000561034f000000000505043b000007b20850009c000000bc0000213d00000000085200490000002006600039000007b30a000041000000000b86004b000000000b000019000000000b0a2019000007b308800197000c00000006001d000007b30d600197000000000e8d004b000000000a00801900000000088d013f000007b30880009c000000000a0bc01900000000080a004b000000bc0000c13d000000010850008c000016e60000c13d0000000c08100360000000000808043b000000010a00008a000007b30b000041000000000aa8004b000000000a000019000000000a0b2019000007b308800197000007b30d80009c000000000b008019000007b308800167000007b30880009c000000000b0ac0190000006008000039000000000a0b004b0000171f0000c13d000007b60870009c000003fa0000213d0000004008700039000000400080043f0000002008700039000007b90a0000410000000000a804350000000108000039000000000087043500000000080700190000171f0000013d000007b60490009c000003fa0000213d0000004004900039000000400040043f000000000421034f000000010b00003a000000000bb904360000000004400350000000000c04043b0000000000cb0435000004e80000613d000000090e000029000000f804e00210000007b30d000041000000000e0e004b000000000d04c019000007b704c001970000000004d4019f00000000004b0435000000400400043d000000200b400039000000000c030433000000000d0c004b0000158e0000613d000000000d000019000000000ebd0019000000200dd00039000000000f3d0019000000000f0f04330000000000fe0435000000000ecd004b000015870000413d0000000003bc00190000000000030435000000000b050433000000000c0b004b0000159b0000613d000000000c000019000000000d3c0019000000200cc00039000000000e5c0019000000000e0e04330000000000ed0435000000000dbc004b000015940000413d00000000033b001900000000000304350000000005060433000000000b05004b000015a80000613d000000000b000019000000000c3b0019000000200bb00039000000000d6b0019000000000d0d04330000000000dc0435000000000c5b004b000015a10000413d000000000335001900000000000304350000000005070433000000000605004b000015b50000613d0000000006000019000000000b3600190000002006600039000000000c760019000000000c0c04330000000000cb0435000000000b56004b000015ae0000413d000000000335001900000000000304350000000005080433000000000605004b000015c20000613d000000000600001900000000073600190000002006600039000000000b860019000000000b0b04330000000000b70435000000000756004b000015bb0000413d0000000003350019000000000003043500000000050a0433000000000605004b000015cf0000613d0000000006000019000000000736001900000020066000390000000008a6001900000000080804330000000000870435000000000756004b000015c80000413d000000000335001900000000000304350000000005090433000000000605004b000015dc0000613d000000000600001900000000073600190000002006600039000000000896001900000000080804330000000000870435000000000756004b000015d50000413d000000000335001900000000000304350000000003430049000000200530008a00000000005404350000001f05300039000000200300008a000000000535016f0000000007450019000000000557004b00000000050000190000000105004039000007b20670009c000003fa0000213d0000000105500190000003fa0000c13d000000400070043f0000000b0d0000290000000006d200490000000c05000029000001c40c5000390000000005c1034f000000000505043b0000001f0960008a000007b306900197000007b308500197000007b30a000041000000000b68004b000000000b000019000000000b0a4019000000000668013f000000000895004b000000000a004019000007b30660009c000000000b0ac01900000000060b004b000000bc0000c13d0000000006d50019000000000561034f000000000505043b000007b20850009c000000bc0000213d00000000085200490000002006600039000007b30a000041000000000b86004b000000000b000019000000000b0a2019000007b308800197000c00000006001d000007b30d600197000000000e8d004b000000000a00801900000000088d013f000007b30880009c000000000a0bc01900000000080a004b000000bc0000c13d000000010850008c0000180d0000c13d0000000c08100360000000000808043b000000010a00008a000007b30b000041000000000aa8004b000000000a000019000000000a0b2019000007b308800197000007b30d80009c000000000b008019000007b308800167000007b30880009c000000000b0ac0190000006008000039000000000a0b004b000018460000c13d000007b60870009c000003fa0000213d0000004008700039000000400080043f0000002008700039000007b90a0000410000000000a80435000000010800003900000000008704350000000008070019000018460000013d000000400600043d000500000006001d000000380650008c0000165f0000413d0000002007500270000007ae0650009c000000000705a019000007ae0650009c0000000008000019000000040800203900000002068001bf0000ffff0970008c000000000608a0190000001008700270000000000807a019000000ff0780008c000000000700001900000001070020390000000508000029000007b60880009c000003fa0000213d000000000676019f00000005090000290000004007900039000000400070043f000000000812034f000000020760003a00000000077904360000000008800350000000000808043b0000000000870435000004e80000613d000007b708800197000000f809600210000000000889019f000007bb088001c700000000008704350000000306600210000000f80660015f00000000056501cf000000050600002900000021066000390000000000560435000016710000013d0000000506000029000007b60660009c000003fa0000213d00000005080000290000004006800039000000400060043f000000000712034f000000010600003a00000000066804360000000007700350000000000707043b0000000000760435000004e80000613d000000f805500210000007b707700197000000000557019f000007b30550016700000000005604350000002004400039000000000442034f000000000404043b000007b305000041000000000634004b00000000060000190000000006058019000007b303300197000007b307400197000000000837004b0000000005008019000000000337013f000007b30330009c000000000506c019000000000305004b0000000b03000029000000bc0000c13d0000000004340019000000000342034f000000000303043b000007b20530009c000000bc0000213d000000200530008c000000bc0000413d00000000053100490000002004400039000007b306000041000000000754004b00000000070000190000000007062019000007b305500197000007b308400197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000506004b000000bc0000c13d000000000542034f000000400600043d000400000006001d000000000505043b000000800650008c000017a80000413d0000008006500270000007b80750009c000000000605a019000007b80750009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c00000001066020390000004107600039000000070770017f0000000407700029000000040870006c00000000080000190000000108004039000007b20970009c000003fa0000213d0000000108800190000003fa0000c13d000000400070043f00000002076000390000000408000029000000000778043600000021086000390000000508800272000016d20000613d000000000912034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b000016ca0000413d000000000800004b000016d40000613d00000004080000290000000008080433000000000808004b000004e80000613d0000000008070433000007b708800197000000f809600210000000000889019f000007b90880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c000000000500201900000004060000290000002106600039000017bb0000013d000000380850008c0000170e0000413d000000200a500270000007ae0850009c000000000a05a019000007ae0850009c000000000b000019000000040b0020390000000208b001bf0000ffff0da0008c00000000080ba019000000100ba00270000000000b0aa019000000ff0ab0008c000000000a000019000000010a002039000007b60b70009c000003fa0000213d0000000008a8019f000000400a7000390000004000a0043f000000000b21034f000000020a80003a000000000aa70436000000000bb00350000000000b0b043b0000000000ba0435000004e80000613d000007b70bb00197000000f80d800210000000000bbd019f000007bb0bb001c70000000000ba04350000000308800210000000f80880015f00000000088501cf000000210a70003900000000008a043500000000080700190000171f0000013d000007b60870009c000003fa0000213d0000004008700039000000400080043f000000000a21034f000000010800003a0000000008870436000000000aa00350000000000a0a043b0000000000a80435000004e80000613d000000f80b500210000007b70aa00197000000000aba019f000007b30aa001670000000000a804350000000008070019000000400700043d000007b60a70009c000003fa0000213d000000400a7000390000004000a0043f000000000d21034f000000010600003a000700000006001d000000000a6704360000000006d003500008000000060353000000000606043b000900000006001d00000000006a0435000004e80000613d0000000906000029000007b706600197000600000006001d000007bc0b6001c70000000000ba0435000000200ac00039000000000aa1034f000000000c0a043b000007b30a000041000000000b9c004b000000000b000019000000000b0a8019000007b309900197000007b30fc00197000000000e9f004b000000000a00801900000000099f013f000007b30990009c000000000a0bc01900000000090a004b0000000b06000029000000bc0000c13d00000000096c0019000000000a91034f00000000060a043b000b00000006001d000007b20a60009c000000bc0000213d0000000b06000029000000200a60008c000000bc0000413d0000000b0220006a0000002006900039000007b309000041000000000a26004b000000000a000019000000000a092019000007b302200197000500000006001d000007b30b600197000000000c2b004b000000000900801900000000022b013f000007b30220009c00000000090ac019000000000209004b000000bc0000c13d0000000509100360000000400200043d000000000609043b000400000006001d000000800960008c000019140000413d00000004060000290000008009600270000007b80a60009c000000000906a019000007b80a60009c000000000a000019000000100a002039000000080ba001bf000007b20c90009c000000000b0aa019000000400a900270000007b20c90009c000000000a09a0190000000409b001bf000007ae0ca0009c00000000090ba019000000200ba00270000007ae0ca0009c000000000b0aa019000000020c9001bf0000ffff0ab0008c000000000c09a0190000001009b0027000000000090ba019000000ff0990008c000000010cc020390000004109c00039000000000939016f0000000009920019000000000a29004b000000000a000019000000010a004039000007b20b90009c000003fa0000213d000000010aa00190000003fa0000c13d000000400090043f0000000209c00039000000000f9204360000002109c000390000000509900272000017960000613d000000000e000019000000050ae00210000000000baf0019000000000aad034f000000000a0a043b0000000000ab0435000000010ee00039000000000a9e004b0000178e0000413d000000000600004b000017980000613d0000000009020433000000000909004b000004e80000613d00000000090f0433000007b709900197000000f80ac0021000000000099a019f000007b90990004100000000009f04350000000309c00210000000f809900089000000040a9001ef000000ff0990008c000000000a0020190000002109200039000019250000013d0000000406000029000007b60660009c000003fa0000213d00000004080000290000004006800039000000400060043f000000000712034f000000010600003a00000000066804360000000007700350000000000707043b0000000000760435000004e80000613d000000f808500210000007b309000041000000000505004b000000000908c019000007b705700197000000000595019f0000000000560435000000400530008c000000bc0000413d000000400500043d000300000005001d0000002004400039000000000542034f000000000505043b000000800650008c000018d10000413d0000008006500270000007b80750009c000000000605a019000007b80750009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c00000001066020390000004107600039000000070770017f0000000307700029000000030870006c00000000080000190000000108004039000007b20970009c000003fa0000213d0000000108800190000003fa0000c13d000000400070043f00000002076000390000000308000029000000000778043600000021086000390000000508800272000017f90000613d000000000112034f0000000009000019000000050a900210000000000ba70019000000000aa1034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b000017f10000413d000000000100004b000017fb0000613d00000003010000290000000001010433000000000101004b000004e80000613d0000000001070433000007b701100197000000f808600210000000000118019f000007b90110004100000000001704350000000301600210000000f80110008900000000051501cf000000ff0110008c000000000500201900000003010000290000002101100039000018e40000013d000000380850008c000018350000413d000000200a500270000007ae0850009c000000000a05a019000007ae0850009c000000000b000019000000040b0020390000000208b001bf0000ffff0da0008c00000000080ba019000000100ba00270000000000b0aa019000000ff0ab0008c000000000a000019000000010a002039000007b60b70009c000003fa0000213d0000000008a8019f000000400a7000390000004000a0043f000000000b21034f000000020a80003a000000000aa70436000000000bb00350000000000b0b043b0000000000ba0435000004e80000613d000007b70bb00197000000f80d800210000000000bbd019f000007bb0bb001c70000000000ba04350000000308800210000000f80880015f00000000088501cf000000210a70003900000000008a04350000000008070019000018460000013d000007b60870009c000003fa0000213d0000004008700039000000400080043f000000000a21034f000000010800003a0000000008870436000000000aa00350000000000a0a043b0000000000a80435000004e80000613d000000f80b500210000007b70aa00197000000000aba019f000007b30aa001670000000000a804350000000008070019000000400700043d000007b60a70009c000003fa0000213d000000400a7000390000004000a0043f000000000d21034f000000010600003a000700000006001d000000000f6704360000000006d003500008000000060353000000000606043b000900000006001d00000000006f0435000004e80000613d0000000906000029000007b706600197000600000006001d000007bc0b6001c70000000000bf0435000000200bc00039000000000bb1034f000000000c0b043b000007b30b000041000000000f9c004b000000000f000019000000000f0b8019000007b309900197000007b30ec00197000000000a9e004b000000000b00801900000000099e013f000007b30990009c000000000b0fc01900000000090b004b0000000b06000029000000bc0000c13d00000000096c0019000000000a91034f00000000060a043b000b00000006001d000007b20a60009c000000bc0000213d0000000b06000029000000200a60008c000000bc0000413d0000000b0220006a0000002006900039000007b309000041000000000a26004b000000000a000019000000000a092019000007b302200197000400000006001d000007b30b600197000000000c2b004b000000000900801900000000022b013f000007b30220009c00000000090ac019000000000209004b000000bc0000c13d0000000409100360000000400200043d000000000609043b000500000006001d000000800a60008c000000200f2000390000197b0000413d0000000506000029000000800a600270000007b80b60009c000000000a06a019000007b80b60009c000000000b000019000000100b002039000000080cb001bf000007b20ea0009c000000000c0ba019000000400ba00270000007b20ea0009c000000000b0aa019000000040ec001bf000007ae0ab0009c000000000e0ca019000000200cb00270000007ae0ab0009c000000000c0ba019000000020ae001bf0000ffff0bc0008c000000000a0ea019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000410ba00039000000000b3b016f000000000cb20019000000000b2c004b000000000e000019000000010e004039000007b20bc0009c000003fa0000213d000000010be00190000003fa0000c13d0000004000c0043f000000020ba000390000000000b20435000000210ba00039000000050eb00272000018be0000613d000000000c000019000000050bc002100000000009bf0019000000000bbd034f000000000b0b043b0000000000b90435000000010cc000390000000009ec004b000018b60000413d000000000600004b000018c00000613d0000000009020433000000000909004b000004e80000613d00000000090f0433000007b709900197000000f80ba0021000000000099b019f000007b90990004100000000009f04350000000309a00210000000f809900089000000050a9001ef000000ff0990008c000000000a00201900000021092000390000000000a904350000198c0000013d0000000306000029000007b60660009c000003fa0000213d00000003070000290000004006700039000000400060043f000000000612034f000000010100003a00000000011704360000000006600350000000000606043b0000000000610435000004e80000613d000000f807500210000007b308000041000000000505004b000000000807c019000007b705600197000000000585019f0000000000510435000000410130008c000004e80000413d0000002001400039000000000112034f000000000101043b000000f801100270000200000001001d0000001b0110008a000000020110008c00001b780000813d0000000c01000029000101440010003d0000000101200360000000000101043b000000000101004b00001aa90000613d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000000201043b0000000101200210000000000302004b0000190b0000613d000000090300008a000000000331004b0000190f0000213d00000000322100d9000000020220008c0000190f0000c13d00000002011000290000000803100039000000020130006c000019e10000813d000007d30100004100000000001004350000001101000039000004eb0000013d000000000001042f000007b60920009c000003fa0000213d0000004009200039000000400090043f00000020092000390000000906000029000000000069043500000007060000290000000000620435000000000a06004b000004e80000613d0000000406000029000000f80a600210000007b30b000041000000000c06004b000000000b0ac019000000060ab001af0000000000a904350000000b06000029000000400960008c000000bc0000413d000000400900043d0000000506000029000500200060003d000000050a10036000000000060a043b000900000006001d000000800a60008c000000200e90003900001a2d0000413d0000000906000029000000800a600270000007b80b60009c000000000a06a019000007b80b60009c000000000b000019000000100b002039000000080cb001bf000007b20fa0009c000000000c0ba019000000400ba00270000007b20fa0009c000000000b0aa019000000040ac001bf000007ae0fb0009c000000000a0ca019000000200cb00270000007ae0fb0009c000000000c0ba0190000000206a001bf0000ffff0bc0008c00000000060aa019000000100ac00270000000000a0ca019000000ff0aa0008c0000000106602039000600000006001d000000410a600039000000000a3a016f000000000ca90019000000000a9c004b000000000a000019000000010a004039000007b20bc0009c000003fa0000213d000000010aa00190000003fa0000c13d0000004000c0043f0000000606000029000000020a6000390000000000a90435000000210a600039000000050fa00272000019670000613d000000000c000019000000050ac00210000000000bae0019000000000aad034f000000000a0a043b0000000000ab0435000000010cc00039000000000afc004b0000195f0000413d000000000600004b000019690000613d000000000a090433000000000a0a004b000004e80000613d000000000a0e0433000007b70aa001970000000606000029000000f80b600210000000000aab019f000007b90aa000410000000000ae0435000000030a600210000000f80aa00089000000090ba001ef000000ff0aa0008c000000000b002019000000210a9000390000000000ba043500001a400000013d000007b60920009c000003fa0000213d0000004009200039000000400090043f000000090600002900000000006f043500000007060000290000000000620435000000000906004b000004e80000613d0000000506000029000000f809600210000007b30a000041000000000b06004b000000000a09c0190000000609a001af00000000009f04350000000b06000029000000400960008c000000bc0000413d000000400900043d0000000406000029000500200060003d000000050a10036000000000060a043b000900000006001d000000800a60008c000000200e90003900001a6b0000413d0000000906000029000000800a600270000007b80b60009c000000000a06a019000007b80b60009c000000000b000019000000100b002039000000080cb001bf000007b20fa0009c000000000c0ba019000000400ba00270000007b20fa0009c000000000b0aa019000000040fc001bf000007ae0ab0009c000000000f0ca019000000200cb00270000007ae0ab0009c000000000c0ba0190000000206f001bf0000ffff0bc0008c00000000060fa019000000100bc00270000000000b0ca019000000ff0bb0008c0000000106602039000600000006001d000000410b600039000000000b3b016f000000000cb90019000000000b9c004b000000000f000019000000010f004039000007b20bc0009c000003fa0000213d000000010bf00190000003fa0000c13d0000004000c0043f0000000606000029000000020b6000390000000000b90435000000210b600039000000050cb00272000019cd0000613d000000000f000019000000050bf00210000000000abe0019000000000bbd034f000000000b0b043b0000000000ba0435000000010ff00039000000000acf004b000019c50000413d000000000600004b000019cf0000613d000000000a090433000000000a0a004b000004e80000613d000000000a0e0433000007b70aa001970000000606000029000000f80b600210000000000aab019f000007b90aa000410000000000ae0435000000030a600210000000f80aa00089000000090ba001ef000000ff0aa0008c000000000b002019000000210a9000390000000000ba043500001a7e0000013d000000800130008c000200000003001d00001aa90000413d0000008001300270000007b80230009c000000000103a019000007b80230009c0000000002000019000000100200203900000008042001bf000007b20510009c000000000402a0190000004002100270000007b20510009c000000000201a01900000004014001bf000007ae0520009c000000000104a0190000002004200270000007ae0520009c000000000402a01900000002051001bf0000ffff0240008c000000000501a0190000001001400270000000000104a019000000ff0110008c00000001055020390000004101500039000000070210017f000000400100043d0000000002210019000000000412004b00000000040000190000000104004039000007b20620009c000003fa0000213d0000000104400190000003fa0000c13d000000400020043f00000002025000390000000006210436000000010200036700000000040000310000002107500039000000050770027200001a1a0000613d000000000842034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00001a120000413d000000000700004b00001a1c0000613d0000000007010433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000035301cf000000ff0550008c00000000030020190000002105100039000000000035043500001abf0000013d000007b60a90009c000003fa0000213d000000400a9000390000004000a0043f000000070a0000290000000000a90435000000080600035f000000000c06043b0000000000ce0435000000000a0a004b000004e80000613d0000000906000029000000f80a600210000007b30b000041000000000d06004b000000000b0ac019000007b70ac00197000000000aba019f0000000000ae04350000000b06000029000000410a60008c000004e80000413d0000000506000029000000200a600039000000000aa1034f0000000006000415000000100660008a000b0020006000cd000000000a0a043b000000f80ca002700000001b0ac0008c000000000e00001900001b280000613d0000001c0ac0008c00001b780000c13d00000000060004150000000f0660008a000b0020006000cd0000001b0ec0008a000000800ae0008c00001b280000413d000000400c00043d000007b60ac0009c000003fa0000213d000000400ac000390000004000a0043f000000020a00003a000000000aac0436000000080600035f000000000d06043b0000000000da0435000004e80000613d000007b70bd00197000007b90bb001c70000000000ba0435000000f80ae00210000000210bc000390000000000ab043500000000060004150000000f0660008a000b0020006000cd00001b3b0000013d000007b60a90009c000003fa0000213d000000400a9000390000004000a0043f000000070b0000290000000000b90435000000080600035f000000000a06043b0000000000ae0435000000000b0b004b000004e80000613d0000000906000029000000f80b600210000007b30c000041000000000d06004b000000000c0bc019000007b70aa00197000000000aca019f0000000000ae04350000000b06000029000000410a60008c000004e80000413d0000000506000029000000200a600039000000000ba1034f00000000060004150000000e0660008a000b0020006000cd000000000b0b043b000000f80cb002700000001b0bc0008c000000000d00001900001b7f0000613d0000001c0ac0008c00001b780000c13d00000000060004150000000d0660008a000b0020006000cd0000001b0dc0008a000000800bd0008c00001b7f0000413d000000400c00043d000007b60ac0009c000003fa0000213d000000400ac000390000004000a0043f000000020a00003a000000000aac0436000000080600035f000000000e06043b0000000000ea0435000004e80000613d000007b70be00197000007b90bb001c70000000000ba0435000000f80ad00210000000210bc000390000000000ab043500000000060004150000000d0660008a000b0020006000cd00001b920000013d000000400100043d000007b60210009c000003fa0000213d0000004002100039000000400020043f000000010200003a000000000321043600000000040000310000000102000367000000000542034f0000000005500350000000000505043b0000000000530435000004e80000613d0000000208000029000000f806800210000007b307000041000000000808004b000000000706c019000007b705500197000000000575019f000000000053043500000001030000290000008003300039000000000332034f0000000c0540006a000000230550008a000000000303043b000007b306000041000000000753004b00000000070000190000000007068019000007b305500197000007b308300197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000506004b0000000b06000029000000bc0000c13d0000000a050000290000000005050433000000090700002900000000070704330000000808000029000000000808043300000006090000290000000009090433000000050a000029000000000a0a04330000000006630019000000000362034f000000000303043b000007b20b30009c000000bc0000213d000000000b3400490000002006600039000007b30c000041000000000db6004b000000000d000019000000000d0c2019000007b30bb00197000007b30e600197000000000fbe004b000000000c008019000000000bbe013f000007b30bb0009c000000000c0dc019000000000b0c004b000000bc0000c13d0000000005570019000000000585001900000000059500190000000005a50019000000000535001900000004070000290000000007070433000000000575001900000003070000290000000007070433000000000575001900000000070104330000000005750019000000400700043d000007b205500197000000380850008c0000004009700039000000000842034f000000200470003900001bcf0000413d000000200b500270000007ae0a50009c000000000b05a019000007ae0a50009c000000000c000019000000040c002039000000020ac001bf0000ffff0db0008c000000000a0ca019000000100cb00270000000000c0ba019000000ff0bc0008c000000000b000019000000010b002039000007b60c70009c000003fa0000213d000000000aba019f000000400090043f0000000209a0003a00000000009704350000000008800350000000000808043b0000000000840435000004e80000613d000007b708800197000000f809a00210000000000889019f000007bd088001c700000000008404350000000304a00210000000f80440015f00000000044501cf0000002105700039000000000045043500001bdd0000013d000000400c00043d000007b60ac0009c000003fa0000213d000000400ac000390000004000a0043f000000070a000029000000000fac0436000000080600035f000000000d06043b0000000000df0435000000000a0a004b000004e80000613d000000f80ae00210000007b30b000041000000000e0e004b000000000b0ac019000007b70ad00197000000000aba019f0000000000af04350000000b06000029000000050a600270000000000a0c001f000000000a040433000000000a5a0019000000000b080433000000000aba0019000000000b070433000000000aba0019000000000b020433000000000aba0019000000000b090433000000000aba0019000000000b0c0433000000000aba0019000000400d00043d000007b206a00197000900000006001d000000380a60008c0006004000d0003d000b002000d0003d00001c9c0000413d0000000906000029000000200a600270000007ae0b60009c000000000a06a019000007ae0b60009c000000000f000019000000040f002039000000020bf001bf0000ffff0ea0008c000000000b0fa019000000100ea00270000000000e0aa019000000ff0ae0008c000000000a000019000000010a002039000007b60ed0009c000003fa0000213d000000000bab019f0000000606000029000000400060043f000000020ab0003a0000000000ad0435000000080600035f000000000a06043b0000000b060000290000000000a60435000004e80000613d000007b70aa00197000000f80eb00210000000000aae019f000007bd0aa001c70000000b060000290000000000a60435000000030ab00210000000f80aa0015f000000090aa001ef000000210bd000390000000000ab043500001caf0000013d000000400100043d0000004402100039000007d203000041000000000032043500000024021000390000000f0300003900000c9e0000013d000000400c00043d000007b60bc0009c000003fa0000213d000000400bc000390000004000b0043f000000070a000029000000000eac0436000000080600035f000000000f06043b0000000000fe0435000000000b0a004b000004e80000613d000000f80bd00210000007b30a000041000000000d0d004b000000000a0bc019000007b70bf00197000000000aab019f0000000000ae04350000000b06000029000000050a600270000000000a0c001f000000000a040433000000000a5a0019000000000b080433000000000aba0019000000000b070433000000000aba0019000000000b020433000000000aba0019000000000b090433000000000aba0019000000000b0c0433000000000aba0019000000400d00043d000007b206a00197000900000006001d000000380b60008c0006004000d0003d000b002000d0003d00001d540000413d0000000906000029000000200f600270000007ae0b60009c000000000f06a019000007ae0b60009c000000000e000019000000040e002039000000020be001bf0000ffff0af0008c000000000b0ea019000000100af00270000000000a0fa019000000ff0aa0008c000000000f000019000000010f002039000007b60ad0009c000003fa0000213d000000000bfb019f0000000606000029000000400060043f000000020ab0003a0000000000ad0435000000080600035f000000000f06043b0000000b060000290000000000f60435000004e80000613d000007b70af00197000000f80eb00210000000000aae019f000007bd0aa001c70000000b060000290000000000a60435000000030ab00210000000f80aa0015f000000090aa001ef000000210bd000390000000000ab043500001d670000013d000007b60a70009c000003fa0000213d000000400090043f000000010900003a00000000009704350000000008800350000000000808043b0000000000840435000004e80000613d000007b708800197000000f805500210000000000585019f000007bc055000410000000000540435000000400400043d00000020054000390000000008070433000000000908004b00001bea0000613d0000000009000019000000000a5900190000002009900039000000000b790019000000000b0b04330000000000ba0435000000000a89004b00001be30000413d000000000758001900000000000704350000000a080000290000000008080433000000000908004b00001bf80000613d0000000009000019000000000a79001900000020099000390000000a0b900029000000000b0b04330000000000ba0435000000000a89004b00001bf10000413d0000000007780019000000000007043500000009080000290000000008080433000000000908004b00001c060000613d0000000009000019000000000a7900190000002009900039000000090b900029000000000b0b04330000000000ba0435000000000a89004b00001bff0000413d0000000007780019000000000007043500000008080000290000000008080433000000000908004b00001c140000613d0000000009000019000000000a7900190000002009900039000000080b900029000000000b0b04330000000000ba0435000000000a89004b00001c0d0000413d0000000007780019000000000007043500000006080000290000000008080433000000000908004b00001c220000613d0000000009000019000000000a7900190000002009900039000000060b900029000000000b0b04330000000000ba0435000000000a89004b00001c1b0000413d0000000007780019000000000007043500000005080000290000000008080433000000000908004b00001c300000613d0000000009000019000000000a7900190000002009900039000000050b900029000000000b0b04330000000000ba0435000000000a89004b00001c290000413d000000000662034f00000000027800190000001f0730018f0000000000020435000000050830027200001c3f0000613d0000000009000019000000050a900210000000000ba20019000000000aa6034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b00001c370000413d000000000907004b00001c4e0000613d0000000508800210000000000686034f00000000088200190000000307700210000000000908043300000000097901cf000000000979022f000000000606043b0000010007700089000000000676022f00000000067601cf000000000696019f0000000000680435000000000232001900000000000204350000000003010433000000000603004b00001c5b0000613d000000000600001900000000072600190000002006600039000000000816001900000000080804330000000000870435000000000736004b00001c540000413d0000000001230019000000000001043500000004020000290000000002020433000000000302004b00001c690000613d000000000300001900000000061300190000002003300039000000040730002900000000070704330000000000760435000000000623004b00001c620000413d0000000001120019000000000001043500000003020000290000000002020433000000000302004b00001c770000613d000000000300001900000000061300190000002003300039000000030730002900000000070704330000000000760435000000000623004b00001c700000413d000000000112001900000000000104350000000001410049000000200210008a00000000002404350000001f01100039000000070210017f0000000001420019000000000221004b00000000020000190000000102004039000007b20310009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000007ae01000041000007ae0250009c000000000501801900000040025002100000000003040433000007ae0430009c00000000030180190000006003300210000000000223019f0000000003000414000007ae0430009c0000000003018019000000c001300210000000000121019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d000000000101043b00000e4d0000013d000007b60ad0009c000003fa0000213d0000000606000029000000400060043f000000070b0000290000000000bd0435000000080600035f000000000a06043b0000000b060000290000000000a60435000000000b0b004b000004e80000613d000007b70aa001970000000906000029000000f80b600210000000000aab019f000007bc0aa000410000000b060000290000000000a60435000000400600043d000000200a600039000007be0b00004100090000000a001d0000000000ba0435000b00000006001d000000210e600039000000000f0d0433000000000b0f004b00001cc10000613d000000000b000019000000000aeb0019000000200bb000390000000006db0019000000000606043300000000006a04350000000006fb004b00001cba0000413d000000000def001900000000000d0435000000000e04043300000000060e004b00001cce0000613d000000000b0000190000000006db0019000000200bb00039000000000a4b0019000000000a0a04330000000000a604350000000006eb004b00001cc70000413d000000000dde001900000000000d0435000000000e08043300000000040e004b00001cdb0000613d00000000040000190000000006d400190000002004400039000000000a840019000000000a0a04330000000000a604350000000006e4004b00001cd40000413d0000000c041003600000000001de00190000001f0650018f0000000000010435000000050850027200001cea0000613d000000000d000019000000050ad00210000000000ba10019000000000aa4034f000000000a0a043b0000000000ab0435000000010dd00039000000000a8d004b00001ce20000413d000000000a06004b00001cf90000613d0000000508800210000000000484034f00000000088100190000000306600210000000000a080433000000000a6a01cf000000000a6a022f000000000404043b0000010006600089000000000464022f00000000046401cf0000000004a4019f0000000000480435000000000151001900000000000104350000000004070433000000000504004b00001d060000613d000000000500001900000000061500190000002005500039000000000875001900000000080804330000000000860435000000000645004b00001cff0000413d0000000001140019000000000001043500000000040c0433000000000504004b00001d130000613d0000000005000019000000000615001900000020055000390000000007c5001900000000070704330000000000760435000000000645004b00001d0c0000413d000000000114001900000000000104350000000004020433000000000504004b00001d200000613d000000000500001900000000061500190000002005500039000000000725001900000000070704330000000000760435000000000645004b00001d190000413d000000000114001900000000000104350000000002090433000000000402004b00001d2d0000613d000000000400001900000000051400190000002004400039000000000694001900000000060604330000000000650435000000000524004b00001d260000413d000000000112001900000000000104350000000b040000290000000001410049000000200210008a00000000002404350000001f01100039000000000231016f0000000001420019000000000221004b00000000020000190000000102004039000007b20310009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000007ae010000410000000903000029000007ae0230009c000000000301801900000040023002100000000b030000290000000003030433000007ae0430009c00000000030180190000006003300210000000000223019f0000000003000414000007ae0430009c0000000003018019000000c001300210000000000121019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d00001e0b0000013d000007b60ad0009c000003fa0000213d0000000606000029000000400060043f000000070a0000290000000000ad0435000000080600035f000000000f06043b0000000b060000290000000000f60435000000000a0a004b000004e80000613d000007b70af001970000000906000029000000f80b600210000000000aab019f000007bc0aa000410000000b060000290000000000a60435000000400600043d000000200a600039000007bf0b00004100090000000a001d0000000000ba0435000b00000006001d000000210e600039000000000f0d0433000000000b0f004b00001d790000613d000000000b000019000000000aeb0019000000200bb000390000000006db0019000000000606043300000000006a04350000000006fb004b00001d720000413d000000000def001900000000000d0435000000000e04043300000000060e004b00001d860000613d000000000b0000190000000006db0019000000200bb00039000000000a4b0019000000000a0a04330000000000a604350000000006eb004b00001d7f0000413d000000000dde001900000000000d0435000000000e08043300000000040e004b00001d930000613d00000000040000190000000006d400190000002004400039000000000a840019000000000a0a04330000000000a604350000000006e4004b00001d8c0000413d0000000c041003600000000001de00190000001f0650018f0000000000010435000000050850027200001da20000613d000000000d000019000000050ad00210000000000ba10019000000000aa4034f000000000a0a043b0000000000ab0435000000010dd00039000000000a8d004b00001d9a0000413d000000000a06004b00001db10000613d0000000508800210000000000484034f00000000088100190000000306600210000000000a080433000000000a6a01cf000000000a6a022f000000000404043b0000010006600089000000000464022f00000000046401cf0000000004a4019f0000000000480435000000000151001900000000000104350000000004070433000000000504004b00001dbe0000613d000000000500001900000000061500190000002005500039000000000875001900000000080804330000000000860435000000000645004b00001db70000413d0000000001140019000000000001043500000000040c0433000000000504004b00001dcb0000613d0000000005000019000000000615001900000020055000390000000007c5001900000000070704330000000000760435000000000645004b00001dc40000413d000000000114001900000000000104350000000004020433000000000504004b00001dd80000613d000000000500001900000000061500190000002005500039000000000725001900000000070704330000000000760435000000000645004b00001dd10000413d000000000114001900000000000104350000000002090433000000000402004b00001de50000613d000000000400001900000000051400190000002004400039000000000694001900000000060604330000000000650435000000000524004b00001dde0000413d000000000112001900000000000104350000000b040000290000000001410049000000200210008a00000000002404350000001f01100039000000000231016f0000000001420019000000000221004b00000000020000190000000102004039000007b20310009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000007ae010000410000000903000029000007ae0230009c000000000301801900000040023002100000000b030000290000000003030433000007ae0430009c00000000030180190000006003300210000000000223019f0000000003000414000007ae0430009c0000000003018019000000c001300210000000000121019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d000000000101043b00000000020004150000000a02200069000000000200000200000e4d0000013d00000000030004140000000004120019000000000224004b00000000050000190000000105004039000007ae02100197000000010150019000001e690000c13d0000000001000031000000000541004b00001e690000413d0000000102200367000007c00530009c00001e6d0000813d0000000001410049000007ae0110019700000000011203df000000c002300210000007c102200197000007c2022001c700000000012103af00008010020000391eb21ead0000040f00000000030100190000006003300270000007ae03300197000000010220019000001e740000613d0000003f02300039000007c304200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000007b20640009c00001e8f0000213d000000010550019000001e8f0000c13d000000400040043f00000000043204360000001f05300039000000050550027200001e470000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b00001e3f0000413d000000000500004b00001e490000613d0000001f0530018f000000050330027200001e550000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b00001e4d0000413d000000000605004b00001e640000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f00000000001304350000000001020433000000200110008c00001e950000c13d0000000001040433000000000001042d000007d3010000410000000000100435000000110100003900001e920000013d000000400100043d0000004402100039000007d00300004100000000003204350000002402100039000000080300003900001e9b0000013d0000001f0430018f000000050230027200001e7f0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b00001e780000413d000000000504004b00001e8d0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f0000000000120435000000600130021000001eb400010430000007d30100004100000000001004350000004101000039000000040010043f000007d40100004100001eb400010430000000400100043d0000004402100039000007c503000041000000000032043500000024021000390000001f030000390000000000320435000007c6020000410000000000210435000000040210003900000020030000390000000000320435000007ae02000041000007ae0310009c00000000010280190000004001100210000007c7011001c700001eb400010430000000000001042f00001eab002104230000000102000039000000000001042d0000000002000019000000000001042d00001eb0002104230000000102000039000000000001042d0000000002000019000000000001042d00001eb20000043200001eb30001042e00001eb40001043000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000ffffffff00000000000000000000000000000000000000000000000000000000ebe4a3d700000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffff80000000000000000000000000000000000000000000000000000000000000009a8a0592ac89c5ad3bc6df8224c17b485976f597df104ee20d0df415241f670b0200000200000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffbf00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00000000000000000000000000000000ffffffffffffffffffffffffffffffff81000000000000000000000000000000000000000000000000000000000000009400000000000000000000000000000000000000000000000000000000000000b800000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000000f80000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000000000000ffffffff000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001ffffffe007ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff6b656363616b3235362072657475726e656420696e76616c696420646174610008c379a0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000064000000000000000000000000848e1bfa1ac4e3576b728bda6721b215c70a7799a5b4866282a71bab954baac8000000000000000000000000000000000000000000000000fffffffffffffe1fc2f8787176b8ac6bf7215b4adcc1e069bf4ab82d9ab1df05a57a91d425935b6ead7c5bef027816a800da1736444fb58a807ef4c9603b7848673f7e3a68eb14a519b453ce45aaaaf3a300f5a9ec95869b4f28ab10430b572ee218c3a6a5e07d6f000000000000000000000000000000000000000000000000ffffffffffffff5f1901000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff7f4f766572666c6f770000000000000000000000000000000000000000000000008080000000000000000000000000000000000000000000000000000000000000496e76616c696420762076616c756500000000000000000000000000000000004e487b71000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff9f0000000000000000000000000000000000000040000000000000000000000000556e737570706f72746564207478207479706500000000000000000000000000456e636f64696e6720756e737570706f727465642074780000000000000000000000000000000000000000000000000000000064000000800000000000000000d911e45b07a9c649117ffaea017b6308f32dfe1921ce79a3b2fc49b0d41abe31", + "deployedBytecode": "0x00020000000000020011000000000002000100000001035500000000030100190000006005300270000007ae0050019d0000008004000039000000400040043f000007ae0350019700000001022001900000008a0000c13d000000040230008c000000bc0000413d000000000201043b000007b002200197000007b10220009c000000bc0000c13d0000000002000416000000000202004b000000bc0000c13d000000040230008a000000200620008c000000bc0000413d0000000406100370000000000d06043b000007b206d0009c000000bc0000213d0000000002d20049000007b306000041000002600720008c00000000070000190000000007064019000007b302200197000000000802004b000000000600a019000007b30220009c000000000607c019000000000206004b000000bc0000c13d000000040cd000390000000002c1034f000000000202043b000000010620008c000000920000213d000000000402004b000000c80000613d000000010120008c000000be0000c13d000c0000000d001d000b0000000c001d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000400300043d000000000401043b000000800140008c0000021b0000413d0000008001400270000007b80240009c000000000104a019000007b80240009c0000000002000019000000100200203900000008052001bf000007b20610009c000000000502a0190000004002100270000007b20610009c000000000201a01900000004015001bf000007ae0620009c000000000105a0190000002006200270000007ae0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000007b20610009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000000020150003900000000061304360000000101000367000000000200003100000021075000390000000507700272000000780000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000000700000413d000000000700004b0000007a0000613d0000000007030433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c000000000400201900000021053000390000022e0000013d0000000001000416000000000101004b000000bc0000c13d000000200100003900000100001004430000012000000443000007af0100004100001eb30001042e000000020620008c0000010b0000613d000000710220008c000000be0000c13d000001c402d00039000000000221034f0000000006d30049000000230660008a000000000202043b000007b307000041000000000862004b00000000080000190000000008078019000007b306600197000007b309200197000000000a69004b0000000007008019000000000669013f000007b30660009c000000000708c019000000000607004b000000bc0000c13d0000000002c20019000000000621034f000000000606043b000007b20760009c000000bc0000213d00000000076300490000002002200039000007b308000041000000000972004b00000000090000190000000009082019000007b307700197000007b30a200197000000000b7a004b000000000800801900000000077a013f000007b30770009c000000000809c019000000000708004b000002dd0000613d000000000100001900001eb400010430000007c601000041000000800010043f0000002001000039000000840010043f0000001701000039000000a40010043f000007d801000041000000c40010043f000007d90100004100001eb400010430000000000231034f0000010005c00039000000000451034f000000000404043b000000800640008c000001650000413d0000008006400270000007b80740009c000000000604a019000007b80740009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a000000c108600039000000000778016f000000400070043f0000000207600039000000800070043f00000021076000390000000507700272000000f90000613d00000000080000190000000509800210000000000a92034f000000000a0a043b000000a0099000390000000000a904350000000108800039000000000978004b000000f10000413d000000000700004b000000fb0000613d000000800700043d000000000707004b000004e80000613d000000a00700043d000007b707700197000000f808600210000000000778019f000007b907700041000000a00070043f0000000306600210000000f80660008900000000046401cf000000ff0660008c0000000004002019000000a10040043f000001720000013d000c0000000d001d000b0000000c001d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000400300043d000000000401043b000000800140008c0000027c0000413d0000008001400270000007b80240009c000000000104a019000007b80240009c0000000002000019000000100200203900000008052001bf000007b20610009c000000000502a0190000004002100270000007b20610009c000000000201a01900000004015001bf000007ae0620009c000000000105a0190000002006200270000007ae0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000007b20610009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000000020150003900000000061304360000000101000367000000000200003100000021075000390000000507700272000001530000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b0000014b0000413d000000000700004b000001550000613d0000000007030433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c000000000400201900000021053000390000028f0000013d000000f806400210000007b307000041000000000404004b000000000706c019000000c004000039000000400040043f0000000104000039000000800040043f0000000004200350000000000404043b000007b704400197000000000474019f000000a00040043f000c0000000d001d000b0000000c001d000000400400043d000000600550008a000000000651034f000000000606043b000000800760008c000001bf0000413d0000008007600270000007b80860009c000000000706a019000007b80860009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008840019000000000948004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f0000000208700039000000000884043600000021097000390000000509900272000001ad0000613d000000000a000019000000050ba00210000000000cb80019000000000bb2034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000001a50000413d000000000900004b000001af0000613d0000000009040433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c00000000060020190000002107400039000001cf0000013d000007b60740009c000003fa0000213d0000004007400039000000400070043f000000010700003a00000000077404360000000008200350000000000808043b0000000000870435000004e80000613d000000f809600210000007b30a000041000000000606004b000000000a09c019000007b7068001970000000006a6019f0000000000670435000000400550008a000000000651034f000000400500043d000000000606043b000000800760008c000002fb0000413d0000008007600270000007b80860009c000000000706a019000007b80860009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008850019000000000958004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f0000000208700039000000000885043600000021097000390000000509900272000002090000613d000000000a000019000000050ba00210000000000cb80019000000000bb2034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000002010000413d000000000900004b0000020b0000613d0000000009050433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c000000000600201900000021075000390000030b0000013d000007b60130009c000003fa0000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000101000367000000000621034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807400210000007b308000041000000000404004b000000000807c019000007b704600197000000000484019f0000000000450435000000400400043d0000000c050000290000010406500039000000000561034f000000000505043b000000800750008c0000039a0000413d0000008007500270000007b80850009c000000000705a019000007b80850009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008840019000000000948004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f00000002087000390000000008840436000000210970003900000005099002720000026a0000613d000000000a21034f000000000b000019000000050cb00210000000000dc80019000000000cca034f000000000c0c043b0000000000cd0435000000010bb00039000000000c9b004b000002620000413d000000000900004b0000026c0000613d0000000009040433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000057501cf000000ff0770008c00000000050020190000002107400039000003ab0000013d000007b60130009c000003fa0000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000101000367000000000621034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807400210000007b308000041000000000404004b000000000807c019000007b704600197000000000484019f0000000000450435000000400400043d0000000c050000290000010406500039000000000561034f000000000505043b000000800750008c000003f80000413d0000008007500270000007b80850009c000000000705a019000007b80850009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008840019000000000948004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f0000000208700039000000000884043600000021097000390000000509900272000002cb0000613d000000000a21034f000000000b000019000000050cb00210000000000dc80019000000000cca034f000000000c0c043b0000000000cd0435000000010bb00039000000000c9b004b000002c30000413d000000000900004b000002cd0000613d0000000009040433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000057501cf000000ff0770008c000000000500201900000021074000390000056d0000013d00000000070004140000000008260019000000000668004b0000000006000019000000010600403900000001066001900000190f0000c13d000000000383004b0000190f0000413d000c0000000d001d000b0000000c001d000007c00370009c000003fe0000413d0000004401400039000007d0020000410000000000210435000000240140003900000008020000390000000000210435000007c6010000410000000000140435000000040140003900000020020000390000000000210435000007ae01000041000007ae0240009c00000000040180190000004001400210000007c7011001c700001eb400010430000007b60750009c000003fa0000213d0000004007500039000000400070043f000000010700003a00000000077504360000000008200350000000000808043b0000000000870435000004e80000613d000000f809600210000007b30a000041000000000606004b000000000a09c019000007b7068001970000000006a6019f0000000000670435000000400600043d000a00000006001d00000020066000390000000007040433000000000807004b0000031a0000613d000000000800001900000000096800190000002008800039000000000a480019000000000a0a04330000000000a90435000000000978004b000003130000413d000000000467001900000000000404350000000006050433000000000706004b000003270000613d000000000700001900000000084700190000002007700039000000000957001900000000090904330000000000980435000000000867004b000003200000413d000000000446001900000000000404350000000a060000290000000004640049000000200540008a00000000005604350000001f044000390008002000000092000000080440017f0000000005640019000000000445004b00000000040000190000000104004039000900000005001d000007b20550009c000003fa0000213d0000000104400190000003fa0000c13d0000000904000029000000400040043f000007b60440009c000003fa0000213d0000000c070000290000004404700039000000000441034f000000000404043b00000009080000290000004005800039000000400050043f0000002005800039000007ba060000410000000000650435000000150500003900000000005804350000006004400210000000210580003900000000004504350000012404700039000000000541034f000000400600043d000700000006001d000000000505043b000000800650008c000006180000413d0000008006500270000007b80750009c000000000605a019000007b80750009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c00000001066020390000004107600039000000080770017f0000000707700029000000070870006c00000000080000190000000108004039000007b20970009c000003fa0000213d0000000108800190000003fa0000c13d000000400070043f00000002076000390000000708000029000000000778043600000021086000390000000508800272000003860000613d0000000009000019000000050a900210000000000ba70019000000000aa2034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b0000037e0000413d000000000800004b000003880000613d00000007080000290000000008080433000000000808004b000004e80000613d0000000008070433000007b708800197000000f809600210000000000889019f000007b90880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c0000000005002019000000070600002900000021066000390000062a0000013d000007b60740009c000003fa0000213d0000004007400039000000400070043f000000000821034f000000010700003a00000000077404360000000008800350000000000808043b0000000000870435000004e80000613d000000f809500210000007b30a000041000000000505004b000000000a09c019000007b7058001970000000005a5019f0000000000570435000000400500043d000000600660008a000000000761034f000000000707043b000000800870008c000004ee0000413d0000008008700270000007b80970009c000000000807a019000007b80970009c00000000090000190000001009002039000000080a9001bf000007b20b80009c000000000a09a0190000004009800270000007b20b80009c000000000908a019000000040ba001bf000007ae0890009c000000000b0aa019000000200a900270000007ae0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000007b20b90009c000003fa0000213d000000010aa00190000003fa0000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa00272000003e60000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000003de0000413d000000000a00004b000003e80000613d000000000a050433000000000a0a004b000004e80000613d000000000a090433000007b70aa00197000000f80b800210000000000aab019f000007b90aa000410000000000a904350000000308800210000000f80880008900000000078701cf000000ff0880008c00000000070020190000002108500039000004ff0000013d000007b60740009c000004df0000a13d000007d30100004100000000001004350000004101000039000004eb0000013d000007ae02200197000000000121034f0000000002850049000007ae0220019700000000012103df000000c002700210000007c102200197000007c2022001c700000000012103af00008010020000391eb21ead0000040f00000000030100190000006003300270000007ae0530019700000001022001900000054c0000613d0000003f02500039000007c302200197000000400600043d0000000002260019000000000362004b00000000030000190000000103004039000007b20420009c000003fa0000213d0000000103300190000003fa0000c13d000000400020043f0000000004560436000000010200036700000000030000310000001f0750003900000005077002720000042a0000613d000000000832034f0000000009000019000000050a900210000000000ba40019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000004220000413d000000000700004b0000042c0000613d0000001f0750018f0000000505500272000004380000613d00000000080000190000000509800210000000000a940019000000000991034f000000000909043b00000000009a04350000000108800039000000000958004b000004300000413d000000000807004b000004470000613d0000000505500210000000000151034f00000000055400190000000307700210000000000805043300000000087801cf000000000878022f000000000101043b0000010007700089000000000171022f00000000017101cf000000000181019f00000000001504350000000001060433000000200110008c00000c980000c13d0000000c060000290000000001630049000000230510008a000a02040060003d0000000a01200360000000000101043b000007b306000041000000000751004b00000000070000190000000007068019000007b305500197000007b308100197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000506004b0000000b05000029000000bc0000c13d0000000004040433000900000004001d0000000001510019000000000412034f000000000504043b000007b20450009c000000bc0000213d000000050450021000000000034300490000002006100039000007b301000041000000000736004b00000000070000190000000007012019000007b303300197000007b308600197000000000938004b0000000001008019000000000338013f000007b30330009c000000000107c019000000000101004b000000bc0000c13d000000400100043d0000002003100039000007c405500198000004830000613d000000000262034f000000000600001900000005076002100000000008730019000000000772034f000000000707043b00000000007804350000000106600039000000000756004b0000047b0000413d000000000200004b000004850000613d00000000004104350000003f02400039000000200400008a000000000242016f0000000002210019000000000412004b00000000040000190000000104004039000007b20520009c000003fa0000213d0000000104400190000003fa0000c13d000000400020043f000007ae02000041000007ae0430009c000000000302801900000040033002100000000001010433000007ae0410009c00000000010280190000006001100210000000000131019f0000000003000414000007ae0430009c0000000003028019000000c002300210000000000112019f000007bf011001c700008010020000391eb21ea80000040f00000001022001900000000b0a0000290000000c03000029000000bc0000613d00000000020000310000000003320049000000230530008a0000000a0300002900000020043000390000000103000367000000000443034f000000000404043b000007b306000041000000000754004b00000000070000190000000007068019000007b305500197000007b308400197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000101043b000a00000001001d000000000106004b000000bc0000c13d0000000001a40019000000000413034f000000000404043b000007b20540009c000000bc0000213d00000000054200490000002001100039000007b306000041000000000751004b00000000070000190000000007062019000007b305500197000007b308100197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000506004b000000bc0000c13d00000000050004140000000006140019000000000446004b0000000004000019000000010400403900000001044001900000190f0000c13d000000000462004b0000190f0000413d000007c00450009c00000ba00000413d000000400400043d000002ea0000013d0000004007400039000000400070043f000000000821034f000000010700003a00000000077404360000000008800350000000000808043b0000000000870435000005670000c13d000007d30100004100000000001004350000003201000039000000040010043f000007d40100004100001eb400010430000007b60850009c000003fa0000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a700210000007b30b000041000000000707004b000000000b0ac019000007b7079001970000000007b7019f0000000000780435000000400700043d000000400660008a000000000861034f000000000808043b000000800980008c000006710000413d0000008009800270000007b80a80009c000000000908a019000007b80a80009c000000000a000019000000100a002039000000080ba001bf000007b20c90009c000000000b0aa019000000400a900270000007b20c90009c000000000a09a019000000040cb001bf000007ae09a0009c000000000c0ba019000000200ba00270000007ae09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa70019000000000b7a004b000000000b000019000000010b004039000007b20ca0009c000003fa0000213d000000010bb00190000003fa0000c13d0000004000a0043f000000020a900039000000000aa70436000000210b900039000000050bb002720000053a0000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b000005320000413d000000000b00004b0000053c0000613d000000000b070433000000000b0b004b000004e80000613d000000000b0a0433000007b70bb00197000000f80c900210000000000bbc019f000007b90bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c00000000080020190000002109700039000006820000013d0000001f0350018f0000000502500272000005570000613d00000000040000190000000506400210000000000761034f000000000707043b00000000007604350000000104400039000000000624004b000005500000413d000000000403004b000005650000613d00000003033002100000000502200210000000000402043300000000043401cf000000000434022f000000000121034f000000000101043b0000010003300089000000000131022f00000000013101cf000000000141019f0000000000120435000000600150021000001eb400010430000000f809500210000007b30a000041000000000505004b000000000a09c019000007b7058001970000000005a5019f0000000000570435000000400500043d000000400760008a000000000671034f000000000606043b000000800860008c000005ba0000413d0000008008600270000007b80960009c000000000806a019000007b80960009c00000000090000190000001009002039000000080a9001bf000007b20b80009c000000000a09a0190000004009800270000007b20b80009c000000000908a019000000040ba001bf000007ae0890009c000000000b0aa019000000200a900270000007ae0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000007b20b90009c000003fa0000213d000000010aa00190000003fa0000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa00272000005a80000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000005a00000413d000000000a00004b000005aa0000613d000000000a050433000000000a0a004b000004e80000613d000000000a090433000007b70aa00197000000f80b800210000000000aab019f000007b90aa000410000000000a904350000000308800210000000f80880008900000000068601cf000000ff0880008c00000000060020190000002108500039000005cb0000013d000007b60850009c000003fa0000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a600210000007b30b000041000000000606004b000000000b0ac019000007b7069001970000000006b6019f0000000000680435000000400600043d000000200770008a000000000871034f000000000808043b000000800980008c000006e20000413d0000008009800270000007b80a80009c000000000908a019000007b80a80009c000000000a000019000000100a002039000000080ba001bf000007b20c90009c000000000b0aa019000000400a900270000007b20c90009c000000000a09a019000000040cb001bf000007ae09a0009c000000000c0ba019000000200ba00270000007ae09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa60019000000000b6a004b000000000b000019000000010b004039000007b20ca0009c000003fa0000213d000000010bb00190000003fa0000c13d0000004000a0043f000000020a900039000000000aa60436000000210b900039000000050bb00272000006060000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b000005fe0000413d000000000b00004b000006080000613d000000000b060433000000000b0b004b000004e80000613d000000000b0a0433000007b70bb00197000000f80c900210000000000bbc019f000007b90bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c00000000080020190000002109600039000006f30000013d0000000706000029000007b60660009c000003fa0000213d00000007070000290000004006700039000000400060043f000000010600003a00000000066704360000000007200350000000000707043b0000000000760435000004e80000613d000000f808500210000007b309000041000000000505004b000000000908c019000007b705700197000000000595019f00000000005604350000000b0b0000290000000005b30049000000a006400039000000000461034f000000000404043b0000001f0550008a000007b307500197000007b308400197000007b309000041000000000a78004b000000000a000019000000000a094019000000000778013f000000000854004b0000000009004019000007b30770009c000000000a09c01900000000070a004b000000bc0000c13d0000000008b40019000000000781034f000000000707043b000007b20970009c000000bc0000213d00000000097300490000002008800039000007b30a000041000000000b98004b000000000b000019000000000b0a2019000007b309900197000007b30c800197000000000d9c004b000000000a00801900000000099c013f000007b30990009c000000000a0bc01900000000090a004b000000bc0000c13d000000010970008c0000086d0000c13d000000000281034f000000000202043b000000010700008a000007b308000041000000000772004b00000000070000190000000007082019000007b302200197000007b30920009c0000000008008019000007b302200167000007b30220009c000000000807c019000600600000003d000000000208004b0000096d0000c13d000000400200043d000600000002001d000007b60220009c000003fa0000213d00000006080000290000004002800039000000400020043f0000002002800039000007b9070000410000000000720435000000010200003900000000002804350000096d0000013d000007b60970009c000003fa0000213d0000004009700039000000400090043f000000000a21034f000000010900003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000000f80b800210000007b30c000041000000000808004b000000000c0bc019000007b708a001970000000008c8019f0000000000890435000000400900043d000007b60890009c000003fa0000213d000000200860008a000000000881034f000000000808043b000000400a9000390000004000a0043f000000200a900039000007ba0b0000410000000000ba0435000000150a0000390000000000a904350000006008800210000000210a90003900000000008a0435000000c006600039000000000661034f000000400800043d000000000606043b000a00000006001d000000800a60008c000007b60000413d0000000a06000029000000800a600270000007b80b60009c000000000a06a019000007b80b60009c000000000b000019000000100b002039000000080cb001bf000007b20da0009c000000000c0ba019000000400ba00270000007b20da0009c000000000b0aa019000000040dc001bf000007ae0ab0009c000000000d0ca019000000200cb00270000007ae0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000007b20db0009c000003fa0000213d000000010cc00190000003fa0000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc00272000006cf0000613d000000000d21034f000000000e000019000000050fe002100000000006fb0019000000000ffd034f000000000f0f043b0000000000f60435000000010ee000390000000006ce004b000006c70000413d000000000600004b000006d10000613d0000000006080433000000000606004b000004e80000613d00000000060b0433000007b706600197000000f80ca0021000000000066c019f000007b90660004100000000006b04350000000306a00210000000f8066000890000000a0a6001ef000000ff0660008c000000000a00201900000021068000390000000000a60435000007c90000013d000007b60960009c000003fa0000213d0000004009600039000000400090043f000000000a21034f000000010900003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000000f80b800210000007b30c000041000000000808004b000000000c0bc019000007b708a001970000000008c8019f0000000000890435000000400800043d000a0040007000920000000a09100360000000000909043b000000800a90008c000007410000413d000000800a900270000007b80b90009c000000000a09a019000007b80b90009c000000000b000019000000100b002039000000080cb001bf000007b20da0009c000000000c0ba019000000400ba00270000007b20da0009c000000000b0aa019000000040dc001bf000007ae0ab0009c000000000d0ca019000000200cb00270000007ae0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000007b20db0009c000003fa0000213d000000010cc00190000003fa0000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc002720000072e0000613d000000000d21034f000000000e000019000000050fe002100000000007fb0019000000000ffd034f000000000f0f043b0000000000f70435000000010ee000390000000007ce004b000007260000413d000000000700004b000007300000613d0000000007080433000000000707004b000004e80000613d00000000070b0433000007b707700197000000f80ca0021000000000077c019f000007b90770004100000000007b04350000000307a00210000000f80770008900000000097901cf000000ff0770008c000000000900201900000021078000390000000000970435000007530000013d000007b60780009c000003fa0000213d0000004007800039000000400070043f000000000721034f000000010a00003a000000000aa804360000000007700350000000000b07043b0000000000ba0435000004e80000613d000000f807900210000007b30c000041000000000909004b000000000c07c019000007b707b001970000000007c7019f00000000007a0435000000400a00043d000007b607a0009c000003fa0000213d0000000a0c0000290000002007c0008a000000000771034f000000000707043b0000004009a00039000000400090043f0000002009a00039000007ba0b0000410000000000b90435000000150900003900000000009a043500000060077002100000002109a000390000000000790435000000c007c00039000000000771034f000000400900043d000000000707043b000a00000007001d000000800b70008c000008980000413d0000000a07000029000000800b700270000007b80c70009c000000000b07a019000007b80c70009c000000000c000019000000100c002039000000080dc001bf000007b20eb0009c000000000d0ca019000000400cb00270000007b20eb0009c000000000c0ba019000000040ed001bf000007ae0bc0009c000000000e0da019000000200dc00270000007ae0bc0009c000000000d0ca0190000000207e001bf0000ffff0cd0008c00000000070ea019000000100cd00270000000000c0da019000000ff0cc0008c0000000107702039000000200c00008a000900000007001d000000410d700039000000000ccd016f000000000cc90019000000000d9c004b000000000d000019000000010d004039000007b20ec0009c000003fa0000213d000000010dd00190000003fa0000c13d0000004000c0043f0000000907000029000000020c700039000000000cc90436000000210d700039000000050dd00272000007a20000613d000000000e21034f000000000f0000190000000507f00210000000000b7c001900000000077e034f000000000707043b00000000007b0435000000010ff000390000000007df004b0000079a0000413d000000000700004b000007a40000613d0000000007090433000000000707004b000004e80000613d00000000070c0433000007b707700197000000090d000029000000f80bd0021000000000077b019f000007b90770004100000000007c04350000000307d00210000000f8077000890000000a0b7001ef000000ff0770008c000000000b00201900000021079000390000000000b70435000008ab0000013d000007b60680009c000003fa0000213d0000004006800039000000400060043f000000000621034f000000010a00003a000000000aa804360000000006600350000000000b06043b0000000000ba0435000004e80000613d0000000a0d000029000000f806d00210000007b30c000041000000000d0d004b000000000c06c019000007b706b001970000000006c6019f00000000006a0435000000400600043d000000200a600039000000000b030433000000000c0b004b000007d60000613d000000000c000019000000000dac0019000000200cc00039000000000e3c0019000000000e0e04330000000000ed0435000000000dbc004b000007cf0000413d0000000003ab00190000000000030435000000000a040433000000000b0a004b000007e30000613d000000000b000019000000000c3b0019000000200bb00039000000000d4b0019000000000d0d04330000000000dc0435000000000cab004b000007dc0000413d00000000033a001900000000000304350000000004050433000000000a04004b000007f00000613d000000000a000019000000000b3a0019000000200aa00039000000000c5a0019000000000c0c04330000000000cb0435000000000b4a004b000007e90000413d000000000334001900000000000304350000000004070433000000000504004b000007fd0000613d0000000005000019000000000a3500190000002005500039000000000b750019000000000b0b04330000000000ba0435000000000a45004b000007f60000413d000000000334001900000000000304350000000004090433000000000504004b0000080a0000613d000000000500001900000000073500190000002005500039000000000a950019000000000a0a04330000000000a70435000000000745004b000008030000413d000000000334001900000000000304350000000004080433000000000504004b000008170000613d000000000500001900000000073500190000002005500039000000000985001900000000090904330000000000970435000000000745004b000008100000413d000000000334001900000000000304350000000003630049000000200430008a00000000004604350000001f04300039000000200300008a000000000434016f0000000007640019000000000447004b00000000040000190000000104004039000007b20570009c000003fa0000213d0000000104400190000003fa0000c13d000000400070043f0000000c05000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b000007b308000041000000000954004b00000000090000190000000009088019000007b305500197000007b30a400197000000000b5a004b000000000800801900000000055a013f000007b30550009c000000000809c019000000000508004b0000000b05000029000000bc0000c13d0000000005540019000000000451034f000000000404043b000007b20840009c000000bc0000213d00000000084200490000002005500039000007b309000041000000000a85004b000000000a000019000000000a092019000007b308800197000007b30b500197000000000c8b004b000000000900801900000000088b013f000007b30880009c00000000090ac019000000000809004b000000bc0000c13d000000010840008c00000a5e0000c13d000000000851034f000000000808043b000000010900008a000007b30a000041000000000998004b000000000900001900000000090a2019000007b308800197000007b30b80009c000000000a008019000007b308800167000007b30880009c000000000a09c019000000600800003900000000090a004b00000cbb0000c13d000007b60870009c000003fa0000213d0000004008700039000000400080043f0000002008700039000007b909000041000000000098043500000001080000390000000000870435000000000807001900000cbb0000013d000000400800043d000600000008001d000000380870008c0000095c0000413d0000002009700270000007ae0870009c000000000907a019000007ae0870009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000000060a000029000007b60aa0009c000003fa0000213d000000000898019f000000060a0000290000004009a00039000000400090043f000000020980003a00000000099a04360000000002200350000000000202043b0000000000290435000004e80000613d000007b702200197000000f80a80021000000000022a019f000007bb022001c700000000002904350000000302800210000000f80220015f00000000022701cf0000000607000029000000210770003900000000002704350000096d0000013d000007b60790009c000003fa0000213d0000004007900039000000400070043f000000000721034f000000010b00003a000000000bb904360000000007700350000000000c07043b0000000000cb0435000004e80000613d0000000a0e000029000000f807e00210000007b30d000041000000000e0e004b000000000d07c019000007b707c001970000000007d7019f00000000007b0435000000400700043d000000200b700039000000000c030433000000000d0c004b000008b80000613d000000000d000019000000000ebd0019000000200dd00039000000000f3d0019000000000f0f04330000000000fe0435000000000ecd004b000008b10000413d0000000003bc00190000000000030435000000000b040433000000000c0b004b000008c50000613d000000000c000019000000000d3c0019000000200cc00039000000000e4c0019000000000e0e04330000000000ed0435000000000dbc004b000008be0000413d00000000033b001900000000000304350000000004050433000000000b04004b000008d20000613d000000000b000019000000000c3b0019000000200bb00039000000000d5b0019000000000d0d04330000000000dc0435000000000c4b004b000008cb0000413d000000000334001900000000000304350000000004060433000000000504004b000008df0000613d0000000005000019000000000b3500190000002005500039000000000c650019000000000c0c04330000000000cb0435000000000b45004b000008d80000413d000000000334001900000000000304350000000004080433000000000504004b000008ec0000613d000000000500001900000000063500190000002005500039000000000b850019000000000b0b04330000000000b60435000000000645004b000008e50000413d0000000003340019000000000003043500000000040a0433000000000504004b000008f90000613d0000000005000019000000000635001900000020055000390000000008a5001900000000080804330000000000860435000000000645004b000008f20000413d000000000334001900000000000304350000000004090433000000000504004b000009060000613d000000000500001900000000063500190000002005500039000000000895001900000000080804330000000000860435000000000645004b000008ff0000413d000000000334001900000000000304350000000003730049000000200430008a00000000004704350000001f04300039000000200300008a000000000434016f0000000006740019000000000446004b00000000040000190000000104004039000007b20560009c000003fa0000213d0000000104400190000003fa0000c13d000000400060043f0000000c05000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b000007b308000041000000000954004b00000000090000190000000009088019000007b305500197000007b30a400197000000000b5a004b000000000800801900000000055a013f000007b30550009c000000000809c019000000000508004b0000000b05000029000000bc0000c13d0000000005540019000000000451034f000000000404043b000007b20840009c000000bc0000213d00000000084200490000002005500039000007b309000041000000000a85004b000000000a000019000000000a092019000007b308800197000007b30b500197000000000c8b004b000000000900801900000000088b013f000007b30880009c00000000090ac019000000000809004b000000bc0000c13d000000010840008c00000cf60000c13d000000000851034f000000000808043b000000010900008a000007b30a000041000000000998004b000000000900001900000000090a2019000007b308800197000007b30b80009c000000000a008019000007b308800167000007b30880009c000000000a09c019000000600800003900000000090a004b00000dc60000c13d000007b60860009c000003fa0000213d0000004008600039000000400080043f0000002008600039000007b909000041000000000098043500000001080000390000000000860435000000000806001900000dc60000013d0000000608000029000007b60880009c000003fa0000213d00000006090000290000004008900039000000400080043f000000010800003a00000000088904360000000002200350000000000202043b0000000000280435000004e80000613d000000f807700210000007b702200197000000000272019f000007b3022001670000000000280435000000800260008a000000000621034f0000006002000039000000000606043b000000000606004b000009ce0000c13d000007b306000041000000000754004b00000000070000190000000007068019000007b305500197000007b308400197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000506004b0000000b05000029000000bc0000c13d0000000a060000290000000006060433000000800700043d0000000908000029000000000808043300000007090000290000000009090433000000060a000029000000000a0a04330000000005540019000000000451034f000000000404043b000007b20b40009c000000bc0000213d000000000b4300490000002005500039000007b30c000041000000000db5004b000000000d000019000000000d0c2019000007b30bb00197000007b30e500197000000000fbe004b000000000c008019000000000bbe013f000007b30bb0009c000000000c0dc019000000000b0c004b000000bc0000c13d0000000006760019000000000686001900000000069600190000000006a60019000000000646001900000000070204330000000006760019000000400700043d000007b206600197000000380860008c00000a860000413d0000002009600270000007ae0860009c000000000906a019000007ae0860009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000007b60a70009c000003fa0000213d000000000898019f0000004009700039000000400090043f000000000931034f000000020380003a00000000033704360000000009900350000000000909043b0000000000930435000004e80000613d000007b709900197000000f80a80021000000000099a019f000007bd099001c700000000009304350000000303800210000000f80330015f00000000033601cf0000002106700039000000000036043500000a960000013d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000400400043d000000000201043b000000800120008c00000a250000413d0000008001200270000007b80320009c000000000102a019000007b80320009c0000000003000019000000100300203900000008053001bf000007b20610009c000000000503a0190000004003100270000007b20610009c000000000301a01900000004015001bf000007ae0630009c000000000105a0190000002006300270000007ae0530009c000000000603a01900000002051001bf0000ffff0360008c000000000501a0190000001001600270000000000106a019000000ff0110008c00000001055020390000004101500039000000080110017f0000000001140019000000000341004b00000000030000190000000103004039000007b20610009c000003fa0000213d0000000103300190000003fa0000c13d000000400010043f00000002015000390000000006140436000000010100036700000000030000310000002107500039000000050770027200000a130000613d000000000831034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000a0b0000413d000000000700004b00000a150000613d0000000007040433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000025201cf000000ff0550008c0000000002002019000000210540003900000a380000013d000007b60140009c000003fa0000213d0000004001400039000000400010043f000000010100003a000000000514043600000000030000310000000101000367000000000631034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807200210000007b308000041000000000202004b000000000807c019000007b702600197000000000282019f0000000000250435000000400200043d00000020052000390000000006040433000000000706004b00000a460000613d000000000700001900000000085700190000002007700039000000000947001900000000090904330000000000980435000000000867004b00000a3f0000413d0000000004560019000007d105000041000000000054043500000000042400490000001e0540008a00000000005204350000002104400039000000080540017f0000000004250019000000000554004b00000000050000190000000105004039000007b20640009c000003fa0000213d0000000105500190000003fa0000c13d0000000c06000029000001c405600039000000400040043f000000000451034f0000000005630049000000230550008a000000000404043b000009730000013d000000380840008c00000caa0000413d0000002009400270000007ae0840009c000000000904a019000007ae0840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000007b60a70009c000003fa0000213d000000000898019f0000004009700039000000400090043f000000000a21034f000000020980003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000007b70aa00197000000f80b800210000000000aab019f000007bb0aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf00000021097000390000000000890435000000000807001900000cbb0000013d000007b60870009c000003fa0000213d0000004008700039000000400080043f000000000831034f000000010300003a00000000033704360000000008800350000000000808043b0000000000830435000004e80000613d000007b708800197000000f806600210000000000686019f000007bc066000410000000000630435000000400300043d00000020063000390000000008070433000000000908004b00000aa30000613d0000000009000019000000000a6900190000002009900039000000000b790019000000000b0b04330000000000ba0435000000000a89004b00000a9c0000413d00000000076800190000000000070435000000800800043d000000000908004b00000ab00000613d0000000009000019000000000a790019000000a00b900039000000000b0b04330000000000ba04350000002009900039000000000a89004b00000aa90000413d000000000778001900000000000704350000000a0c00002900000000080c0433000000000908004b00000abe0000613d0000000009000019000000000a7900190000002009900039000000000bc90019000000000b0b04330000000000ba0435000000000a89004b00000ab70000413d00000000077800190000000000070435000000090c00002900000000080c0433000000000908004b00000acc0000613d0000000009000019000000000a7900190000002009900039000000000bc90019000000000b0b04330000000000ba0435000000000a89004b00000ac50000413d00000000077800190000000000070435000000070c00002900000000080c0433000000000908004b00000ada0000613d0000000009000019000000000a7900190000002009900039000000000bc90019000000000b0b04330000000000ba0435000000000a89004b00000ad30000413d00000000077800190000000000070435000000060c00002900000000080c0433000000000908004b00000ae80000613d0000000009000019000000000a7900190000002009900039000000000bc90019000000000b0b04330000000000ba0435000000000a89004b00000ae10000413d000000000551034f00000000017800190000001f0740018f0000000000010435000000050840027200000af70000613d0000000009000019000000050a900210000000000ba10019000000000aa5034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b00000aef0000413d000000000907004b00000b060000613d0000000508800210000000000585034f00000000088100190000000307700210000000000908043300000000097901cf000000000979022f000000000505043b0000010007700089000000000575022f00000000057501cf000000000595019f0000000000580435000000000141001900000000000104350000000004020433000000000504004b00000b130000613d000000000500001900000000071500190000002005500039000000000825001900000000080804330000000000870435000000000745004b00000b0c0000413d000000000114001900000000000104350000000001310049000000200210008a00000000002304350000001f01100039000000080210017f0000000001320019000000000221004b00000000020000190000000102004039000007b20410009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000007ae01000041000007ae0260009c000000000601801900000040026002100000000003030433000007ae0430009c00000000030180190000006003300210000000000223019f0000000003000414000007ae0430009c0000000003018019000000c001300210000000000121019f000007bf011001c700008010020000391eb21ea80000040f00000001022001900000000b030000290000000c02000029000000bc0000613d000c00000002001d0000000102000367000b00000003001d000000000332034f000000000101043b000a00000001001d001100000001001d000000000103043b000000010310008c00000e010000213d000000000301004b00000eca0000613d000000010110008c00000f760000c13d0000000001000415000a00000001001d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000400300043d000000000401043b000000800140008c00000fde0000413d0000008001400270000007b80240009c000000000104a019000007b80240009c0000000002000019000000100200203900000008052001bf000007b20610009c000000000502a0190000004002100270000007b20610009c000000000201a01900000004015001bf000007ae0620009c000000000105a0190000002006200270000007ae0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000007b20610009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f00000002015000390000000006130436000000010100036700000000020000310000002107500039000000050770027200000b8e0000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000b860000413d000000000700004b00000b900000613d0000000007030433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c0000000004002019000000210530003900000ff10000013d000007ae01100197000000000113034f0000000002620049000007ae0220019700000000012103df000000c002500210000007c102200197000007c2022001c700000000012103af00008010020000391eb21ead0000040f00000000030100190000006003300270000007ae04300197000000010220019000000d1e0000613d0000003f02400039000007c302200197000000400500043d0000000002250019000000000352004b00000000030000190000000103004039000007b20620009c000003fa0000213d0000000103300190000003fa0000c13d000000400020043f000000000245043600000001030003670000001f06400039000000050660027200000bcb0000613d000000000730036800000000080000190000000509800210000000000a920019000000000997034f000000000909043b00000000009a04350000000108800039000000000968004b00000bc30000413d000000000600004b00000bcd0000613d0000001f0640018f000000050440027200000bd90000613d000000000700001900000005087002100000000009820019000000000881034f000000000808043b00000000008904350000000107700039000000000847004b00000bd10000413d000000000706004b00000be80000613d0000000504400210000000000141034f00000000044200190000000306600210000000000704043300000000076701cf000000000767022f000000000101043b0000010006600089000000000161022f00000000016101cf000000000171019f00000000001404350000000001050433000000200110008c00000c980000c13d0000000c0b0000290000006401b00039000000000113034f0000004404b00039000000000543034f0000002404b00039000000000443034f0000012406b00039000000000663034f0000010407b00039000000000773034f000000e408b00039000000000883034f000000c409b00039000000000993034f000000a40ab00039000000000aa3034f000000840bb00039000000000bb3034f0000000b03300360000000000303043b000000000404043b000000000505043b000000000c01043b000000000b0b043b000000000a0a043b000000000909043b000000000808043b000000000707043b000000000606043b0000000002020433000000400100043d000001c00d10003900000000002d0435000001a0021000390000000a0d0000290000000000d204350000018002100039000000090d0000290000000000d2043500000160021000390000000000620435000001400210003900000000007204350000012002100039000000000082043500000100021000390000000000920435000000e0021000390000000000a20435000000c0021000390000000000b20435000000a0021000390000000000c204350000008002100039000000000052043500000060021000390000000000420435000000400210003900000000003204350000002002100039000007c8030000410000000000320435000001c0030000390000000000310435000007c90310009c000003fa0000213d000001e003100039000000400030043f000007ae04000041000007ae0320009c000000000204801900000040022002100000000001010433000007ae0310009c00000000010480190000006001100210000000000121019f0000000002000414000007ae0320009c0000000002048019000000c002200210000000000112019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d000000000101043b000900000001001d000000400100043d000a00000001001d000007b40100004100000000001004390000000001000414000007ae0210009c000007ae01008041000000c001100210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d0000000a040000290000002002400039000000000101043b000007ca030000410000000000320435000000800340003900000000001304350000006001400039000007cb0300004100000000003104350000004001400039000007cc03000041000000000031043500000080010000390000000000140435000007cd0140009c000003fa0000213d0000000a04000029000000a001400039000000400010043f000007ae01000041000007ae0320009c000000000201801900000040022002100000000003040433000007ae0430009c00000000030180190000006003300210000000000223019f0000000003000414000007ae0430009c0000000003018019000000c001300210000000000121019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d000000000301043b000000400100043d0000004202100039000000090400002900000000004204350000002002100039000007ce0400004100000000004204350000002204100039000000000034043500000042030000390000000000310435000007cf0310009c000003fa0000213d0000008003100039000000400030043f000007ae03000041000007ae0420009c000000000203801900000040022002100000000001010433000007ae0410009c00000000010380190000006001100210000000000121019f0000000002000414000007ae0420009c0000000002038019000000c002200210000000000112019f00000b310000013d000000400100043d0000004402100039000007c503000041000000000032043500000024021000390000001f030000390000000000320435000007c6020000410000000000210435000000040210003900000020030000390000000000320435000007ae02000041000007ae0310009c00000000010280190000004001100210000007c7011001c700001eb400010430000007b60870009c000003fa0000213d0000004008700039000000400080043f000000000921034f000000010800003a00000000088704360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a400210000007b7099001970000000009a9019f000007b30990016700000000009804350000000008070019000000400700043d000007b60970009c000003fa0000213d0000004009700039000000400090043f000000000221034f000000010c00003a0000000009c704360000000002200350000000000b02043b0000000000b90435000004e80000613d000007b702b00197000007bc0a2001c70000000000a9043500000000090604330000000009490019000000000a0804330000000009a90019000000000a0704330000000009a90019000000400a00043d000007b209900197000000380d90008c00000d390000413d000000200d900270000007ae0c90009c000000000d09a019000007ae0c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d002039000007b60ea0009c000003fa0000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000004e80000613d000000f80bc0021000000000022b019f000007bd022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a00039000000000029043500000d460000013d000000380840008c00000db50000413d0000002009400270000007ae0840009c000000000904a019000007ae0840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000007b60a60009c000003fa0000213d000000000898019f0000004009600039000000400090043f000000000a21034f000000020980003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000007b70aa00197000000f80b800210000000000aab019f000007bb0aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf00000021096000390000000000890435000000000806001900000dc60000013d0000001f0340018f000000050240027200000d290000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b00000d220000413d000000000503004b00000d370000613d00000003033002100000000502200210000000000502043300000000053501cf000000000535022f000000000121034f000000000101043b0000010003300089000000000131022f00000000013101cf000000000151019f0000000000120435000000600140021000001eb400010430000007b60da0009c000003fa0000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000004e80000613d000000f809900210000000000229019f000007bc0220004100000000002d0435000000400200043d0000002009200039000007be0b0000410000000000b90435000000210b200039000000000c0a0433000000000d0c004b00000d560000613d000000000d000019000000000ebd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ecd004b00000d4f0000413d000000000abc001900000000000a0435000000000b060433000000000c0b004b00000d630000613d000000000c000019000000000dac0019000000200cc00039000000000e6c0019000000000e0e04330000000000ed0435000000000dbc004b00000d5c0000413d0000000006ab00190000000000060435000000000a080433000000000b0a004b00000d700000613d000000000b000019000000000c6b0019000000200bb00039000000000d8b0019000000000d0d04330000000000dc0435000000000cab004b00000d690000413d000000000551034f00000000016a00190000001f0640018f0000000000010435000000050840027200000d7f0000613d000000000a000019000000050ba00210000000000cb10019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b00000d770000413d000000000a06004b00000d8e0000613d0000000508800210000000000585034f00000000088100190000000306600210000000000a080433000000000a6a01cf000000000a6a022f000000000505043b0000010006600089000000000565022f00000000056501cf0000000005a5019f0000000000580435000000000141001900000000000104350000000004070433000000000504004b00000d9b0000613d000000000500001900000000061500190000002005500039000000000875001900000000080804330000000000860435000000000645004b00000d940000413d000000000114001900000000000104350000000001210049000000200410008a00000000004204350000001f01100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000007b20410009c000003fa0000213d0000000103300190000003fa0000c13d000000400010043f000007ae01000041000007ae0390009c000000000901801900000040039002100000000002020433000007ae0420009c00000000020180190000006002200210000000000232019f00000b2c0000013d000007b60860009c000003fa0000213d0000004008600039000000400080043f000000000921034f000000010800003a00000000088604360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a400210000007b7099001970000000009a9019f000007b30990016700000000009804350000000008060019000000400600043d000007b60960009c000003fa0000213d0000004009600039000000400090043f000000000221034f000000010c00003a0000000009c604360000000002200350000000000b02043b0000000000b90435000004e80000613d000007b702b00197000007bc0a2001c70000000000a9043500000000090704330000000009490019000000000a0804330000000009a90019000000000a0604330000000009a90019000000400a00043d000007b209900197000000380d90008c00000e580000413d000000200d900270000007ae0c90009c000000000d09a019000007ae0c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d002039000007b60ea0009c000003fa0000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000004e80000613d000000f80bc0021000000000022b019f000007bd022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a00039000000000029043500000e650000013d000000020310008c00000f1c0000613d000000710110008c00000f760000c13d0000000b09000029000001e001900039000000000312034f00000000010000310000000c0410006a000000230440008a000000000303043b000007b305000041000000000643004b00000000060000190000000006058019000007b304400197000007b307300197000000000847004b0000000005008019000000000447013f000007b30440009c000000000506c019000000000405004b000000bc0000c13d0000000003930019000000000232034f000000000202043b000007b20420009c000000bc0000213d00000000042100490000002001300039000007b303000041000000000541004b00000000050000190000000005032019000007b304400197000007b306100197000000000746004b0000000003008019000000000446013f000007b30440009c000000000305c019000000000303004b000000bc0000c13d1eb21e100000040f000000400200043d00000040032000390000000000130435000000400100003900000000011204360000000a030000290000000000310435000007d50320009c000003fa0000213d0000006003200039000000400030043f000007ae03000041000007ae0410009c000000000103801900000040011002100000000002020433000007ae0420009c00000000020380190000006002200210000000000112019f0000000002000414000007ae0420009c0000000002038019000000c002200210000000000112019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d000000000101043b000000400200043d0000002003200039000000110400002900000000004304350000000000120435000007ae01000041000007ae0320009c00000000020180190000004001200210000007d6011001c700001eb30001042e000007b60da0009c000003fa0000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000004e80000613d000000f809900210000000000229019f000007bc0220004100000000002d0435000000400200043d0000002009200039000007bf0b0000410000000000b90435000000210b200039000000000c0a0433000000000d0c004b00000e750000613d000000000d000019000000000ebd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ecd004b00000e6e0000413d000000000abc001900000000000a0435000000000b070433000000000c0b004b00000e820000613d000000000c000019000000000dac0019000000200cc00039000000000e7c0019000000000e0e04330000000000ed0435000000000dbc004b00000e7b0000413d0000000007ab00190000000000070435000000000a080433000000000b0a004b00000e8f0000613d000000000b000019000000000c7b0019000000200bb00039000000000d8b0019000000000d0d04330000000000dc0435000000000cab004b00000e880000413d000000000551034f00000000017a00190000001f0740018f0000000000010435000000050840027200000e9e0000613d000000000a000019000000050ba00210000000000cb10019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b00000e960000413d000000000a07004b00000ead0000613d0000000508800210000000000585034f00000000088100190000000307700210000000000a080433000000000a7a01cf000000000a7a022f000000000505043b0000010007700089000000000575022f00000000057501cf0000000005a5019f0000000000580435000000000141001900000000000104350000000004060433000000000504004b00000eba0000613d000000000500001900000000071500190000002005500039000000000865001900000000080804330000000000870435000000000745004b00000eb30000413d000000000114001900000000000104350000000001210049000000200410008a00000000004204350000001f01100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000007b20410009c000003fa0000213d0000000103300190000003fa0000c13d00000daa0000013d000000400100043d000a00000001001d0000000b010000290000010004100039000000000142034f000000000301043b000000800130008c00000f7d0000413d0000008001300270000007b80530009c000000000103a019000007b80530009c0000000005000019000000100500203900000008065001bf000007b20710009c000000000605a0190000004005100270000007b20710009c000000000501a01900000004016001bf000007ae0750009c000000000106a0190000002006500270000007ae0750009c000000000605a01900000002051001bf0000ffff0760008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004106500039000000000116016f0000000a011000290000000a0610006c00000000060000190000000106004039000007b20710009c000003fa0000213d0000000106600190000003fa0000c13d000000400010043f00000002015000390000000a06000029000000000616043600000000010000310000002107500039000000050770027200000f080000613d000000000812034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000f000000413d000000000700004b00000f0a0000613d0000000a070000290000000007070433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000035301cf000000ff0550008c00000000030020190000000a05000029000000210550003900000f910000013d0000000001000415000a00000001001d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000400300043d000000000401043b000000800140008c0000103f0000413d0000008001400270000007b80240009c000000000104a019000007b80240009c0000000002000019000000100200203900000008052001bf000007b20610009c000000000502a0190000004002100270000007b20610009c000000000201a01900000004015001bf000007ae0620009c000000000105a0190000002006200270000007ae0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000007b20610009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f00000002015000390000000006130436000000010100036700000000020000310000002107500039000000050770027200000f640000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000f5c0000413d000000000700004b00000f660000613d0000000007030433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c00000000040020190000002105300039000010520000013d000000400100043d0000004402100039000007d70300004100000000003204350000002402100039000000130300003900000c9e0000013d0000000a01000029000007b60110009c000003fa0000213d0000000a050000290000004001500039000000400010043f000000010100003a00000000051504360000000001000031000000000612034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807300210000007b308000041000000000303004b000000000807c019000007b703600197000000000383019f0000000000350435000000400300043d000000600440008a000000000542034f000000000505043b000000800650008c000010a00000413d0000008006500270000007b80750009c000000000605a019000007b80750009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007730019000000000837004b00000000080000190000000108004039000007b20970009c000003fa0000213d0000000108800190000003fa0000c13d000000400070043f000000020760003900000000077304360000002108600039000000050880027200000fcc0000613d000000000912034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b00000fc40000413d000000000800004b00000fce0000613d0000000008030433000000000808004b000004e80000613d0000000008070433000007b708800197000000f809600210000000000889019f000007b90880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106300039000010b10000013d000007b60130009c000003fa0000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000101000367000000000621034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807400210000007b308000041000000000404004b000000000807c019000007b704600197000000000484019f0000000000450435000000400500043d0000000c040000290000010404400039000000000641034f000000000606043b000000800760008c000010fe0000413d0000008007600270000007b80860009c000000000706a019000007b80860009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008850019000000000958004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f00000002087000390000000008850436000000210970003900000005099002720000102d0000613d000000000a21034f000000000b000019000000050cb00210000000000dc80019000000000cca034f000000000c0c043b0000000000cd0435000000010bb00039000000000c9b004b000010250000413d000000000900004b0000102f0000613d0000000009050433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c000000000600201900000021075000390000110f0000013d000007b60130009c000003fa0000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000101000367000000000621034f0000000006600350000000000606043b0000000000650435000004e80000613d000000f807400210000007b308000041000000000404004b000000000807c019000007b704600197000000000484019f0000000000450435000000400500043d0000000c040000290000010404400039000000000641034f000000000606043b000000800760008c0000115c0000413d0000008007600270000007b80860009c000000000706a019000007b80860009c0000000008000019000000100800203900000008098001bf000007b20a70009c000000000908a0190000004008700270000007b20a70009c000000000807a019000000040a9001bf000007ae0780009c000000000a09a0190000002009800270000007ae0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008850019000000000958004b00000000090000190000000109004039000007b20a80009c000003fa0000213d0000000109900190000003fa0000c13d000000400080043f00000002087000390000000008850436000000210970003900000005099002720000108e0000613d000000000a21034f000000000b000019000000050cb00210000000000dc80019000000000cca034f000000000c0c043b0000000000cd0435000000010bb00039000000000c9b004b000010860000413d000000000900004b000010900000613d0000000009050433000000000909004b000004e80000613d0000000009080433000007b709900197000000f80a70021000000000099a019f000007b90990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c000000000600201900000021075000390000116d0000013d000007b60630009c000003fa0000213d0000004006300039000000400060043f000000000712034f000000010600003a00000000066304360000000007700350000000000707043b0000000000760435000004e80000613d000000f808500210000007b309000041000000000505004b000000000908c019000007b705700197000000000595019f0000000000560435000000400440008a000000000542034f000000400400043d000000000505043b000000800650008c000011ba0000413d0000008006500270000007b80750009c000000000605a019000007b80750009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007740019000000000847004b00000000080000190000000108004039000007b20970009c000003fa0000213d0000000108800190000003fa0000c13d000000400070043f0000000207600039000000000774043600000021086000390000000508800272000010ec0000613d000000000912034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b000010e40000413d000000000800004b000010ee0000613d0000000008040433000000000808004b000004e80000613d0000000008070433000007b708800197000000f809600210000000000889019f000007b90880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106400039000011cb0000013d000007b60750009c000003fa0000213d0000004007500039000000400070043f000000000821034f000000010700003a00000000077504360000000008800350000000000808043b0000000000870435000004e80000613d000000f809600210000007b30a000041000000000606004b000000000a09c019000007b7068001970000000006a6019f0000000000670435000000400600043d000000600440008a000000000741034f000000000707043b000000800870008c0000125b0000413d0000008008700270000007b80970009c000000000807a019000007b80970009c00000000090000190000001009002039000000080a9001bf000007b20b80009c000000000a09a0190000004009800270000007b20b80009c000000000908a019000000040ba001bf000007ae0890009c000000000b0aa019000000200a900270000007ae0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009960019000000000a69004b000000000a000019000000010a004039000007b20b90009c000003fa0000213d000000010aa00190000003fa0000c13d000000400090043f00000002098000390000000009960436000000210a800039000000050aa002720000114a0000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000011420000413d000000000a00004b0000114c0000613d000000000a060433000000000a0a004b000004e80000613d000000000a090433000007b70aa00197000000f80b800210000000000aab019f000007b90aa000410000000000a904350000000308800210000000f80880008900000000078701cf000000ff0880008c000000000700201900000021086000390000126c0000013d000007b60750009c000003fa0000213d0000004007500039000000400070043f000000000821034f000000010700003a00000000077504360000000008800350000000000808043b0000000000870435000004e80000613d000000f809600210000007b30a000041000000000606004b000000000a09c019000007b7068001970000000006a6019f0000000000670435000000400600043d000000400440008a000000000741034f000000000707043b000000800870008c000012b90000413d0000008008700270000007b80970009c000000000807a019000007b80970009c00000000090000190000001009002039000000080a9001bf000007b20b80009c000000000a09a0190000004009800270000007b20b80009c000000000908a019000000040ba001bf000007ae0890009c000000000b0aa019000000200a900270000007ae0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009960019000000000a69004b000000000a000019000000010a004039000007b20b90009c000003fa0000213d000000010aa00190000003fa0000c13d000000400090043f00000002098000390000000009960436000000210a800039000000050aa00272000011a80000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000011a00000413d000000000a00004b000011aa0000613d000000000a060433000000000a0a004b000004e80000613d000000000a090433000007b70aa00197000000f80b800210000000000aab019f000007b90aa000410000000000a904350000000308800210000000f80880008900000000078701cf000000ff0880008c00000000070020190000002108600039000012ca0000013d000007b60640009c000003fa0000213d0000004006400039000000400060043f000000000712034f000000010600003a00000000066404360000000007700350000000000707043b0000000000760435000004e80000613d000000f808500210000007b309000041000000000505004b000000000908c019000007b705700197000000000595019f0000000000560435000000400500043d000900000005001d00000020055000390000000006030433000000000706004b000011da0000613d000000000700001900000000085700190000002007700039000000000937001900000000090904330000000000980435000000000867004b000011d30000413d000000000356001900000000000304350000000005040433000000000605004b000011e70000613d000000000600001900000000073600190000002006600039000000000846001900000000080804330000000000870435000000000756004b000011e00000413d0000000003350019000000000003043500000009050000290000000003530049000000200430008a00000000004504350000001f033000390007002000000092000000070330017f0000000004530019000000000334004b00000000030000190000000103004039000800000004001d000007b20440009c000003fa0000213d0000000103300190000003fa0000c13d0000000803000029000000400030043f000007b60330009c000003fa0000213d0000000c060000290000004403600039000000000332034f000000000303043b00000008070000290000004004700039000000400040043f0000002004700039000007ba050000410000000000540435000000150400003900000000004704350000006003300210000000210470003900000000003404350000012403600039000000000432034f000000400500043d000600000005001d000000000404043b000000800540008c000013e70000413d0000008005400270000007b80640009c000000000504a019000007b80640009c0000000006000019000000100600203900000008076001bf000007b20850009c000000000706a0190000004006500270000007b20850009c000000000605a01900000004087001bf000007ae0560009c000000000807a0190000002007600270000007ae0560009c000000000706a01900000002058001bf0000ffff0670008c000000000508a0190000001006700270000000000607a019000000ff0660008c00000001055020390000004106500039000000070660017f0000000606600029000000060760006c00000000070000190000000107004039000007b20860009c000003fa0000213d0000000107700190000003fa0000c13d000000400060043f00000002065000390000000607000029000000000667043600000021075000390000000507700272000012470000613d000000000812034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b0000123f0000413d000000000700004b000012490000613d00000006070000290000000007070433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c000000000400201900000006050000290000002105500039000013fa0000013d000007b60860009c000003fa0000213d0000004008600039000000400080043f000000000921034f000000010800003a00000000088604360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a700210000007b30b000041000000000707004b000000000b0ac019000007b7079001970000000007b7019f0000000000780435000000400700043d000000400440008a000000000841034f000000000808043b000000800980008c000013170000413d0000008009800270000007b80a80009c000000000908a019000007b80a80009c000000000a000019000000100a002039000000080ba001bf000007b20c90009c000000000b0aa019000000400a900270000007b20c90009c000000000a09a019000000040cb001bf000007ae09a0009c000000000c0ba019000000200ba00270000007ae09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa70019000000000b7a004b000000000b000019000000010b004039000007b20ca0009c000003fa0000213d000000010bb00190000003fa0000c13d0000004000a0043f000000020a900039000000000aa70436000000210b900039000000050bb00272000012a70000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b0000129f0000413d000000000b00004b000012a90000613d000000000b070433000000000b0b004b000004e80000613d000000000b0a0433000007b70bb00197000000f80c900210000000000bbc019f000007b90bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c00000000080020190000002109700039000013280000013d000007b60860009c000003fa0000213d0000004008600039000000400080043f000000000921034f000000010800003a00000000088604360000000009900350000000000909043b0000000000980435000004e80000613d000000f80a700210000007b30b000041000000000707004b000000000b0ac019000007b7079001970000000007b7019f0000000000780435000000400700043d000000200440008a000000000841034f000000000808043b000000800980008c000013880000413d0000008009800270000007b80a80009c000000000908a019000007b80a80009c000000000a000019000000100a002039000000080ba001bf000007b20c90009c000000000b0aa019000000400a900270000007b20c90009c000000000a09a019000000040cb001bf000007ae09a0009c000000000c0ba019000000200ba00270000007ae09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa70019000000000b7a004b000000000b000019000000010b004039000007b20ca0009c000003fa0000213d000000010bb00190000003fa0000c13d0000004000a0043f000000020a900039000000000aa70436000000210b900039000000050bb00272000013050000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b000012fd0000413d000000000b00004b000013070000613d000000000b070433000000000b0b004b000004e80000613d000000000b0a0433000007b70bb00197000000f80c900210000000000bbc019f000007b90bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c00000000080020190000002109700039000013990000013d000007b60970009c000003fa0000213d0000004009700039000000400090043f000000000a21034f000000010900003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000000f80b800210000007b30c000041000000000808004b000000000c0bc019000007b708a001970000000008c8019f0000000000890435000000400900043d000007b60890009c000003fa0000213d000000200840008a000000000881034f000000000808043b000000400a9000390000004000a0043f000000200a900039000007ba0b0000410000000000ba0435000000150a0000390000000000a904350000006008800210000000210a90003900000000008a0435000000c004400039000000000441034f000000400800043d000000000404043b000900000004001d000000800a40008c000014b60000413d0000000904000029000000800a400270000007b80b40009c000000000a04a019000007b80b40009c000000000b000019000000100b002039000000080cb001bf000007b20da0009c000000000c0ba019000000400ba00270000007b20da0009c000000000b0aa019000000040dc001bf000007ae0ab0009c000000000d0ca019000000200cb00270000007ae0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000007b20db0009c000003fa0000213d000000010cc00190000003fa0000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc00272000013750000613d000000000d21034f000000000e000019000000050fe002100000000004fb0019000000000ffd034f000000000f0f043b0000000000f40435000000010ee000390000000004ce004b0000136d0000413d000000000400004b000013770000613d0000000004080433000000000404004b000004e80000613d00000000040b0433000007b704400197000000f80ca0021000000000044c019f000007b90440004100000000004b04350000000304a00210000000f804400089000000090a4001ef000000ff0440008c000000000a00201900000021048000390000000000a40435000014c90000013d000007b60970009c000003fa0000213d0000004009700039000000400090043f000000000a21034f000000010900003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000004e80000613d000000f80b800210000007b30c000041000000000808004b000000000c0bc019000007b708a001970000000008c8019f0000000000890435000000400800043d00090040004000920000000909100360000000000909043b000000800a90008c000014410000413d000000800a900270000007b80b90009c000000000a09a019000007b80b90009c000000000b000019000000100b002039000000080cb001bf000007b20da0009c000000000c0ba019000000400ba00270000007b20da0009c000000000b0aa019000000040dc001bf000007ae0ab0009c000000000d0ca019000000200cb00270000007ae0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000007b20db0009c000003fa0000213d000000010cc00190000003fa0000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc00272000013d40000613d000000000d21034f000000000e000019000000050fe002100000000004fb0019000000000ffd034f000000000f0f043b0000000000f40435000000010ee000390000000004ce004b000013cc0000413d000000000400004b000013d60000613d0000000004080433000000000404004b000004e80000613d00000000040b0433000007b704400197000000f80ca0021000000000044c019f000007b90440004100000000004b04350000000304a00210000000f80440008900000000094901cf000000ff0440008c000000000900201900000021048000390000000000940435000014530000013d0000000605000029000007b60550009c000003fa0000213d00000006070000290000004005700039000000400050043f000000000612034f000000010500003a00000000055704360000000006600350000000000606043b0000000000650435000004e80000613d000000f807400210000007b308000041000000000404004b000000000807c019000007b704600197000000000484019f00000000004504350000000b0a0000290000000006a10049000000a004300039000000000342034f000000000503043b0000001f0360008a000007b306300197000007b307500197000007b308000041000000000967004b00000000090000190000000009084019000000000667013f000000000735004b0000000008004019000007b30660009c000000000908c019000000000609004b000000bc0000c13d0000000006a50019000000000562034f000000000505043b000007b20750009c000000bc0000213d00000000075100490000002006600039000007b308000041000000000976004b00000000090000190000000009082019000007b307700197000007b30a600197000000000b7a004b000000000800801900000000077a013f000007b30770009c000000000809c019000000000708004b000000bc0000c13d000000010750008c000016330000c13d000000000562034f000000000505043b000000010600008a000007b307000041000000000665004b00000000060000190000000006072019000007b305500197000007b30850009c0000000007008019000007b305500167000007b30550009c000000000706c019000500600000003d000000000507004b000016710000c13d000000400500043d000500000005001d000007b60550009c000003fa0000213d00000005070000290000004005700039000000400050043f0000002005700039000007b906000041000000000065043500000001050000390000000000570435000016710000013d000007b60480009c000003fa0000213d0000004004800039000000400040043f000000000421034f000000010a00003a000000000aa804360000000004400350000000000b04043b0000000000ba0435000004e80000613d000000f804900210000007b30c000041000000000909004b000000000c04c019000007b704b001970000000004c4019f00000000004a0435000000400a00043d000007b604a0009c000003fa0000213d000000090c0000290000002004c0008a000000000441034f000000000404043b0000004009a00039000000400090043f0000002009a00039000007ba0b0000410000000000b90435000000150900003900000000009a043500000060044002100000002109a000390000000000490435000000c004c00039000000000441034f000000400900043d000000000404043b000900000004001d000000800b40008c0000156e0000413d0000000904000029000000800b400270000007b80c40009c000000000b04a019000007b80c40009c000000000c000019000000100c002039000000080dc001bf000007b20eb0009c000000000d0ca019000000400cb00270000007b20eb0009c000000000c0ba019000000040ed001bf000007ae0bc0009c000000000e0da019000000200dc00270000007ae0bc0009c000000000d0ca0190000000204e001bf0000ffff0cd0008c00000000040ea019000000100cd00270000000000c0da019000000ff0cc0008c0000000104402039000000200c00008a000800000004001d000000410d400039000000000ccd016f000000000cc90019000000000d9c004b000000000d000019000000010d004039000007b20ec0009c000003fa0000213d000000010dd00190000003fa0000c13d0000004000c0043f0000000804000029000000020c400039000000000cc90436000000210d400039000000050dd00272000014a20000613d000000000e21034f000000000f0000190000000504f00210000000000b4c001900000000044e034f000000000404043b00000000004b0435000000010ff000390000000004df004b0000149a0000413d000000000400004b000014a40000613d0000000004090433000000000404004b000004e80000613d00000000040c0433000007b704400197000000080d000029000000f80bd0021000000000044b019f000007b90440004100000000004c04350000000304d00210000000f804400089000000090b4001ef000000ff0440008c000000000b00201900000021049000390000000000b40435000015810000013d000007b60480009c000003fa0000213d0000004004800039000000400040043f000000000421034f000000010a00003a000000000aa804360000000004400350000000000b04043b0000000000ba0435000004e80000613d000000090d000029000000f804d00210000007b30c000041000000000d0d004b000000000c04c019000007b704b001970000000004c4019f00000000004a0435000000400400043d000000200a400039000000000b030433000000000c0b004b000014d60000613d000000000c000019000000000dac0019000000200cc00039000000000e3c0019000000000e0e04330000000000ed0435000000000dbc004b000014cf0000413d0000000003ab00190000000000030435000000000a050433000000000b0a004b000014e30000613d000000000b000019000000000c3b0019000000200bb00039000000000d5b0019000000000d0d04330000000000dc0435000000000cab004b000014dc0000413d00000000033a001900000000000304350000000005060433000000000a05004b000014f00000613d000000000a000019000000000b3a0019000000200aa00039000000000c6a0019000000000c0c04330000000000cb0435000000000b5a004b000014e90000413d000000000335001900000000000304350000000005070433000000000605004b000014fd0000613d0000000006000019000000000a3600190000002006600039000000000b760019000000000b0b04330000000000ba0435000000000a56004b000014f60000413d000000000335001900000000000304350000000005090433000000000605004b0000150a0000613d000000000600001900000000073600190000002006600039000000000a960019000000000a0a04330000000000a70435000000000756004b000015030000413d000000000335001900000000000304350000000005080433000000000605004b000015170000613d000000000600001900000000073600190000002006600039000000000986001900000000090904330000000000970435000000000756004b000015100000413d000000000335001900000000000304350000000003430049000000200530008a00000000005404350000001f05300039000000200300008a000000000535016f0000000007450019000000000557004b00000000050000190000000105004039000007b20670009c000003fa0000213d0000000105500190000003fa0000c13d000000400070043f0000000b0d0000290000000006d200490000000c05000029000001c40c5000390000000005c1034f000000000505043b0000001f0960008a000007b306900197000007b308500197000007b30a000041000000000b68004b000000000b000019000000000b0a4019000000000668013f000000000895004b000000000a004019000007b30660009c000000000b0ac01900000000060b004b000000bc0000c13d0000000006d50019000000000561034f000000000505043b000007b20850009c000000bc0000213d00000000085200490000002006600039000007b30a000041000000000b86004b000000000b000019000000000b0a2019000007b308800197000c00000006001d000007b30d600197000000000e8d004b000000000a00801900000000088d013f000007b30880009c000000000a0bc01900000000080a004b000000bc0000c13d000000010850008c000016e60000c13d0000000c08100360000000000808043b000000010a00008a000007b30b000041000000000aa8004b000000000a000019000000000a0b2019000007b308800197000007b30d80009c000000000b008019000007b308800167000007b30880009c000000000b0ac0190000006008000039000000000a0b004b0000171f0000c13d000007b60870009c000003fa0000213d0000004008700039000000400080043f0000002008700039000007b90a0000410000000000a804350000000108000039000000000087043500000000080700190000171f0000013d000007b60490009c000003fa0000213d0000004004900039000000400040043f000000000421034f000000010b00003a000000000bb904360000000004400350000000000c04043b0000000000cb0435000004e80000613d000000090e000029000000f804e00210000007b30d000041000000000e0e004b000000000d04c019000007b704c001970000000004d4019f00000000004b0435000000400400043d000000200b400039000000000c030433000000000d0c004b0000158e0000613d000000000d000019000000000ebd0019000000200dd00039000000000f3d0019000000000f0f04330000000000fe0435000000000ecd004b000015870000413d0000000003bc00190000000000030435000000000b050433000000000c0b004b0000159b0000613d000000000c000019000000000d3c0019000000200cc00039000000000e5c0019000000000e0e04330000000000ed0435000000000dbc004b000015940000413d00000000033b001900000000000304350000000005060433000000000b05004b000015a80000613d000000000b000019000000000c3b0019000000200bb00039000000000d6b0019000000000d0d04330000000000dc0435000000000c5b004b000015a10000413d000000000335001900000000000304350000000005070433000000000605004b000015b50000613d0000000006000019000000000b3600190000002006600039000000000c760019000000000c0c04330000000000cb0435000000000b56004b000015ae0000413d000000000335001900000000000304350000000005080433000000000605004b000015c20000613d000000000600001900000000073600190000002006600039000000000b860019000000000b0b04330000000000b70435000000000756004b000015bb0000413d0000000003350019000000000003043500000000050a0433000000000605004b000015cf0000613d0000000006000019000000000736001900000020066000390000000008a6001900000000080804330000000000870435000000000756004b000015c80000413d000000000335001900000000000304350000000005090433000000000605004b000015dc0000613d000000000600001900000000073600190000002006600039000000000896001900000000080804330000000000870435000000000756004b000015d50000413d000000000335001900000000000304350000000003430049000000200530008a00000000005404350000001f05300039000000200300008a000000000535016f0000000007450019000000000557004b00000000050000190000000105004039000007b20670009c000003fa0000213d0000000105500190000003fa0000c13d000000400070043f0000000b0d0000290000000006d200490000000c05000029000001c40c5000390000000005c1034f000000000505043b0000001f0960008a000007b306900197000007b308500197000007b30a000041000000000b68004b000000000b000019000000000b0a4019000000000668013f000000000895004b000000000a004019000007b30660009c000000000b0ac01900000000060b004b000000bc0000c13d0000000006d50019000000000561034f000000000505043b000007b20850009c000000bc0000213d00000000085200490000002006600039000007b30a000041000000000b86004b000000000b000019000000000b0a2019000007b308800197000c00000006001d000007b30d600197000000000e8d004b000000000a00801900000000088d013f000007b30880009c000000000a0bc01900000000080a004b000000bc0000c13d000000010850008c0000180d0000c13d0000000c08100360000000000808043b000000010a00008a000007b30b000041000000000aa8004b000000000a000019000000000a0b2019000007b308800197000007b30d80009c000000000b008019000007b308800167000007b30880009c000000000b0ac0190000006008000039000000000a0b004b000018460000c13d000007b60870009c000003fa0000213d0000004008700039000000400080043f0000002008700039000007b90a0000410000000000a80435000000010800003900000000008704350000000008070019000018460000013d000000400600043d000500000006001d000000380650008c0000165f0000413d0000002007500270000007ae0650009c000000000705a019000007ae0650009c0000000008000019000000040800203900000002068001bf0000ffff0970008c000000000608a0190000001008700270000000000807a019000000ff0780008c000000000700001900000001070020390000000508000029000007b60880009c000003fa0000213d000000000676019f00000005090000290000004007900039000000400070043f000000000812034f000000020760003a00000000077904360000000008800350000000000808043b0000000000870435000004e80000613d000007b708800197000000f809600210000000000889019f000007bb088001c700000000008704350000000306600210000000f80660015f00000000056501cf000000050600002900000021066000390000000000560435000016710000013d0000000506000029000007b60660009c000003fa0000213d00000005080000290000004006800039000000400060043f000000000712034f000000010600003a00000000066804360000000007700350000000000707043b0000000000760435000004e80000613d000000f805500210000007b707700197000000000557019f000007b30550016700000000005604350000002004400039000000000442034f000000000404043b000007b305000041000000000634004b00000000060000190000000006058019000007b303300197000007b307400197000000000837004b0000000005008019000000000337013f000007b30330009c000000000506c019000000000305004b0000000b03000029000000bc0000c13d0000000004340019000000000342034f000000000303043b000007b20530009c000000bc0000213d000000200530008c000000bc0000413d00000000053100490000002004400039000007b306000041000000000754004b00000000070000190000000007062019000007b305500197000007b308400197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000506004b000000bc0000c13d000000000542034f000000400600043d000400000006001d000000000505043b000000800650008c000017a80000413d0000008006500270000007b80750009c000000000605a019000007b80750009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c00000001066020390000004107600039000000070770017f0000000407700029000000040870006c00000000080000190000000108004039000007b20970009c000003fa0000213d0000000108800190000003fa0000c13d000000400070043f00000002076000390000000408000029000000000778043600000021086000390000000508800272000016d20000613d000000000912034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b000016ca0000413d000000000800004b000016d40000613d00000004080000290000000008080433000000000808004b000004e80000613d0000000008070433000007b708800197000000f809600210000000000889019f000007b90880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c000000000500201900000004060000290000002106600039000017bb0000013d000000380850008c0000170e0000413d000000200a500270000007ae0850009c000000000a05a019000007ae0850009c000000000b000019000000040b0020390000000208b001bf0000ffff0da0008c00000000080ba019000000100ba00270000000000b0aa019000000ff0ab0008c000000000a000019000000010a002039000007b60b70009c000003fa0000213d0000000008a8019f000000400a7000390000004000a0043f000000000b21034f000000020a80003a000000000aa70436000000000bb00350000000000b0b043b0000000000ba0435000004e80000613d000007b70bb00197000000f80d800210000000000bbd019f000007bb0bb001c70000000000ba04350000000308800210000000f80880015f00000000088501cf000000210a70003900000000008a043500000000080700190000171f0000013d000007b60870009c000003fa0000213d0000004008700039000000400080043f000000000a21034f000000010800003a0000000008870436000000000aa00350000000000a0a043b0000000000a80435000004e80000613d000000f80b500210000007b70aa00197000000000aba019f000007b30aa001670000000000a804350000000008070019000000400700043d000007b60a70009c000003fa0000213d000000400a7000390000004000a0043f000000000d21034f000000010600003a000700000006001d000000000a6704360000000006d003500008000000060353000000000606043b000900000006001d00000000006a0435000004e80000613d0000000906000029000007b706600197000600000006001d000007bc0b6001c70000000000ba0435000000200ac00039000000000aa1034f000000000c0a043b000007b30a000041000000000b9c004b000000000b000019000000000b0a8019000007b309900197000007b30fc00197000000000e9f004b000000000a00801900000000099f013f000007b30990009c000000000a0bc01900000000090a004b0000000b06000029000000bc0000c13d00000000096c0019000000000a91034f00000000060a043b000b00000006001d000007b20a60009c000000bc0000213d0000000b06000029000000200a60008c000000bc0000413d0000000b0220006a0000002006900039000007b309000041000000000a26004b000000000a000019000000000a092019000007b302200197000500000006001d000007b30b600197000000000c2b004b000000000900801900000000022b013f000007b30220009c00000000090ac019000000000209004b000000bc0000c13d0000000509100360000000400200043d000000000609043b000400000006001d000000800960008c000019140000413d00000004060000290000008009600270000007b80a60009c000000000906a019000007b80a60009c000000000a000019000000100a002039000000080ba001bf000007b20c90009c000000000b0aa019000000400a900270000007b20c90009c000000000a09a0190000000409b001bf000007ae0ca0009c00000000090ba019000000200ba00270000007ae0ca0009c000000000b0aa019000000020c9001bf0000ffff0ab0008c000000000c09a0190000001009b0027000000000090ba019000000ff0990008c000000010cc020390000004109c00039000000000939016f0000000009920019000000000a29004b000000000a000019000000010a004039000007b20b90009c000003fa0000213d000000010aa00190000003fa0000c13d000000400090043f0000000209c00039000000000f9204360000002109c000390000000509900272000017960000613d000000000e000019000000050ae00210000000000baf0019000000000aad034f000000000a0a043b0000000000ab0435000000010ee00039000000000a9e004b0000178e0000413d000000000600004b000017980000613d0000000009020433000000000909004b000004e80000613d00000000090f0433000007b709900197000000f80ac0021000000000099a019f000007b90990004100000000009f04350000000309c00210000000f809900089000000040a9001ef000000ff0990008c000000000a0020190000002109200039000019250000013d0000000406000029000007b60660009c000003fa0000213d00000004080000290000004006800039000000400060043f000000000712034f000000010600003a00000000066804360000000007700350000000000707043b0000000000760435000004e80000613d000000f808500210000007b309000041000000000505004b000000000908c019000007b705700197000000000595019f0000000000560435000000400530008c000000bc0000413d000000400500043d000300000005001d0000002004400039000000000542034f000000000505043b000000800650008c000018d10000413d0000008006500270000007b80750009c000000000605a019000007b80750009c0000000007000019000000100700203900000008087001bf000007b20960009c000000000807a0190000004007600270000007b20960009c000000000706a01900000004098001bf000007ae0670009c000000000908a0190000002008700270000007ae0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c00000001066020390000004107600039000000070770017f0000000307700029000000030870006c00000000080000190000000108004039000007b20970009c000003fa0000213d0000000108800190000003fa0000c13d000000400070043f00000002076000390000000308000029000000000778043600000021086000390000000508800272000017f90000613d000000000112034f0000000009000019000000050a900210000000000ba70019000000000aa1034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b000017f10000413d000000000100004b000017fb0000613d00000003010000290000000001010433000000000101004b000004e80000613d0000000001070433000007b701100197000000f808600210000000000118019f000007b90110004100000000001704350000000301600210000000f80110008900000000051501cf000000ff0110008c000000000500201900000003010000290000002101100039000018e40000013d000000380850008c000018350000413d000000200a500270000007ae0850009c000000000a05a019000007ae0850009c000000000b000019000000040b0020390000000208b001bf0000ffff0da0008c00000000080ba019000000100ba00270000000000b0aa019000000ff0ab0008c000000000a000019000000010a002039000007b60b70009c000003fa0000213d0000000008a8019f000000400a7000390000004000a0043f000000000b21034f000000020a80003a000000000aa70436000000000bb00350000000000b0b043b0000000000ba0435000004e80000613d000007b70bb00197000000f80d800210000000000bbd019f000007bb0bb001c70000000000ba04350000000308800210000000f80880015f00000000088501cf000000210a70003900000000008a04350000000008070019000018460000013d000007b60870009c000003fa0000213d0000004008700039000000400080043f000000000a21034f000000010800003a0000000008870436000000000aa00350000000000a0a043b0000000000a80435000004e80000613d000000f80b500210000007b70aa00197000000000aba019f000007b30aa001670000000000a804350000000008070019000000400700043d000007b60a70009c000003fa0000213d000000400a7000390000004000a0043f000000000d21034f000000010600003a000700000006001d000000000f6704360000000006d003500008000000060353000000000606043b000900000006001d00000000006f0435000004e80000613d0000000906000029000007b706600197000600000006001d000007bc0b6001c70000000000bf0435000000200bc00039000000000bb1034f000000000c0b043b000007b30b000041000000000f9c004b000000000f000019000000000f0b8019000007b309900197000007b30ec00197000000000a9e004b000000000b00801900000000099e013f000007b30990009c000000000b0fc01900000000090b004b0000000b06000029000000bc0000c13d00000000096c0019000000000a91034f00000000060a043b000b00000006001d000007b20a60009c000000bc0000213d0000000b06000029000000200a60008c000000bc0000413d0000000b0220006a0000002006900039000007b309000041000000000a26004b000000000a000019000000000a092019000007b302200197000400000006001d000007b30b600197000000000c2b004b000000000900801900000000022b013f000007b30220009c00000000090ac019000000000209004b000000bc0000c13d0000000409100360000000400200043d000000000609043b000500000006001d000000800a60008c000000200f2000390000197b0000413d0000000506000029000000800a600270000007b80b60009c000000000a06a019000007b80b60009c000000000b000019000000100b002039000000080cb001bf000007b20ea0009c000000000c0ba019000000400ba00270000007b20ea0009c000000000b0aa019000000040ec001bf000007ae0ab0009c000000000e0ca019000000200cb00270000007ae0ab0009c000000000c0ba019000000020ae001bf0000ffff0bc0008c000000000a0ea019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000410ba00039000000000b3b016f000000000cb20019000000000b2c004b000000000e000019000000010e004039000007b20bc0009c000003fa0000213d000000010be00190000003fa0000c13d0000004000c0043f000000020ba000390000000000b20435000000210ba00039000000050eb00272000018be0000613d000000000c000019000000050bc002100000000009bf0019000000000bbd034f000000000b0b043b0000000000b90435000000010cc000390000000009ec004b000018b60000413d000000000600004b000018c00000613d0000000009020433000000000909004b000004e80000613d00000000090f0433000007b709900197000000f80ba0021000000000099b019f000007b90990004100000000009f04350000000309a00210000000f809900089000000050a9001ef000000ff0990008c000000000a00201900000021092000390000000000a904350000198c0000013d0000000306000029000007b60660009c000003fa0000213d00000003070000290000004006700039000000400060043f000000000612034f000000010100003a00000000011704360000000006600350000000000606043b0000000000610435000004e80000613d000000f807500210000007b308000041000000000505004b000000000807c019000007b705600197000000000585019f0000000000510435000000410130008c000004e80000413d0000002001400039000000000112034f000000000101043b000000f801100270000200000001001d0000001b0110008a000000020110008c00001b780000813d0000000c01000029000101440010003d0000000101200360000000000101043b000000000101004b00001aa90000613d000007b4010000410000000000100439000007ae010000410000000002000414000007ae0320009c0000000002018019000000c001200210000007b5011001c70000800b020000391eb21ea80000040f0000000102200190000019130000613d000000000201043b0000000101200210000000000302004b0000190b0000613d000000090300008a000000000331004b0000190f0000213d00000000322100d9000000020220008c0000190f0000c13d00000002011000290000000803100039000000020130006c000019e10000813d000007d30100004100000000001004350000001101000039000004eb0000013d000000000001042f000007b60920009c000003fa0000213d0000004009200039000000400090043f00000020092000390000000906000029000000000069043500000007060000290000000000620435000000000a06004b000004e80000613d0000000406000029000000f80a600210000007b30b000041000000000c06004b000000000b0ac019000000060ab001af0000000000a904350000000b06000029000000400960008c000000bc0000413d000000400900043d0000000506000029000500200060003d000000050a10036000000000060a043b000900000006001d000000800a60008c000000200e90003900001a2d0000413d0000000906000029000000800a600270000007b80b60009c000000000a06a019000007b80b60009c000000000b000019000000100b002039000000080cb001bf000007b20fa0009c000000000c0ba019000000400ba00270000007b20fa0009c000000000b0aa019000000040ac001bf000007ae0fb0009c000000000a0ca019000000200cb00270000007ae0fb0009c000000000c0ba0190000000206a001bf0000ffff0bc0008c00000000060aa019000000100ac00270000000000a0ca019000000ff0aa0008c0000000106602039000600000006001d000000410a600039000000000a3a016f000000000ca90019000000000a9c004b000000000a000019000000010a004039000007b20bc0009c000003fa0000213d000000010aa00190000003fa0000c13d0000004000c0043f0000000606000029000000020a6000390000000000a90435000000210a600039000000050fa00272000019670000613d000000000c000019000000050ac00210000000000bae0019000000000aad034f000000000a0a043b0000000000ab0435000000010cc00039000000000afc004b0000195f0000413d000000000600004b000019690000613d000000000a090433000000000a0a004b000004e80000613d000000000a0e0433000007b70aa001970000000606000029000000f80b600210000000000aab019f000007b90aa000410000000000ae0435000000030a600210000000f80aa00089000000090ba001ef000000ff0aa0008c000000000b002019000000210a9000390000000000ba043500001a400000013d000007b60920009c000003fa0000213d0000004009200039000000400090043f000000090600002900000000006f043500000007060000290000000000620435000000000906004b000004e80000613d0000000506000029000000f809600210000007b30a000041000000000b06004b000000000a09c0190000000609a001af00000000009f04350000000b06000029000000400960008c000000bc0000413d000000400900043d0000000406000029000500200060003d000000050a10036000000000060a043b000900000006001d000000800a60008c000000200e90003900001a6b0000413d0000000906000029000000800a600270000007b80b60009c000000000a06a019000007b80b60009c000000000b000019000000100b002039000000080cb001bf000007b20fa0009c000000000c0ba019000000400ba00270000007b20fa0009c000000000b0aa019000000040fc001bf000007ae0ab0009c000000000f0ca019000000200cb00270000007ae0ab0009c000000000c0ba0190000000206f001bf0000ffff0bc0008c00000000060fa019000000100bc00270000000000b0ca019000000ff0bb0008c0000000106602039000600000006001d000000410b600039000000000b3b016f000000000cb90019000000000b9c004b000000000f000019000000010f004039000007b20bc0009c000003fa0000213d000000010bf00190000003fa0000c13d0000004000c0043f0000000606000029000000020b6000390000000000b90435000000210b600039000000050cb00272000019cd0000613d000000000f000019000000050bf00210000000000abe0019000000000bbd034f000000000b0b043b0000000000ba0435000000010ff00039000000000acf004b000019c50000413d000000000600004b000019cf0000613d000000000a090433000000000a0a004b000004e80000613d000000000a0e0433000007b70aa001970000000606000029000000f80b600210000000000aab019f000007b90aa000410000000000ae0435000000030a600210000000f80aa00089000000090ba001ef000000ff0aa0008c000000000b002019000000210a9000390000000000ba043500001a7e0000013d000000800130008c000200000003001d00001aa90000413d0000008001300270000007b80230009c000000000103a019000007b80230009c0000000002000019000000100200203900000008042001bf000007b20510009c000000000402a0190000004002100270000007b20510009c000000000201a01900000004014001bf000007ae0520009c000000000104a0190000002004200270000007ae0520009c000000000402a01900000002051001bf0000ffff0240008c000000000501a0190000001001400270000000000104a019000000ff0110008c00000001055020390000004101500039000000070210017f000000400100043d0000000002210019000000000412004b00000000040000190000000104004039000007b20620009c000003fa0000213d0000000104400190000003fa0000c13d000000400020043f00000002025000390000000006210436000000010200036700000000040000310000002107500039000000050770027200001a1a0000613d000000000842034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00001a120000413d000000000700004b00001a1c0000613d0000000007010433000000000707004b000004e80000613d0000000007060433000007b707700197000000f808500210000000000778019f000007b90770004100000000007604350000000305500210000000f80550008900000000035301cf000000ff0550008c00000000030020190000002105100039000000000035043500001abf0000013d000007b60a90009c000003fa0000213d000000400a9000390000004000a0043f000000070a0000290000000000a90435000000080600035f000000000c06043b0000000000ce0435000000000a0a004b000004e80000613d0000000906000029000000f80a600210000007b30b000041000000000d06004b000000000b0ac019000007b70ac00197000000000aba019f0000000000ae04350000000b06000029000000410a60008c000004e80000413d0000000506000029000000200a600039000000000aa1034f0000000006000415000000100660008a000b0020006000cd000000000a0a043b000000f80ca002700000001b0ac0008c000000000e00001900001b280000613d0000001c0ac0008c00001b780000c13d00000000060004150000000f0660008a000b0020006000cd0000001b0ec0008a000000800ae0008c00001b280000413d000000400c00043d000007b60ac0009c000003fa0000213d000000400ac000390000004000a0043f000000020a00003a000000000aac0436000000080600035f000000000d06043b0000000000da0435000004e80000613d000007b70bd00197000007b90bb001c70000000000ba0435000000f80ae00210000000210bc000390000000000ab043500000000060004150000000f0660008a000b0020006000cd00001b3b0000013d000007b60a90009c000003fa0000213d000000400a9000390000004000a0043f000000070b0000290000000000b90435000000080600035f000000000a06043b0000000000ae0435000000000b0b004b000004e80000613d0000000906000029000000f80b600210000007b30c000041000000000d06004b000000000c0bc019000007b70aa00197000000000aca019f0000000000ae04350000000b06000029000000410a60008c000004e80000413d0000000506000029000000200a600039000000000ba1034f00000000060004150000000e0660008a000b0020006000cd000000000b0b043b000000f80cb002700000001b0bc0008c000000000d00001900001b7f0000613d0000001c0ac0008c00001b780000c13d00000000060004150000000d0660008a000b0020006000cd0000001b0dc0008a000000800bd0008c00001b7f0000413d000000400c00043d000007b60ac0009c000003fa0000213d000000400ac000390000004000a0043f000000020a00003a000000000aac0436000000080600035f000000000e06043b0000000000ea0435000004e80000613d000007b70be00197000007b90bb001c70000000000ba0435000000f80ad00210000000210bc000390000000000ab043500000000060004150000000d0660008a000b0020006000cd00001b920000013d000000400100043d000007b60210009c000003fa0000213d0000004002100039000000400020043f000000010200003a000000000321043600000000040000310000000102000367000000000542034f0000000005500350000000000505043b0000000000530435000004e80000613d0000000208000029000000f806800210000007b307000041000000000808004b000000000706c019000007b705500197000000000575019f000000000053043500000001030000290000008003300039000000000332034f0000000c0540006a000000230550008a000000000303043b000007b306000041000000000753004b00000000070000190000000007068019000007b305500197000007b308300197000000000958004b0000000006008019000000000558013f000007b30550009c000000000607c019000000000506004b0000000b06000029000000bc0000c13d0000000a050000290000000005050433000000090700002900000000070704330000000808000029000000000808043300000006090000290000000009090433000000050a000029000000000a0a04330000000006630019000000000362034f000000000303043b000007b20b30009c000000bc0000213d000000000b3400490000002006600039000007b30c000041000000000db6004b000000000d000019000000000d0c2019000007b30bb00197000007b30e600197000000000fbe004b000000000c008019000000000bbe013f000007b30bb0009c000000000c0dc019000000000b0c004b000000bc0000c13d0000000005570019000000000585001900000000059500190000000005a50019000000000535001900000004070000290000000007070433000000000575001900000003070000290000000007070433000000000575001900000000070104330000000005750019000000400700043d000007b205500197000000380850008c0000004009700039000000000842034f000000200470003900001bcf0000413d000000200b500270000007ae0a50009c000000000b05a019000007ae0a50009c000000000c000019000000040c002039000000020ac001bf0000ffff0db0008c000000000a0ca019000000100cb00270000000000c0ba019000000ff0bc0008c000000000b000019000000010b002039000007b60c70009c000003fa0000213d000000000aba019f000000400090043f0000000209a0003a00000000009704350000000008800350000000000808043b0000000000840435000004e80000613d000007b708800197000000f809a00210000000000889019f000007bd088001c700000000008404350000000304a00210000000f80440015f00000000044501cf0000002105700039000000000045043500001bdd0000013d000000400c00043d000007b60ac0009c000003fa0000213d000000400ac000390000004000a0043f000000070a000029000000000fac0436000000080600035f000000000d06043b0000000000df0435000000000a0a004b000004e80000613d000000f80ae00210000007b30b000041000000000e0e004b000000000b0ac019000007b70ad00197000000000aba019f0000000000af04350000000b06000029000000050a600270000000000a0c001f000000000a040433000000000a5a0019000000000b080433000000000aba0019000000000b070433000000000aba0019000000000b020433000000000aba0019000000000b090433000000000aba0019000000000b0c0433000000000aba0019000000400d00043d000007b206a00197000900000006001d000000380a60008c0006004000d0003d000b002000d0003d00001c9c0000413d0000000906000029000000200a600270000007ae0b60009c000000000a06a019000007ae0b60009c000000000f000019000000040f002039000000020bf001bf0000ffff0ea0008c000000000b0fa019000000100ea00270000000000e0aa019000000ff0ae0008c000000000a000019000000010a002039000007b60ed0009c000003fa0000213d000000000bab019f0000000606000029000000400060043f000000020ab0003a0000000000ad0435000000080600035f000000000a06043b0000000b060000290000000000a60435000004e80000613d000007b70aa00197000000f80eb00210000000000aae019f000007bd0aa001c70000000b060000290000000000a60435000000030ab00210000000f80aa0015f000000090aa001ef000000210bd000390000000000ab043500001caf0000013d000000400100043d0000004402100039000007d203000041000000000032043500000024021000390000000f0300003900000c9e0000013d000000400c00043d000007b60bc0009c000003fa0000213d000000400bc000390000004000b0043f000000070a000029000000000eac0436000000080600035f000000000f06043b0000000000fe0435000000000b0a004b000004e80000613d000000f80bd00210000007b30a000041000000000d0d004b000000000a0bc019000007b70bf00197000000000aab019f0000000000ae04350000000b06000029000000050a600270000000000a0c001f000000000a040433000000000a5a0019000000000b080433000000000aba0019000000000b070433000000000aba0019000000000b020433000000000aba0019000000000b090433000000000aba0019000000000b0c0433000000000aba0019000000400d00043d000007b206a00197000900000006001d000000380b60008c0006004000d0003d000b002000d0003d00001d540000413d0000000906000029000000200f600270000007ae0b60009c000000000f06a019000007ae0b60009c000000000e000019000000040e002039000000020be001bf0000ffff0af0008c000000000b0ea019000000100af00270000000000a0fa019000000ff0aa0008c000000000f000019000000010f002039000007b60ad0009c000003fa0000213d000000000bfb019f0000000606000029000000400060043f000000020ab0003a0000000000ad0435000000080600035f000000000f06043b0000000b060000290000000000f60435000004e80000613d000007b70af00197000000f80eb00210000000000aae019f000007bd0aa001c70000000b060000290000000000a60435000000030ab00210000000f80aa0015f000000090aa001ef000000210bd000390000000000ab043500001d670000013d000007b60a70009c000003fa0000213d000000400090043f000000010900003a00000000009704350000000008800350000000000808043b0000000000840435000004e80000613d000007b708800197000000f805500210000000000585019f000007bc055000410000000000540435000000400400043d00000020054000390000000008070433000000000908004b00001bea0000613d0000000009000019000000000a5900190000002009900039000000000b790019000000000b0b04330000000000ba0435000000000a89004b00001be30000413d000000000758001900000000000704350000000a080000290000000008080433000000000908004b00001bf80000613d0000000009000019000000000a79001900000020099000390000000a0b900029000000000b0b04330000000000ba0435000000000a89004b00001bf10000413d0000000007780019000000000007043500000009080000290000000008080433000000000908004b00001c060000613d0000000009000019000000000a7900190000002009900039000000090b900029000000000b0b04330000000000ba0435000000000a89004b00001bff0000413d0000000007780019000000000007043500000008080000290000000008080433000000000908004b00001c140000613d0000000009000019000000000a7900190000002009900039000000080b900029000000000b0b04330000000000ba0435000000000a89004b00001c0d0000413d0000000007780019000000000007043500000006080000290000000008080433000000000908004b00001c220000613d0000000009000019000000000a7900190000002009900039000000060b900029000000000b0b04330000000000ba0435000000000a89004b00001c1b0000413d0000000007780019000000000007043500000005080000290000000008080433000000000908004b00001c300000613d0000000009000019000000000a7900190000002009900039000000050b900029000000000b0b04330000000000ba0435000000000a89004b00001c290000413d000000000662034f00000000027800190000001f0730018f0000000000020435000000050830027200001c3f0000613d0000000009000019000000050a900210000000000ba20019000000000aa6034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b00001c370000413d000000000907004b00001c4e0000613d0000000508800210000000000686034f00000000088200190000000307700210000000000908043300000000097901cf000000000979022f000000000606043b0000010007700089000000000676022f00000000067601cf000000000696019f0000000000680435000000000232001900000000000204350000000003010433000000000603004b00001c5b0000613d000000000600001900000000072600190000002006600039000000000816001900000000080804330000000000870435000000000736004b00001c540000413d0000000001230019000000000001043500000004020000290000000002020433000000000302004b00001c690000613d000000000300001900000000061300190000002003300039000000040730002900000000070704330000000000760435000000000623004b00001c620000413d0000000001120019000000000001043500000003020000290000000002020433000000000302004b00001c770000613d000000000300001900000000061300190000002003300039000000030730002900000000070704330000000000760435000000000623004b00001c700000413d000000000112001900000000000104350000000001410049000000200210008a00000000002404350000001f01100039000000070210017f0000000001420019000000000221004b00000000020000190000000102004039000007b20310009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000007ae01000041000007ae0250009c000000000501801900000040025002100000000003040433000007ae0430009c00000000030180190000006003300210000000000223019f0000000003000414000007ae0430009c0000000003018019000000c001300210000000000121019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d000000000101043b00000e4d0000013d000007b60ad0009c000003fa0000213d0000000606000029000000400060043f000000070b0000290000000000bd0435000000080600035f000000000a06043b0000000b060000290000000000a60435000000000b0b004b000004e80000613d000007b70aa001970000000906000029000000f80b600210000000000aab019f000007bc0aa000410000000b060000290000000000a60435000000400600043d000000200a600039000007be0b00004100090000000a001d0000000000ba0435000b00000006001d000000210e600039000000000f0d0433000000000b0f004b00001cc10000613d000000000b000019000000000aeb0019000000200bb000390000000006db0019000000000606043300000000006a04350000000006fb004b00001cba0000413d000000000def001900000000000d0435000000000e04043300000000060e004b00001cce0000613d000000000b0000190000000006db0019000000200bb00039000000000a4b0019000000000a0a04330000000000a604350000000006eb004b00001cc70000413d000000000dde001900000000000d0435000000000e08043300000000040e004b00001cdb0000613d00000000040000190000000006d400190000002004400039000000000a840019000000000a0a04330000000000a604350000000006e4004b00001cd40000413d0000000c041003600000000001de00190000001f0650018f0000000000010435000000050850027200001cea0000613d000000000d000019000000050ad00210000000000ba10019000000000aa4034f000000000a0a043b0000000000ab0435000000010dd00039000000000a8d004b00001ce20000413d000000000a06004b00001cf90000613d0000000508800210000000000484034f00000000088100190000000306600210000000000a080433000000000a6a01cf000000000a6a022f000000000404043b0000010006600089000000000464022f00000000046401cf0000000004a4019f0000000000480435000000000151001900000000000104350000000004070433000000000504004b00001d060000613d000000000500001900000000061500190000002005500039000000000875001900000000080804330000000000860435000000000645004b00001cff0000413d0000000001140019000000000001043500000000040c0433000000000504004b00001d130000613d0000000005000019000000000615001900000020055000390000000007c5001900000000070704330000000000760435000000000645004b00001d0c0000413d000000000114001900000000000104350000000004020433000000000504004b00001d200000613d000000000500001900000000061500190000002005500039000000000725001900000000070704330000000000760435000000000645004b00001d190000413d000000000114001900000000000104350000000002090433000000000402004b00001d2d0000613d000000000400001900000000051400190000002004400039000000000694001900000000060604330000000000650435000000000524004b00001d260000413d000000000112001900000000000104350000000b040000290000000001410049000000200210008a00000000002404350000001f01100039000000000231016f0000000001420019000000000221004b00000000020000190000000102004039000007b20310009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000007ae010000410000000903000029000007ae0230009c000000000301801900000040023002100000000b030000290000000003030433000007ae0430009c00000000030180190000006003300210000000000223019f0000000003000414000007ae0430009c0000000003018019000000c001300210000000000121019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d00001e0b0000013d000007b60ad0009c000003fa0000213d0000000606000029000000400060043f000000070a0000290000000000ad0435000000080600035f000000000f06043b0000000b060000290000000000f60435000000000a0a004b000004e80000613d000007b70af001970000000906000029000000f80b600210000000000aab019f000007bc0aa000410000000b060000290000000000a60435000000400600043d000000200a600039000007bf0b00004100090000000a001d0000000000ba0435000b00000006001d000000210e600039000000000f0d0433000000000b0f004b00001d790000613d000000000b000019000000000aeb0019000000200bb000390000000006db0019000000000606043300000000006a04350000000006fb004b00001d720000413d000000000def001900000000000d0435000000000e04043300000000060e004b00001d860000613d000000000b0000190000000006db0019000000200bb00039000000000a4b0019000000000a0a04330000000000a604350000000006eb004b00001d7f0000413d000000000dde001900000000000d0435000000000e08043300000000040e004b00001d930000613d00000000040000190000000006d400190000002004400039000000000a840019000000000a0a04330000000000a604350000000006e4004b00001d8c0000413d0000000c041003600000000001de00190000001f0650018f0000000000010435000000050850027200001da20000613d000000000d000019000000050ad00210000000000ba10019000000000aa4034f000000000a0a043b0000000000ab0435000000010dd00039000000000a8d004b00001d9a0000413d000000000a06004b00001db10000613d0000000508800210000000000484034f00000000088100190000000306600210000000000a080433000000000a6a01cf000000000a6a022f000000000404043b0000010006600089000000000464022f00000000046401cf0000000004a4019f0000000000480435000000000151001900000000000104350000000004070433000000000504004b00001dbe0000613d000000000500001900000000061500190000002005500039000000000875001900000000080804330000000000860435000000000645004b00001db70000413d0000000001140019000000000001043500000000040c0433000000000504004b00001dcb0000613d0000000005000019000000000615001900000020055000390000000007c5001900000000070704330000000000760435000000000645004b00001dc40000413d000000000114001900000000000104350000000004020433000000000504004b00001dd80000613d000000000500001900000000061500190000002005500039000000000725001900000000070704330000000000760435000000000645004b00001dd10000413d000000000114001900000000000104350000000002090433000000000402004b00001de50000613d000000000400001900000000051400190000002004400039000000000694001900000000060604330000000000650435000000000524004b00001dde0000413d000000000112001900000000000104350000000b040000290000000001410049000000200210008a00000000002404350000001f01100039000000000231016f0000000001420019000000000221004b00000000020000190000000102004039000007b20310009c000003fa0000213d0000000102200190000003fa0000c13d000000400010043f000007ae010000410000000903000029000007ae0230009c000000000301801900000040023002100000000b030000290000000003030433000007ae0430009c00000000030180190000006003300210000000000223019f0000000003000414000007ae0430009c0000000003018019000000c001300210000000000121019f000007bf011001c700008010020000391eb21ea80000040f0000000102200190000000bc0000613d000000000101043b00000000020004150000000a02200069000000000200000200000e4d0000013d00000000030004140000000004120019000000000224004b00000000050000190000000105004039000007ae02100197000000010150019000001e690000c13d0000000001000031000000000541004b00001e690000413d0000000102200367000007c00530009c00001e6d0000813d0000000001410049000007ae0110019700000000011203df000000c002300210000007c102200197000007c2022001c700000000012103af00008010020000391eb21ead0000040f00000000030100190000006003300270000007ae03300197000000010220019000001e740000613d0000003f02300039000007c304200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000007b20640009c00001e8f0000213d000000010550019000001e8f0000c13d000000400040043f00000000043204360000001f05300039000000050550027200001e470000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b00001e3f0000413d000000000500004b00001e490000613d0000001f0530018f000000050330027200001e550000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b00001e4d0000413d000000000605004b00001e640000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f00000000001304350000000001020433000000200110008c00001e950000c13d0000000001040433000000000001042d000007d3010000410000000000100435000000110100003900001e920000013d000000400100043d0000004402100039000007d00300004100000000003204350000002402100039000000080300003900001e9b0000013d0000001f0430018f000000050230027200001e7f0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b00001e780000413d000000000504004b00001e8d0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f0000000000120435000000600130021000001eb400010430000007d30100004100000000001004350000004101000039000000040010043f000007d40100004100001eb400010430000000400100043d0000004402100039000007c503000041000000000032043500000024021000390000001f030000390000000000320435000007c6020000410000000000210435000000040210003900000020030000390000000000320435000007ae02000041000007ae0310009c00000000010280190000004001100210000007c7011001c700001eb400010430000000000001042f00001eab002104230000000102000039000000000001042d0000000002000019000000000001042d00001eb0002104230000000102000039000000000001042d0000000002000019000000000001042d00001eb20000043200001eb30001042e00001eb40001043000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000ffffffff00000000000000000000000000000000000000000000000000000000ebe4a3d700000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffff80000000000000000000000000000000000000000000000000000000000000009a8a0592ac89c5ad3bc6df8224c17b485976f597df104ee20d0df415241f670b0200000200000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffbf00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00000000000000000000000000000000ffffffffffffffffffffffffffffffff81000000000000000000000000000000000000000000000000000000000000009400000000000000000000000000000000000000000000000000000000000000b800000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000000f80000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000000000000ffffffff000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001ffffffe007ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff6b656363616b3235362072657475726e656420696e76616c696420646174610008c379a0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000064000000000000000000000000848e1bfa1ac4e3576b728bda6721b215c70a7799a5b4866282a71bab954baac8000000000000000000000000000000000000000000000000fffffffffffffe1fc2f8787176b8ac6bf7215b4adcc1e069bf4ab82d9ab1df05a57a91d425935b6ead7c5bef027816a800da1736444fb58a807ef4c9603b7848673f7e3a68eb14a519b453ce45aaaaf3a300f5a9ec95869b4f28ab10430b572ee218c3a6a5e07d6f000000000000000000000000000000000000000000000000ffffffffffffff5f1901000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff7f4f766572666c6f770000000000000000000000000000000000000000000000008080000000000000000000000000000000000000000000000000000000000000496e76616c696420762076616c756500000000000000000000000000000000004e487b71000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff9f0000000000000000000000000000000000000040000000000000000000000000556e737570706f72746564207478207479706500000000000000000000000000456e636f64696e6720756e737570706f727465642074780000000000000000000000000000000000000000000000000000000064000000800000000000000000d911e45b07a9c649117ffaea017b6308f32dfe1921ce79a3b2fc49b0d41abe31", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/ComplexUpgrader.json b/.test-node-subtree/src/deps/contracts/ComplexUpgrader.json new file mode 100644 index 00000000..d6b37671 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/ComplexUpgrader.json @@ -0,0 +1,30 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "ComplexUpgrader", + "sourceName": "cache-zk/solpp-generated-contracts/ComplexUpgrader.sol", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_delegateTo", + "type": "address" + }, + { + "internalType": "bytes", + "name": "_calldata", + "type": "bytes" + } + ], + "name": "upgrade", + "outputs": [], + "stateMutability": "payable", + "type": "function" + } + ], + "bytecode": "0x00030000000000020004000000000002000000000301001900000060033002700000004103300197000200000031035500010000000103550000008008000039000000400080043f00000001022001900000005a0000c13d000000040230008c000000620000413d000000000201043b0000004302200197000000440220009c000000620000c13d000000040230008a000000400220008c000000620000413d0000000402100370000000000902043b000000450290009c000000620000213d0000002402100370000000000202043b000000460420009c000000620000213d00000023042000390000004705000041000000000634004b000000000600001900000000060580190000004704400197000000000704004b0000000005008019000000470440009c000000000506c019000000000405004b000000620000c13d0000000405200039000000000151034f000000000401043b000000460140009c000000620000213d00000000014200190000002401100039000000000131004b000000620000213d0000000001000411000080070110008c000000640000c13d000100000005001d000200000004001d000400000008001d0000004c010000410000000000100439000300000009001d000000040090044300000041010000410000000002000414000000410320009c0000000002018019000000c0012002100000004d011001c7000080020200003900fd00f30000040f0000000102200190000000700000613d000000400800043d000000000101043b000000000101004b000000710000c13d000000440180003900000051030000410000000000310435000000240180003900000013030000390000000000310435000000480100004100000000001804350000000401800039000000200300003900000000003104350000004101000041000000410380009c0000000008018019000000400180021000000052011001c7000000ff000104300000000001000416000000000101004b000000620000c13d0000002001000039000001000010044300000120000004430000004201000041000000fe0001042e0000000001000019000000ff000104300000004801000041000000800010043f0000002001000039000000840010043f0000002401000039000000a40010043f0000004901000041000000c40010043f0000004a01000041000000e40010043f0000004b01000041000000ff00010430000000000001042f00000002090000290000001f0190018f0000000102000029000000200320003900000001033003670000000504900272000000810000613d000000000500001900000005065002100000000007680019000000000663034f000000000606043b00000000006704350000000105500039000000000645004b000000790000413d000000000501004b0000000302000029000000910000613d0000000504400210000000000343034f00000000044800190000000301100210000000000504043300000000051501cf000000000515022f000000000303043b0000010001100089000000000313022f00000000011301cf000000000151019f0000000000140435000000000198001900000000000104350000000001000414000000040320008c000000990000c13d00000000030000310000000002000019000000ab0000013d0000004103000041000000410490009c00000000090380190000006004900210000000410580009c00000000080380190000004005800210000000000545019f000000410410009c0000000001038019000000c001100210000000000151019f00fd00f80000040f000000010220015f00020000000103550000006001100270000000410010019d000000410310019700000004090000290000006001000039000000000403004b000000bb0000c13d0000000102200190000000f00000613d00000000010104330000004102000041000000410310009c0000000001028019000000410390009c000000000902801900000040029002100000006001100210000000000121019f000000ff000104300000004e0130009c000000ea0000813d0000001f01300039000000200400008a000000000141016f0000003f01100039000000000441016f000000400100043d0000000004410019000000000514004b00000000050000190000000105004039000000460640009c000000ea0000213d0000000105500190000000ea0000c13d000000400040043f0000001f0430018f000000000931043600000002050003670000000503300272000000da0000613d000000000600001900000005076002100000000008790019000000000775034f000000000707043b00000000007804350000000106600039000000000736004b000000d20000413d000000000604004b000000af0000613d0000000503300210000000000535034f00000000033900190000000304400210000000000603043300000000064601cf000000000646022f000000000505043b0000010004400089000000000545022f00000000044501cf000000000464019f0000000000430435000000af0000013d0000004f0100004100000000001004350000004101000039000000040010043f0000005001000041000000ff000104300000000001000019000000fe0001042e000000000001042f000000f6002104230000000102000039000000000001042d0000000002000019000000000001042d000000fb002104250000000102000039000000000001042d0000000002000019000000000001042d000000fd00000432000000fe0001042e000000ff00010430000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000ffffffff00000000000000000000000000000000000000000000000000000000c987336c00000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff000000000000000000000000000000000000000000000000ffffffffffffffff800000000000000000000000000000000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000043616e206f6e6c792062652063616c6c656420627920464f5243455f4445504c4f5945520000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000840000008000000000000000001806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b83020000020000000000000000000000000000002400000000000000000000000000000000000000000000000000000000000000000000000100000000000000004e487b7100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000000000000000000000044656c65676174656520697320616e20454f410000000000000000000000000000000000000000000000000000000000000000640000000000000000000000000000000000000000000000000000000000000000000000000000000000000000f880b7724c567d03c5657e7444e94f904c63a516ff873019c71825fc76343a7a", + "deployedBytecode": "0x00030000000000020004000000000002000000000301001900000060033002700000004103300197000200000031035500010000000103550000008008000039000000400080043f00000001022001900000005a0000c13d000000040230008c000000620000413d000000000201043b0000004302200197000000440220009c000000620000c13d000000040230008a000000400220008c000000620000413d0000000402100370000000000902043b000000450290009c000000620000213d0000002402100370000000000202043b000000460420009c000000620000213d00000023042000390000004705000041000000000634004b000000000600001900000000060580190000004704400197000000000704004b0000000005008019000000470440009c000000000506c019000000000405004b000000620000c13d0000000405200039000000000151034f000000000401043b000000460140009c000000620000213d00000000014200190000002401100039000000000131004b000000620000213d0000000001000411000080070110008c000000640000c13d000100000005001d000200000004001d000400000008001d0000004c010000410000000000100439000300000009001d000000040090044300000041010000410000000002000414000000410320009c0000000002018019000000c0012002100000004d011001c7000080020200003900fd00f30000040f0000000102200190000000700000613d000000400800043d000000000101043b000000000101004b000000710000c13d000000440180003900000051030000410000000000310435000000240180003900000013030000390000000000310435000000480100004100000000001804350000000401800039000000200300003900000000003104350000004101000041000000410380009c0000000008018019000000400180021000000052011001c7000000ff000104300000000001000416000000000101004b000000620000c13d0000002001000039000001000010044300000120000004430000004201000041000000fe0001042e0000000001000019000000ff000104300000004801000041000000800010043f0000002001000039000000840010043f0000002401000039000000a40010043f0000004901000041000000c40010043f0000004a01000041000000e40010043f0000004b01000041000000ff00010430000000000001042f00000002090000290000001f0190018f0000000102000029000000200320003900000001033003670000000504900272000000810000613d000000000500001900000005065002100000000007680019000000000663034f000000000606043b00000000006704350000000105500039000000000645004b000000790000413d000000000501004b0000000302000029000000910000613d0000000504400210000000000343034f00000000044800190000000301100210000000000504043300000000051501cf000000000515022f000000000303043b0000010001100089000000000313022f00000000011301cf000000000151019f0000000000140435000000000198001900000000000104350000000001000414000000040320008c000000990000c13d00000000030000310000000002000019000000ab0000013d0000004103000041000000410490009c00000000090380190000006004900210000000410580009c00000000080380190000004005800210000000000545019f000000410410009c0000000001038019000000c001100210000000000151019f00fd00f80000040f000000010220015f00020000000103550000006001100270000000410010019d000000410310019700000004090000290000006001000039000000000403004b000000bb0000c13d0000000102200190000000f00000613d00000000010104330000004102000041000000410310009c0000000001028019000000410390009c000000000902801900000040029002100000006001100210000000000121019f000000ff000104300000004e0130009c000000ea0000813d0000001f01300039000000200400008a000000000141016f0000003f01100039000000000441016f000000400100043d0000000004410019000000000514004b00000000050000190000000105004039000000460640009c000000ea0000213d0000000105500190000000ea0000c13d000000400040043f0000001f0430018f000000000931043600000002050003670000000503300272000000da0000613d000000000600001900000005076002100000000008790019000000000775034f000000000707043b00000000007804350000000106600039000000000736004b000000d20000413d000000000604004b000000af0000613d0000000503300210000000000535034f00000000033900190000000304400210000000000603043300000000064601cf000000000646022f000000000505043b0000010004400089000000000545022f00000000044501cf000000000464019f0000000000430435000000af0000013d0000004f0100004100000000001004350000004101000039000000040010043f0000005001000041000000ff000104300000000001000019000000fe0001042e000000000001042f000000f6002104230000000102000039000000000001042d0000000002000019000000000001042d000000fb002104250000000102000039000000000001042d0000000002000019000000000001042d000000fd00000432000000fe0001042e000000ff00010430000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000ffffffff00000000000000000000000000000000000000000000000000000000c987336c00000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff000000000000000000000000000000000000000000000000ffffffffffffffff800000000000000000000000000000000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000043616e206f6e6c792062652063616c6c656420627920464f5243455f4445504c4f5945520000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000840000008000000000000000001806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b83020000020000000000000000000000000000002400000000000000000000000000000000000000000000000000000000000000000000000100000000000000004e487b7100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000000000000000000000044656c65676174656520697320616e20454f410000000000000000000000000000000000000000000000000000000000000000640000000000000000000000000000000000000000000000000000000000000000000000000000000000000000f880b7724c567d03c5657e7444e94f904c63a516ff873019c71825fc76343a7a", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/Compressor.json b/.test-node-subtree/src/deps/contracts/Compressor.json new file mode 100644 index 00000000..6a30eccc --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/Compressor.json @@ -0,0 +1,70 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "Compressor", + "sourceName": "cache-zk/solpp-generated-contracts/Compressor.sol", + "abi": [ + { + "inputs": [ + { + "internalType": "bytes", + "name": "_bytecode", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "_rawCompressedData", + "type": "bytes" + } + ], + "name": "publishCompressedBytecode", + "outputs": [ + { + "internalType": "bytes32", + "name": "bytecodeHash", + "type": "bytes32" + } + ], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_numberOfStateDiffs", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "_enumerationIndexSize", + "type": "uint256" + }, + { + "internalType": "bytes", + "name": "_stateDiffs", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "_compressedStateDiffs", + "type": "bytes" + } + ], + "name": "verifyCompressedStateDiffs", + "outputs": [ + { + "internalType": "bytes32", + "name": "stateDiffHash", + "type": "bytes32" + } + ], + "stateMutability": "payable", + "type": "function" + } + ], + "bytecode": "0x0002000000000002000c0000000000020001000000010355000000000301001900000060043002700000012f0040019d0000008003000039000000400030043f000200000004001d0000012f034001970000000102200190000001fd0000c13d000000040230008c000002590000413d000000000201043b000000e002200270000001310420009c0000018b0000c13d000000040230008a000000800220008c000002590000413d0000000402100370000000000802043b0000004402100370000000000402043b0000002402100370000000000e02043b000700000004001d000001330240009c000002590000213d000000070200002900000023022000390000013404000041000000000532004b000000000500001900000000050480190000013402200197000000000602004b0000000004008019000001340220009c000000000405c019000000000204004b000002590000c13d00000007020000290000000402200039000000000221034f000000000602043b000001330260009c000002590000213d00000007020000290000002405200039000100000056001d000000010230006c000002590000413d0000006402100370000000000202043b000a00000002001d000001330220009c000002590000213d0000000a0200002900000023022000390000013404000041000000000732004b000000000700001900000000070480190000013402200197000000000902004b0000000004008019000001340220009c000000000407c019000000000204004b000002590000c13d0000000a020000290000000402200039000000000221034f000000000202043b000c00000002001d000001330220009c000002590000213d0000000a020000290000002404200039000b00000004001d0000000c02400029000000000232004b000002590000213d0000000002000411000080080220008c000002050000c13d0000000902e0008c0000020d0000813d000000020b00003900000110298000c9000001110a00008a000900000000001d000000000300001900060000000e001d000000000208004b000000650000613d00000000428900d9000001100220008c000002fd0000c13d000000000293004b000000d30000813d0000000002a3004b000002fd0000213d0000011004300039000000000264004b000002590000213d00000000025300190000003c02200039000000000321034f000000000303043b00000133033001980000000003040019000000600000c13d000000010d00008a0000000903d0006b000002fd0000613d0000000b03b00029000000000331034f000000080720008a000000000271034f000000000303043b000000000202043b000000000232004b000002350000c13d000000210200008a00000000022b004b000002fd0000213d0000002002b000390000000c0320006c000001610000813d0000000b02200029000000000221034f000000000f02043b0000015702f00198000000fb03f0027000000020030060390000002102b00039000000000b230019000000000c3b004b000000000c000019000000010c004039000000010cc00190000002fd0000c13d0000000c0cb0006c000002590000213d0000000b02200029000000480c700039000000000cc1034f0000002807700039000000000e71034f000000000221034f000000000702043b00000000020e043b000500000002001d000000060e00002900000000020c043b000800000002001d0000001f0230008c0000000302300210000000ac0000213d000001000c200089000000000ccd01cf000000000d200049000001000e00008a000000000ded004b000000060e000029000000000c0040190000000007c7016f000000000c03004b000000d10000613d000001000c20008c000002fd0000213d00000000c33200d9000000080330008c000002fd0000c13d0000010003200089000000000337022f000000000202004b00000000030060190000000902000029000900010020003d000000f802f00270000000070220018f000000010720008c000000c40000213d000000000702004b000000c80000613d000000010220008c0000016f0000c13d0000000502300029000000080220006c0000000003040019000000600000613d000001810000013d000000020720008c000000cc0000613d000000030220008c0000016f0000c13d000000080230006c0000000003040019000000600000613d000001650000013d0000000502300069000000080220006c0000000003040019000000600000613d000001770000013d0000000003000019000000b50000013d0000000a020000290000000602200039000000000221034f000000000202043b0000ffff0220018f000000090220006b000002170000c13d0000000303e002100000010002300089000000010400008a000800000002001d000400000004001d00000000042401cf00000000023000490003010000000092000000030220006c0000000004004019000500000004001d000a00000003001d000001000230008c000002210000213d0000000007000019000000ed0000013d000000000237004b0000000007040019000001650000c13d000000000208004b000000f20000613d00000000328900d9000001100220008c000002fd0000c13d000000000297004b0000025b0000813d0000000002a7004b000002fd0000213d0000011004700039000000000264004b000002590000213d00000000025700190000003c03200039000000000231034f000000000202043b000001330f2001980000000007040019000000ed0000613d000000000deb00190000000002bd004b000000000200001900000001020040390000000102200190000002fd0000c13d0000000c02d0006c000002590000213d0000000b02b00029000000000221034f000000000202043b0000001f07e0008c000001100000213d000000050220017f00000000070e004b000002f50000613d0000000ab7e000f9000000080770008c000002fd0000c13d0000000a0700006b000002f50000613d000000080220025000000000022f004b000002f50000c13d0000000c02d0006c000001610000813d0000000b02d00029000000000221034f000000000f02043b0000015702f00198000000fb07f0027000000020070060390000000102d00039000000000b270019000000000cdb004b000002fd0000a13d0000000c0cb0006c000002590000213d0000000b02200029000000400c300039000000000cc1034f0000002003300039000000000331034f000000000221034f000000000202043b000000000303043b000900000003001d00000000030c043b0000001f0c70008c000000030c700210000001400000213d000001000ec00089000000040ee001ef000000000dc00049000700000003001d00000000030b0019000000030dd0006c000000000b0300190000000703000029000000000e0040190000000002e2016f000000060e000029000000000d07004b0000015f0000613d000001000dc0008c000002fd0000213d00000000d77c00d9000000080770008c000002fd0000c13d0000010007c00089000000000772022f00000000020c004b0000000007006019000000f802f00270000000070220018f000000010c20008c000001560000213d000000000c02004b000000ea0000613d000000010220008c0000016f0000c13d0000000902700029000000000232004b0000000007040019000000ed0000613d000001810000013d000000030c20008c000000ea0000613d000000020220008c0000016f0000c13d0000000902700069000000000232004b0000000007040019000000ed0000613d000001770000013d0000000007000019000001490000013d0000015c0100004100000000001004350000003201000039000003000000013d0000013501000041000000800010043f0000002001000039000000840010043f0000003a01000039000000a40010043f0000016401000041000000c40010043f0000016501000041000002730000013d0000013501000041000000800010043f0000002001000039000000840010043f0000001501000039000000a40010043f0000016601000041000002670000013d0000013501000041000000800010043f0000002001000039000000840010043f0000002f01000039000000a40010043f0000016001000041000000c40010043f0000016101000041000002730000013d0000013501000041000000800010043f0000002001000039000000840010043f0000002e01000039000000a40010043f0000016201000041000000c40010043f0000016301000041000002730000013d000001320220009c000002590000c13d000000040230008a000000400220008c000002590000413d0000000402100370000000000502043b000001330250009c000002590000213d00000023025000390000013404000041000000000632004b000000000600001900000000060480190000013402200197000000000702004b0000000004008019000001340220009c000000000406c019000000000204004b000002590000c13d0000000402500039000000000221034f000000000202043b000b00000002001d000001330220009c000002590000213d00000024045000390000000b02400029000000000623004b000002590000413d0000002406100370000000000606043b000001330760009c000002590000213d00000023076000390000013408000041000000000937004b000000000900001900000000090880190000013407700197000000000a07004b0000000008008019000001340770009c000000000809c019000000000708004b000002590000c13d0000000407600039000000000871034f000000000808043b000a00000008001d000001330880009c000002590000213d0000002409600039000900000009001d0000000a08900029000000000338004b000002590000213d0000000003000411000080010330008c000003030000c13d0000000203700039000000000331034f000000000303043b0000000303300210000001380330019700000002083001bf0000000a0780006b000002590000413d0000000a0780006900000002097002100000000b0990006c0000030b0000c13d0000000a0980006b000001ef0000613d000000060960003900000000089800190000000e066000390000000c055000390000000009000019000000000a980019000000000aa1034f000000000a0a043b000000030aa00210000001380aa00197000000000b3a004b000003210000813d000000000aa60019000000020b900210000000000bb50019000000000bb1034f000000000aa1034f000000000a0a043b000000000b0b043b000000000aba013f000001330aa001980000032b0000c13d0000000209900039000000000a79004b000001db0000413d0000000b030000290000001f03300190000003190000c13d0000000b03000029000001430330009c000003350000413d0000013501000041000000800010043f0000002001000039000000840010043f0000000201000039000000a40010043f0000015301000041000002670000013d0000000001000416000000000101004b000002590000c13d0000002001000039000001000010044300000120000004430000013001000041000004b80001042e0000013501000041000000800010043f0000002001000039000000840010043f0000001401000039000000a40010043f0000015401000041000002670000013d0000013501000041000000800010043f0000002001000039000000840010043f0000002301000039000000a40010043f0000016701000041000000c40010043f0000016801000041000002730000013d0000013501000041000000800010043f0000002001000039000000840010043f0000002901000039000000a40010043f0000015501000041000000c40010043f0000015601000041000002730000013d000000000208004b0000023d0000c13d0000000702000029000000600220003900000000030000190000000608000029000000000493004b0000025b0000813d0000000004a3004b000002fd0000213d0000011004300039000000000764004b000002590000213d0000000003320019000000000331034f000000000303043b00000133033001980000000003040019000002270000613d000002510000013d0000013501000041000000800010043f0000002001000039000000840010043f0000001801000039000000a40010043f0000015f01000041000002670000013d00000000328900d9000001100220008c0000000608000029000002fd0000c13d000000070200002900000060022000390000000003000019000000000493004b0000025b0000813d0000000004a3004b000002fd0000213d0000011004300039000000000764004b000002590000213d0000000003320019000000000331034f000000000303043b00000133033001980000000003040019000002440000613d00000000018b00190000000002b1004b000000000200001900000001020040390000000102200190000002fd0000c13d0000000c0110006c000002f30000a13d0000000001000019000004b9000104300000000c02b0006c0000026a0000c13d00000000020004140000015a0320009c000002760000413d0000013501000041000000800010043f0000002001000039000000840010043f0000000801000039000000a40010043f0000015d01000041000000c40010043f0000013701000041000004b9000104300000013501000041000000800010043f0000002001000039000000840010043f0000002301000039000000a40010043f0000015801000041000000c40010043f0000015901000041000000e40010043f0000013f01000041000004b9000104300000012f03500197000000000131034f000000010400002900000002034000690000012f0330019700000000013103df000000c002200210000001440220019700000145022001c700000000012103af000080100200003904b704b20000040f000000000301001900000060033002700000012f033001970000000102200190000002cb0000613d0000003f023000390000014604200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000001330640009c0000042e0000213d00000001055001900000042e0000c13d000000400040043f00000000043204360000001f053000390000000505500272000002a20000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b0000029a0000413d000000000500004b000002a40000613d0000001f0530018f0000000503300272000002b00000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b000002a80000413d000000000605004b000002bf0000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f00000000001304350000012f03000041000000400100043d0000012f0510009c000000000301401900000040033002100000000002020433000000200220008c000002e60000c13d0000000002040433000000000021043500000151013001c7000004b80001042e0000001f0430018f0000000502300272000002d60000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000002cf0000413d000000000504004b000002e40000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000004b90001043000000044021000390000015b04000041000000000042043500000024021000390000001f0400003900000000004204350000013502000041000000000021043500000004011000390000002002000039000000000021043500000148013001c7000004b900010430000000000108004b000002fd0000c13d0000013501000041000000800010043f0000002001000039000000840010043f0000001501000039000000a40010043f0000015e01000041000002670000013d0000015c0100004100000000001004350000001101000039000000040010043f0000015001000041000004b9000104300000013501000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f0000013601000041000002670000013d0000013501000041000000800010043f0000002001000039000000840010043f0000004801000039000000a40010043f0000013901000041000000c40010043f0000013a01000041000000e40010043f0000013b01000041000001040010043f0000013c01000041000004b9000104300000013501000041000000800010043f0000002001000039000000840010043f0000000201000039000000a40010043f0000014201000041000002670000013d0000013501000041000000800010043f0000002001000039000000840010043f0000002401000039000000a40010043f0000013d01000041000000c40010043f0000013e01000041000002730000013d0000013501000041000000800010043f0000002001000039000000840010043f0000003201000039000000a40010043f0000014001000041000000c40010043f0000014101000041000002730000013d0000000b030000290000002003300190000003400000c13d0000013501000041000000800010043f0000002001000039000000840010043f0000000201000039000000a40010043f0000015201000041000002670000013d00000000030004140000012f0530009c000002600000213d0000012f04400197000000000141034f00000002022000690000012f0220019700000000012103df000000c002300210000001440220019700000145022001c700000000012103af000000020200003904b704b20000040f000000000301001900000060033002700000012f033001970000000102200190000004320000613d0000003f023000390000014604200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000001330640009c0000042e0000213d00000001055001900000042e0000c13d000000400040043f000000000532043600000001040003670000001f0630003900000005066002720000036e0000613d000000000740036800000000080000190000000509800210000000000a950019000000000997034f000000000909043b00000000009a04350000000108800039000000000968004b000003660000413d000000000600004b000003700000613d0000001f0630018f00000005033002720000037c0000613d000000000700001900000005087002100000000009850019000000000881034f000000000808043b00000000008904350000000107700039000000000837004b000003740000413d000000000706004b0000038b0000613d0000000503300210000000000131034f00000000033500190000000306600210000000000703043300000000076701cf000000000767022f000000000101043b0000010006600089000000000161022f00000000016101cf000000000171019f0000000000130435000000400600043d00000044016000390000002403600039000c00000006001d00000004066000390000000002020433000000200220008c0000044d0000c13d000000000505043300000149020000410000000c070000290000000000270435000000200200003900000000002604350000000a06000029000000000063043500000009024003600000014a035001970000000b04000029000000db044002100000014b04400197000000000434019f0000001f0360018f000b014c004001cb0000000504600272000003ae0000613d000000000500001900000005065002100000000007610019000000000662034f000000000606043b00000000006704350000000105500039000000000645004b000003a60000413d000000000503004b000003bd0000613d0000000504400210000000000242034f00000000044100190000000303300210000000000504043300000000053501cf000000000535022f000000000202043b0000010003300089000000000232022f00000000023201cf000000000252019f00000000002404350000000a02000029000000000121001900000000000104350000001f01200039000000200200008a000000000121016f0000012f020000410000000c040000290000012f0340009c00000000030200190000000003044019000000400330021000000044011000390000012f0410009c00000000010280190000006001100210000000000113019f00000000030004140000012f0430009c0000000003028019000000c002300210000000000112019f000080080200003904b704a80000040f000000000301001900000060033002700000012f03300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000003e70000613d000000000700001900000005087002100000000c09800029000000000881034f000000000808043b00000000008904350000000107700039000000000867004b000003df0000413d000000000705004b000003f60000613d0000000506600210000000000761034f0000000c066000290000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f000000000056043500000001022001900000045c0000613d0000001f01400039000000600210018f0000000c01200029000000000221004b00000000020000190000000102004039000001330410009c0000042e0000213d00000001022001900000042e0000c13d000000400010043f000000200130008c000002590000413d0000014d010000410000000000100439000080040100003900000004001004430000012f0100004100000000020004140000012f0320009c0000000002018019000000c0012002100000014e011001c7000080020200003904b704ad0000040f00000001022001900000047f0000613d000000000101043b000000000101004b000002590000613d000000400400043d0000014f01000041000000000014043500000004014000390000000b0200002900000000002104350000012f0100004100000000020004140000012f0320009c00000000020180190000012f0340009c000c00000004001d0000000001044019000a004000100218000000c0012002100000000a011001af00000150011001c7000080040200003904b704a80000040f0000000102200190000004800000613d0000000c01000029000001330110009c000004a00000a13d0000015c0100004100000000001004350000004101000039000003000000013d0000001f0430018f00000005023002720000043d0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000004360000413d000000000504004b0000044b0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000004b90001043000000135020000410000000c0400002900000000002404350000002002000039000000000026043500000019020000390000000000230435000001470200004100000000002104350000012f010000410000012f0240009c0000000004018019000000400140021000000148011001c7000004b900010430000000400200043d0000001f0430018f0000000505300272000004690000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000004610000413d000000000604004b000004780000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f00000000001504350000012f010000410000012f0420009c000000000201801900000040012002100000006002300210000000000121019f000004b900010430000000000001042f000000400200043d000000000301001900000060033002700000001f0430018f0000012f033001970000000505300272000004900000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000004880000413d000000000604004b0000049f0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000004780000013d0000000c02000029000000400020043f0000000b0100002900000000001204350000000a0100002900000151011001c7000004b80001042e000000000001042f000004ab002104210000000102000039000000000001042d0000000002000019000000000001042d000004b0002104230000000102000039000000000001042d0000000002000019000000000001042d000004b5002104230000000102000039000000000001042d0000000002000019000000000001042d000004b700000432000004b80001042e000004b9000104300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000000000000000000000000000000000000000000000000000000000006006d8b500000000000000000000000000000000000000000000000000000000f5e69a47000000000000000000000000000000000000000000000000ffffffffffffffff800000000000000000000000000000000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c792062792074686520626f6f746c6f61646572000000000000000000000000000000000000000064000000800000000000000000000000000000000000000000000000000000000000000000000000000007fff8456e636f6465642064617461206c656e6774682073686f756c6420626520342074696d65732073686f72746572207468616e20746865206f726967696e616c2062797465636f646500000000000000000000000000000000000000000000000000000000000000000000000000000000000000a4000000800000000000000000456e636f646564206368756e6b20696e646578206973206f7574206f6620626f756e6473000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000084000000800000000000000000456e636f646564206368756e6b20646f6573206e6f74206d6174636820746865206f726967696e616c2062797465636f64650000000000000000000000000000706f000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000020000000000000ffffffff000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001ffffffe07368612072657475726e656420696e76616c6964206461746100000000000000000000000000000000000000000000000000006400000000000000000000000062f84b240000000000000000000000000000000000000000000000000000000000000000fffffffffffffffffffffffffffffffffffffffffffffffffffffffffeffffff0000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000001806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b83020000020000000000000000000000000000002400000000000000000000000079c4f929000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000000000000000000000000000000000000000002000000000000000000000000070720000000000000000000000000000000000000000000000000000000000007070000000000000000000000000000000000000000000000000000000000000496e617070726f7072696174652063616c6c6572000000000000000000000000496e636f7272656374206e756d626572206f6620696e697469616c2073746f72616765206469666673000000000000000000000000000000000000000000000007000000000000000000000000000000000000000000000000000000000000004578747261206461746120696e205f636f6d7072657373656453746174654469666673000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001000000006b656363616b3235362072657475726e656420696e76616c69642064617461004e487b71000000000000000000000000000000000000000000000000000000004f766572666c6f7700000000000000000000000000000000000000000000000072773a20656e756d206b6579206d69736d61746368000000000000000000000069773a20696e697469616c206b6579206d69736d6174636800000000000000007375623a20696e697469616c206d696e757320636f6e766572746564206e6f7420657175616c20746f2066696e616c00000000000000000000000000000000006164643a20696e697469616c20706c757320636f6e766572746564206e6f7420657175616c20746f2066696e616c0000000000000000000000000000000000007472616e73666f726d206f72206e6f20636f6d7072657373696f6e3a20636f6d7072657373656420616e642066696e616c206d69736d61746368000000000000756e737570706f72746564206f7065726174696f6e0000000000000000000000656e756d65726174696f6e20696e6465782073697a6520697320746f6f206c617267650000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000063021b8677d068a1a500877c96c23b9c53b161f5e630886503e38c99c3eb75b6", + "deployedBytecode": "0x0002000000000002000c0000000000020001000000010355000000000301001900000060043002700000012f0040019d0000008003000039000000400030043f000200000004001d0000012f034001970000000102200190000001fd0000c13d000000040230008c000002590000413d000000000201043b000000e002200270000001310420009c0000018b0000c13d000000040230008a000000800220008c000002590000413d0000000402100370000000000802043b0000004402100370000000000402043b0000002402100370000000000e02043b000700000004001d000001330240009c000002590000213d000000070200002900000023022000390000013404000041000000000532004b000000000500001900000000050480190000013402200197000000000602004b0000000004008019000001340220009c000000000405c019000000000204004b000002590000c13d00000007020000290000000402200039000000000221034f000000000602043b000001330260009c000002590000213d00000007020000290000002405200039000100000056001d000000010230006c000002590000413d0000006402100370000000000202043b000a00000002001d000001330220009c000002590000213d0000000a0200002900000023022000390000013404000041000000000732004b000000000700001900000000070480190000013402200197000000000902004b0000000004008019000001340220009c000000000407c019000000000204004b000002590000c13d0000000a020000290000000402200039000000000221034f000000000202043b000c00000002001d000001330220009c000002590000213d0000000a020000290000002404200039000b00000004001d0000000c02400029000000000232004b000002590000213d0000000002000411000080080220008c000002050000c13d0000000902e0008c0000020d0000813d000000020b00003900000110298000c9000001110a00008a000900000000001d000000000300001900060000000e001d000000000208004b000000650000613d00000000428900d9000001100220008c000002fd0000c13d000000000293004b000000d30000813d0000000002a3004b000002fd0000213d0000011004300039000000000264004b000002590000213d00000000025300190000003c02200039000000000321034f000000000303043b00000133033001980000000003040019000000600000c13d000000010d00008a0000000903d0006b000002fd0000613d0000000b03b00029000000000331034f000000080720008a000000000271034f000000000303043b000000000202043b000000000232004b000002350000c13d000000210200008a00000000022b004b000002fd0000213d0000002002b000390000000c0320006c000001610000813d0000000b02200029000000000221034f000000000f02043b0000015702f00198000000fb03f0027000000020030060390000002102b00039000000000b230019000000000c3b004b000000000c000019000000010c004039000000010cc00190000002fd0000c13d0000000c0cb0006c000002590000213d0000000b02200029000000480c700039000000000cc1034f0000002807700039000000000e71034f000000000221034f000000000702043b00000000020e043b000500000002001d000000060e00002900000000020c043b000800000002001d0000001f0230008c0000000302300210000000ac0000213d000001000c200089000000000ccd01cf000000000d200049000001000e00008a000000000ded004b000000060e000029000000000c0040190000000007c7016f000000000c03004b000000d10000613d000001000c20008c000002fd0000213d00000000c33200d9000000080330008c000002fd0000c13d0000010003200089000000000337022f000000000202004b00000000030060190000000902000029000900010020003d000000f802f00270000000070220018f000000010720008c000000c40000213d000000000702004b000000c80000613d000000010220008c0000016f0000c13d0000000502300029000000080220006c0000000003040019000000600000613d000001810000013d000000020720008c000000cc0000613d000000030220008c0000016f0000c13d000000080230006c0000000003040019000000600000613d000001650000013d0000000502300069000000080220006c0000000003040019000000600000613d000001770000013d0000000003000019000000b50000013d0000000a020000290000000602200039000000000221034f000000000202043b0000ffff0220018f000000090220006b000002170000c13d0000000303e002100000010002300089000000010400008a000800000002001d000400000004001d00000000042401cf00000000023000490003010000000092000000030220006c0000000004004019000500000004001d000a00000003001d000001000230008c000002210000213d0000000007000019000000ed0000013d000000000237004b0000000007040019000001650000c13d000000000208004b000000f20000613d00000000328900d9000001100220008c000002fd0000c13d000000000297004b0000025b0000813d0000000002a7004b000002fd0000213d0000011004700039000000000264004b000002590000213d00000000025700190000003c03200039000000000231034f000000000202043b000001330f2001980000000007040019000000ed0000613d000000000deb00190000000002bd004b000000000200001900000001020040390000000102200190000002fd0000c13d0000000c02d0006c000002590000213d0000000b02b00029000000000221034f000000000202043b0000001f07e0008c000001100000213d000000050220017f00000000070e004b000002f50000613d0000000ab7e000f9000000080770008c000002fd0000c13d0000000a0700006b000002f50000613d000000080220025000000000022f004b000002f50000c13d0000000c02d0006c000001610000813d0000000b02d00029000000000221034f000000000f02043b0000015702f00198000000fb07f0027000000020070060390000000102d00039000000000b270019000000000cdb004b000002fd0000a13d0000000c0cb0006c000002590000213d0000000b02200029000000400c300039000000000cc1034f0000002003300039000000000331034f000000000221034f000000000202043b000000000303043b000900000003001d00000000030c043b0000001f0c70008c000000030c700210000001400000213d000001000ec00089000000040ee001ef000000000dc00049000700000003001d00000000030b0019000000030dd0006c000000000b0300190000000703000029000000000e0040190000000002e2016f000000060e000029000000000d07004b0000015f0000613d000001000dc0008c000002fd0000213d00000000d77c00d9000000080770008c000002fd0000c13d0000010007c00089000000000772022f00000000020c004b0000000007006019000000f802f00270000000070220018f000000010c20008c000001560000213d000000000c02004b000000ea0000613d000000010220008c0000016f0000c13d0000000902700029000000000232004b0000000007040019000000ed0000613d000001810000013d000000030c20008c000000ea0000613d000000020220008c0000016f0000c13d0000000902700069000000000232004b0000000007040019000000ed0000613d000001770000013d0000000007000019000001490000013d0000015c0100004100000000001004350000003201000039000003000000013d0000013501000041000000800010043f0000002001000039000000840010043f0000003a01000039000000a40010043f0000016401000041000000c40010043f0000016501000041000002730000013d0000013501000041000000800010043f0000002001000039000000840010043f0000001501000039000000a40010043f0000016601000041000002670000013d0000013501000041000000800010043f0000002001000039000000840010043f0000002f01000039000000a40010043f0000016001000041000000c40010043f0000016101000041000002730000013d0000013501000041000000800010043f0000002001000039000000840010043f0000002e01000039000000a40010043f0000016201000041000000c40010043f0000016301000041000002730000013d000001320220009c000002590000c13d000000040230008a000000400220008c000002590000413d0000000402100370000000000502043b000001330250009c000002590000213d00000023025000390000013404000041000000000632004b000000000600001900000000060480190000013402200197000000000702004b0000000004008019000001340220009c000000000406c019000000000204004b000002590000c13d0000000402500039000000000221034f000000000202043b000b00000002001d000001330220009c000002590000213d00000024045000390000000b02400029000000000623004b000002590000413d0000002406100370000000000606043b000001330760009c000002590000213d00000023076000390000013408000041000000000937004b000000000900001900000000090880190000013407700197000000000a07004b0000000008008019000001340770009c000000000809c019000000000708004b000002590000c13d0000000407600039000000000871034f000000000808043b000a00000008001d000001330880009c000002590000213d0000002409600039000900000009001d0000000a08900029000000000338004b000002590000213d0000000003000411000080010330008c000003030000c13d0000000203700039000000000331034f000000000303043b0000000303300210000001380330019700000002083001bf0000000a0780006b000002590000413d0000000a0780006900000002097002100000000b0990006c0000030b0000c13d0000000a0980006b000001ef0000613d000000060960003900000000089800190000000e066000390000000c055000390000000009000019000000000a980019000000000aa1034f000000000a0a043b000000030aa00210000001380aa00197000000000b3a004b000003210000813d000000000aa60019000000020b900210000000000bb50019000000000bb1034f000000000aa1034f000000000a0a043b000000000b0b043b000000000aba013f000001330aa001980000032b0000c13d0000000209900039000000000a79004b000001db0000413d0000000b030000290000001f03300190000003190000c13d0000000b03000029000001430330009c000003350000413d0000013501000041000000800010043f0000002001000039000000840010043f0000000201000039000000a40010043f0000015301000041000002670000013d0000000001000416000000000101004b000002590000c13d0000002001000039000001000010044300000120000004430000013001000041000004b80001042e0000013501000041000000800010043f0000002001000039000000840010043f0000001401000039000000a40010043f0000015401000041000002670000013d0000013501000041000000800010043f0000002001000039000000840010043f0000002301000039000000a40010043f0000016701000041000000c40010043f0000016801000041000002730000013d0000013501000041000000800010043f0000002001000039000000840010043f0000002901000039000000a40010043f0000015501000041000000c40010043f0000015601000041000002730000013d000000000208004b0000023d0000c13d0000000702000029000000600220003900000000030000190000000608000029000000000493004b0000025b0000813d0000000004a3004b000002fd0000213d0000011004300039000000000764004b000002590000213d0000000003320019000000000331034f000000000303043b00000133033001980000000003040019000002270000613d000002510000013d0000013501000041000000800010043f0000002001000039000000840010043f0000001801000039000000a40010043f0000015f01000041000002670000013d00000000328900d9000001100220008c0000000608000029000002fd0000c13d000000070200002900000060022000390000000003000019000000000493004b0000025b0000813d0000000004a3004b000002fd0000213d0000011004300039000000000764004b000002590000213d0000000003320019000000000331034f000000000303043b00000133033001980000000003040019000002440000613d00000000018b00190000000002b1004b000000000200001900000001020040390000000102200190000002fd0000c13d0000000c0110006c000002f30000a13d0000000001000019000004b9000104300000000c02b0006c0000026a0000c13d00000000020004140000015a0320009c000002760000413d0000013501000041000000800010043f0000002001000039000000840010043f0000000801000039000000a40010043f0000015d01000041000000c40010043f0000013701000041000004b9000104300000013501000041000000800010043f0000002001000039000000840010043f0000002301000039000000a40010043f0000015801000041000000c40010043f0000015901000041000000e40010043f0000013f01000041000004b9000104300000012f03500197000000000131034f000000010400002900000002034000690000012f0330019700000000013103df000000c002200210000001440220019700000145022001c700000000012103af000080100200003904b704b20000040f000000000301001900000060033002700000012f033001970000000102200190000002cb0000613d0000003f023000390000014604200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000001330640009c0000042e0000213d00000001055001900000042e0000c13d000000400040043f00000000043204360000001f053000390000000505500272000002a20000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b0000029a0000413d000000000500004b000002a40000613d0000001f0530018f0000000503300272000002b00000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b000002a80000413d000000000605004b000002bf0000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f00000000001304350000012f03000041000000400100043d0000012f0510009c000000000301401900000040033002100000000002020433000000200220008c000002e60000c13d0000000002040433000000000021043500000151013001c7000004b80001042e0000001f0430018f0000000502300272000002d60000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000002cf0000413d000000000504004b000002e40000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000004b90001043000000044021000390000015b04000041000000000042043500000024021000390000001f0400003900000000004204350000013502000041000000000021043500000004011000390000002002000039000000000021043500000148013001c7000004b900010430000000000108004b000002fd0000c13d0000013501000041000000800010043f0000002001000039000000840010043f0000001501000039000000a40010043f0000015e01000041000002670000013d0000015c0100004100000000001004350000001101000039000000040010043f0000015001000041000004b9000104300000013501000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f0000013601000041000002670000013d0000013501000041000000800010043f0000002001000039000000840010043f0000004801000039000000a40010043f0000013901000041000000c40010043f0000013a01000041000000e40010043f0000013b01000041000001040010043f0000013c01000041000004b9000104300000013501000041000000800010043f0000002001000039000000840010043f0000000201000039000000a40010043f0000014201000041000002670000013d0000013501000041000000800010043f0000002001000039000000840010043f0000002401000039000000a40010043f0000013d01000041000000c40010043f0000013e01000041000002730000013d0000013501000041000000800010043f0000002001000039000000840010043f0000003201000039000000a40010043f0000014001000041000000c40010043f0000014101000041000002730000013d0000000b030000290000002003300190000003400000c13d0000013501000041000000800010043f0000002001000039000000840010043f0000000201000039000000a40010043f0000015201000041000002670000013d00000000030004140000012f0530009c000002600000213d0000012f04400197000000000141034f00000002022000690000012f0220019700000000012103df000000c002300210000001440220019700000145022001c700000000012103af000000020200003904b704b20000040f000000000301001900000060033002700000012f033001970000000102200190000004320000613d0000003f023000390000014604200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000001330640009c0000042e0000213d00000001055001900000042e0000c13d000000400040043f000000000532043600000001040003670000001f0630003900000005066002720000036e0000613d000000000740036800000000080000190000000509800210000000000a950019000000000997034f000000000909043b00000000009a04350000000108800039000000000968004b000003660000413d000000000600004b000003700000613d0000001f0630018f00000005033002720000037c0000613d000000000700001900000005087002100000000009850019000000000881034f000000000808043b00000000008904350000000107700039000000000837004b000003740000413d000000000706004b0000038b0000613d0000000503300210000000000131034f00000000033500190000000306600210000000000703043300000000076701cf000000000767022f000000000101043b0000010006600089000000000161022f00000000016101cf000000000171019f0000000000130435000000400600043d00000044016000390000002403600039000c00000006001d00000004066000390000000002020433000000200220008c0000044d0000c13d000000000505043300000149020000410000000c070000290000000000270435000000200200003900000000002604350000000a06000029000000000063043500000009024003600000014a035001970000000b04000029000000db044002100000014b04400197000000000434019f0000001f0360018f000b014c004001cb0000000504600272000003ae0000613d000000000500001900000005065002100000000007610019000000000662034f000000000606043b00000000006704350000000105500039000000000645004b000003a60000413d000000000503004b000003bd0000613d0000000504400210000000000242034f00000000044100190000000303300210000000000504043300000000053501cf000000000535022f000000000202043b0000010003300089000000000232022f00000000023201cf000000000252019f00000000002404350000000a02000029000000000121001900000000000104350000001f01200039000000200200008a000000000121016f0000012f020000410000000c040000290000012f0340009c00000000030200190000000003044019000000400330021000000044011000390000012f0410009c00000000010280190000006001100210000000000113019f00000000030004140000012f0430009c0000000003028019000000c002300210000000000112019f000080080200003904b704a80000040f000000000301001900000060033002700000012f03300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000003e70000613d000000000700001900000005087002100000000c09800029000000000881034f000000000808043b00000000008904350000000107700039000000000867004b000003df0000413d000000000705004b000003f60000613d0000000506600210000000000761034f0000000c066000290000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f000000000056043500000001022001900000045c0000613d0000001f01400039000000600210018f0000000c01200029000000000221004b00000000020000190000000102004039000001330410009c0000042e0000213d00000001022001900000042e0000c13d000000400010043f000000200130008c000002590000413d0000014d010000410000000000100439000080040100003900000004001004430000012f0100004100000000020004140000012f0320009c0000000002018019000000c0012002100000014e011001c7000080020200003904b704ad0000040f00000001022001900000047f0000613d000000000101043b000000000101004b000002590000613d000000400400043d0000014f01000041000000000014043500000004014000390000000b0200002900000000002104350000012f0100004100000000020004140000012f0320009c00000000020180190000012f0340009c000c00000004001d0000000001044019000a004000100218000000c0012002100000000a011001af00000150011001c7000080040200003904b704a80000040f0000000102200190000004800000613d0000000c01000029000001330110009c000004a00000a13d0000015c0100004100000000001004350000004101000039000003000000013d0000001f0430018f00000005023002720000043d0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000004360000413d000000000504004b0000044b0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000004b90001043000000135020000410000000c0400002900000000002404350000002002000039000000000026043500000019020000390000000000230435000001470200004100000000002104350000012f010000410000012f0240009c0000000004018019000000400140021000000148011001c7000004b900010430000000400200043d0000001f0430018f0000000505300272000004690000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000004610000413d000000000604004b000004780000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f00000000001504350000012f010000410000012f0420009c000000000201801900000040012002100000006002300210000000000121019f000004b900010430000000000001042f000000400200043d000000000301001900000060033002700000001f0430018f0000012f033001970000000505300272000004900000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000004880000413d000000000604004b0000049f0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000004780000013d0000000c02000029000000400020043f0000000b0100002900000000001204350000000a0100002900000151011001c7000004b80001042e000000000001042f000004ab002104210000000102000039000000000001042d0000000002000019000000000001042d000004b0002104230000000102000039000000000001042d0000000002000019000000000001042d000004b5002104230000000102000039000000000001042d0000000002000019000000000001042d000004b700000432000004b80001042e000004b9000104300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000000000000000000000000000000000000000000000000000000000006006d8b500000000000000000000000000000000000000000000000000000000f5e69a47000000000000000000000000000000000000000000000000ffffffffffffffff800000000000000000000000000000000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c792062792074686520626f6f746c6f61646572000000000000000000000000000000000000000064000000800000000000000000000000000000000000000000000000000000000000000000000000000007fff8456e636f6465642064617461206c656e6774682073686f756c6420626520342074696d65732073686f72746572207468616e20746865206f726967696e616c2062797465636f646500000000000000000000000000000000000000000000000000000000000000000000000000000000000000a4000000800000000000000000456e636f646564206368756e6b20696e646578206973206f7574206f6620626f756e6473000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000084000000800000000000000000456e636f646564206368756e6b20646f6573206e6f74206d6174636820746865206f726967696e616c2062797465636f64650000000000000000000000000000706f000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000020000000000000ffffffff000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001ffffffe07368612072657475726e656420696e76616c6964206461746100000000000000000000000000000000000000000000000000006400000000000000000000000062f84b240000000000000000000000000000000000000000000000000000000000000000fffffffffffffffffffffffffffffffffffffffffffffffffffffffffeffffff0000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000001806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b83020000020000000000000000000000000000002400000000000000000000000079c4f929000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000000000000000000000000000000000000000002000000000000000000000000070720000000000000000000000000000000000000000000000000000000000007070000000000000000000000000000000000000000000000000000000000000496e617070726f7072696174652063616c6c6572000000000000000000000000496e636f7272656374206e756d626572206f6620696e697469616c2073746f72616765206469666673000000000000000000000000000000000000000000000007000000000000000000000000000000000000000000000000000000000000004578747261206461746120696e205f636f6d7072657373656453746174654469666673000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001000000006b656363616b3235362072657475726e656420696e76616c69642064617461004e487b71000000000000000000000000000000000000000000000000000000004f766572666c6f7700000000000000000000000000000000000000000000000072773a20656e756d206b6579206d69736d61746368000000000000000000000069773a20696e697469616c206b6579206d69736d6174636800000000000000007375623a20696e697469616c206d696e757320636f6e766572746564206e6f7420657175616c20746f2066696e616c00000000000000000000000000000000006164643a20696e697469616c20706c757320636f6e766572746564206e6f7420657175616c20746f2066696e616c0000000000000000000000000000000000007472616e73666f726d206f72206e6f20636f6d7072657373696f6e3a20636f6d7072657373656420616e642066696e616c206d69736d61746368000000000000756e737570706f72746564206f7065726174696f6e0000000000000000000000656e756d65726174696f6e20696e6465782073697a6520697320746f6f206c617267650000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000063021b8677d068a1a500877c96c23b9c53b161f5e630886503e38c99c3eb75b6", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/ContractDeployer.json b/.test-node-subtree/src/deps/contracts/ContractDeployer.json new file mode 100644 index 00000000..af1a8301 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/ContractDeployer.json @@ -0,0 +1,433 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "ContractDeployer", + "sourceName": "cache-zk/solpp-generated-contracts/ContractDeployer.sol", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "accountAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "enum IContractDeployer.AccountNonceOrdering", + "name": "nonceOrdering", + "type": "uint8" + } + ], + "name": "AccountNonceOrderingUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "accountAddress", + "type": "address" + }, + { + "indexed": false, + "internalType": "enum IContractDeployer.AccountAbstractionVersion", + "name": "aaVersion", + "type": "uint8" + } + ], + "name": "AccountVersionUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "deployerAddress", + "type": "address" + }, + { + "indexed": true, + "internalType": "bytes32", + "name": "bytecodeHash", + "type": "bytes32" + }, + { + "indexed": true, + "internalType": "address", + "name": "contractAddress", + "type": "address" + } + ], + "name": "ContractDeployed", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "_salt", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "_bytecodeHash", + "type": "bytes32" + }, + { + "internalType": "bytes", + "name": "_input", + "type": "bytes" + } + ], + "name": "create", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "_salt", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "_bytecodeHash", + "type": "bytes32" + }, + { + "internalType": "bytes", + "name": "_input", + "type": "bytes" + } + ], + "name": "create2", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "_salt", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "_bytecodeHash", + "type": "bytes32" + }, + { + "internalType": "bytes", + "name": "_input", + "type": "bytes" + }, + { + "internalType": "enum IContractDeployer.AccountAbstractionVersion", + "name": "_aaVersion", + "type": "uint8" + } + ], + "name": "create2Account", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "_bytecodeHash", + "type": "bytes32" + }, + { + "internalType": "bytes", + "name": "_input", + "type": "bytes" + }, + { + "internalType": "enum IContractDeployer.AccountAbstractionVersion", + "name": "_aaVersion", + "type": "uint8" + } + ], + "name": "createAccount", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + } + ], + "name": "extendedAccountVersion", + "outputs": [ + { + "internalType": "enum IContractDeployer.AccountAbstractionVersion", + "name": "", + "type": "uint8" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "_keccak256BytecodeHash", + "type": "bytes32" + } + ], + "name": "forceDeployKeccak256", + "outputs": [], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "components": [ + { + "internalType": "bytes32", + "name": "bytecodeHash", + "type": "bytes32" + }, + { + "internalType": "address", + "name": "newAddress", + "type": "address" + }, + { + "internalType": "bool", + "name": "callConstructor", + "type": "bool" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "bytes", + "name": "input", + "type": "bytes" + } + ], + "internalType": "struct ContractDeployer.ForceDeployment", + "name": "_deployment", + "type": "tuple" + }, + { + "internalType": "address", + "name": "_sender", + "type": "address" + } + ], + "name": "forceDeployOnAddress", + "outputs": [], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "components": [ + { + "internalType": "bytes32", + "name": "bytecodeHash", + "type": "bytes32" + }, + { + "internalType": "address", + "name": "newAddress", + "type": "address" + }, + { + "internalType": "bool", + "name": "callConstructor", + "type": "bool" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "bytes", + "name": "input", + "type": "bytes" + } + ], + "internalType": "struct ContractDeployer.ForceDeployment[]", + "name": "_deployments", + "type": "tuple[]" + } + ], + "name": "forceDeployOnAddresses", + "outputs": [], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + } + ], + "name": "getAccountInfo", + "outputs": [ + { + "components": [ + { + "internalType": "enum IContractDeployer.AccountAbstractionVersion", + "name": "supportedAAVersion", + "type": "uint8" + }, + { + "internalType": "enum IContractDeployer.AccountNonceOrdering", + "name": "nonceOrdering", + "type": "uint8" + } + ], + "internalType": "struct IContractDeployer.AccountInfo", + "name": "info", + "type": "tuple" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_sender", + "type": "address" + }, + { + "internalType": "uint256", + "name": "_senderNonce", + "type": "uint256" + } + ], + "name": "getNewAddressCreate", + "outputs": [ + { + "internalType": "address", + "name": "newAddress", + "type": "address" + } + ], + "stateMutability": "pure", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_sender", + "type": "address" + }, + { + "internalType": "bytes32", + "name": "_bytecodeHash", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "_salt", + "type": "bytes32" + }, + { + "internalType": "bytes", + "name": "_input", + "type": "bytes" + } + ], + "name": "getNewAddressCreate2", + "outputs": [ + { + "internalType": "address", + "name": "newAddress", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "enum IContractDeployer.AccountAbstractionVersion", + "name": "_version", + "type": "uint8" + } + ], + "name": "updateAccountVersion", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "enum IContractDeployer.AccountNonceOrdering", + "name": "_nonceOrdering", + "type": "uint8" + } + ], + "name": "updateNonceOrdering", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "bytecode": "0x0002000000000002000b0000000000020000000003020019000100000001035500000000020100190000006002200270000004f50020019d0000008004000039000000400040043f000004f5022001970000000104300190000000860000c13d000000040420008c000007660000413d000000000401043b000000e004400270000004f70540009c0000008e0000a13d000004f80540009c000000cf0000a13d000004f90540009c0000000005000410000b00000005001d000001470000213d000004fc0540009c000001b40000613d000004fd0440009c000007660000c13d0000000004000416000000000404004b000007660000c13d000000040220008a000000200220008c000007660000413d0000000401100370000000000101043b000b00000001001d000000010110008c000007660000213d000000000200041100000002013001900000002c0000c13d0000ffff0120008c000003aa0000213d000a00000002001d0000000000200435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d000000400400043d000005210240009c000003d30000213d000000000101043b0000004002400039000000400020043f000000000101041a000000ff0210018f000000010320008c000004190000213d00000000032404360000000801100270000000ff0110018f000000010210008c000004190000213d000900000004001d00000000001304350000000b02000029000000010220008c0000065e0000c13d000000000101004b0000065e0000c13d0000000101000039000b00000003001d000800000001001d00000000001304350000000a010000290000050a011001970000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d00000009020000290000000002020433000000010320008c0000000b05000029000004190000213d000000000101043b000000000301041a000001000400008a000000000343016f000000000223019f000000000021041b0000000003050433000000010430008c000004190000213d0000051104000041000000000242016f00000008033002100000ff000330018f000000000223019f000000000021041b000000400100043d00000008020000290000000000210435000004f5020000410000000003000414000004f50430009c0000000003028019000004f50410009c00000000010280190000004001100210000000c002300210000000000112019f00000532011001c70000800d0200003900000002030000390000053304000041000000c90000013d0000000001000416000000000101004b000007660000c13d000000200100003900000100001004430000012000000443000004f601000041000013ce0001042e000005010540009c000001230000213d000005050540009c000002f00000613d000005060540009c0000037d0000613d000005070440009c000007660000c13d0000000004000416000000000404004b000007660000c13d000000040220008a000000200220008c000007660000413d0000000401100370000000000101043b000b00000001001d000000010110008c000007660000213d00000000020004110000000201300190000000a60000c13d0000ffff0120008c000003aa0000213d000a00000002001d0000000000200435000000200000043f000004f5030000410000000001000414000004f50210009c0000000001038019000000c00110021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d000000000101043b000000000201041a000001000300008a000000000232016f0000000b03000029000000000232019f000000000021041b000000400100043d00000000003104350000000002000414000004f50320009c000004f5040000410000000002048019000004f50310009c00000000010480190000004001100210000000c002200210000000000112019f00000532011001c70000800d02000039000000020300003900000544040000410000000a0500002913cd13b80000040f0000000101200190000007660000613d0000000001000019000013ce0001042e000004fe0540009c000002510000613d000004ff0340009c000002bc0000613d000005000340009c000007660000c13d000000040220008a000000200220008c000007660000413d0000000401100370000000000201043b0000000001000411000080070110008c000003d70000c13d0000050e01000041000000800010043f000b00000002001d000000840020043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080040200003913cd13bd0000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000000fb0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000000f30000413d000000000705004b0000010a0000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000003e10000613d0000001f01400039000000600210018f00000080012001bf000000400010043f000000200330008c000007660000413d000000800300043d000000000303004b000004770000c13d0000050b03000041000000000031043500000084032001bf00000020040000390000000000430435000000c4032000390000052a040000410000000000430435000000a4022000390000001a030000390000000000320435000000400110021000000515011001c7000013cf00010430000005020540009c000003070000613d000005030340009c000003b60000613d000005040340009c000007660000c13d0000000003000416000000000303004b000007660000c13d000000040320008a000000800330008c000007660000413d0000000403100370000000000303043b000b00000003001d0000050a0330009c000007660000213d0000006401100370000000000101043b000005080310009c000007660000213d000000040110003913cd0a300000040f00000001040003670000004403400370000000000303043b0000002404400370000000000404043b000000000501001900000000060200190000000b0100002900000000020400190000000004050019000000000506001913cd0a4a0000040f000002fe0000013d000004fa0540009c000001e00000613d000004fb0340009c000007660000c13d000000040320008a000000400330008c000007660000413d0000000403100370000000000303043b000a00000003001d000005080330009c000007660000213d0000000a0420006a0000050902000041000000a40340008c00000000030000190000000003024019000900000004001d0000050904400197000000000504004b000000000200a019000005090440009c000000000203c019000000000202004b000007660000c13d0000002402100370000000000202043b000800000002001d0000050a0220009c000007660000213d00000000020004110000000b0220006c0000042b0000c13d0000000a02000029000700040020003d0000000701100360000000000201043b0000050e01000041000000800010043f000600000002001d000000840020043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080040200003913cd13bd0000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000018a0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000001820000413d000000000705004b000001990000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000005ae0000613d0000001f01400039000000600110018f00000080021001bf000500000002001d000000400020043f000000200230008c000007660000413d000000800200043d000000000202004b000006760000c13d0000050b020000410000000504000029000000000024043500000084021001bf00000020030000390000000000320435000000c4021000390000052a030000410000000000320435000000a4011000390000001a020000390000000000210435000000400140021000000515011001c7000013cf00010430000000040320008a000000200330008c000007660000413d0000000403100370000000000303043b000500000003001d000005080330009c000007660000213d000000050300002900000023033000390000050904000041000000000523004b000000000500001900000000050480190000050903300197000000000603004b0000000004008019000005090330009c000000000405c019000000000304004b000007660000c13d00000005030000290000000403300039000000000331034f000000000d03043b0000050803d0009c000007660000213d0000000503000029000000240e3000390000000503d002100000000003e30019000000000323004b000007660000213d000000090400008a0000000003000411000000000443016f000080070440008c0000041f0000c13d00000000040d004b000004b40000c13d0000000001000416000000000101004b000000cd0000613d000006160000013d000000040420008a000000800440008c000007660000413d0000002404100370000000000404043b000b00000004001d0000004404100370000000000404043b000005080540009c000007660000213d00000023054000390000050906000041000000000725004b000000000700001900000000070680190000050905500197000000000805004b0000000006008019000005090550009c000000000607c019000000000506004b000007660000c13d0000000405400039000000000551034f000000000505043b000a00000005001d000005080550009c000007660000213d0000002405400039000900000005001d0000000a04500029000000000224004b000007660000213d0000006401100370000000000101043b000800000001001d000000010110008c000007660000213d000000020130019000000001011002700000020d0000c13d00000000010004110000052b0110009c00000000010000190000000101004039000000000101004b000003aa0000613d0000052c01000041000000800010043f0000000001000411000700000001001d000000840010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080030200003913cd13b80000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000022e0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000002260000413d000000000705004b0000023d0000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000006240000613d0000001f01400039000000600110018f00000080011001bf000000400010043f000000200130008c000007660000413d000000800200043d000000070100002913cd0b110000040f0000000002010019000700000002001d0000000b01000029000000080300002900000009040000290000000a0500002913cd0f7a0000040f0000000701000029000002fe0000013d000000040420008a000000600440008c000007660000413d0000002404100370000000000404043b000b00000004001d0000004404100370000000000404043b000005080540009c000007660000213d00000023054000390000050906000041000000000725004b000000000700001900000000070680190000050905500197000000000805004b0000000006008019000005090550009c000000000607c019000000000506004b000007660000c13d0000000405400039000000000151034f000000000101043b000a00000001001d000005080110009c000007660000213d0000002404400039000900000004001d0000000a01400029000000000121004b000007660000213d00000002013001900000000101100270000002790000c13d00000000010004110000052b0110009c00000000010000190000000101004039000000000101004b000003aa0000613d0000052c01000041000000800010043f0000000001000411000800000001001d000000840010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080030200003913cd13b80000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000029a0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000002920000413d000000000705004b000002a90000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000005cb0000613d0000001f01400039000000600110018f00000080011001bf000000400010043f000000200130008c000007660000413d000000800200043d000000080100002913cd0b110000040f0000000002010019000800000002001d0000000b0100002900000009030000290000000a0400002913cd0b3d0000040f0000000801000029000002fe0000013d0000000003000416000000000303004b000007660000c13d000000040220008a000000200220008c000007660000413d0000000401100370000000000101043b000b00000001001d0000050a0110009c000007660000213d0000000b010000290000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d000000400200043d000005210320009c000003d30000213d000000000101043b0000004003200039000000400030043f000000000101041a000000ff0310018f000000010430008c000004190000213d00000000033204360000000801100270000000ff0110018f000000010410008c000004190000213d00000000001304350000000002020433000000010120008c000004190000213d0000000101000039000000000202004b000002ff0000c13d0000000b0100002900000540011001980000000001000019000007210000c13d000000010110018f000002ff0000013d0000000003000416000000000303004b000007660000c13d000000040220008a000000400220008c000007660000413d0000000402100370000000000302043b0000050a0230009c000007660000213d0000002401100370000000000201043b000000000103001913cd0b110000040f0000050a01100197000000400200043d0000000000120435000004f501000041000004f50320009c000000000201801900000040012002100000052d011001c7000013ce0001042e000000040420008a000000800440008c000007660000413d0000002404100370000000000404043b000b00000004001d0000000404100370000000000404043b000a00000004001d0000004404100370000000000404043b000005080540009c000007660000213d00000023054000390000050906000041000000000725004b000000000700001900000000070680190000050905500197000000000805004b0000000006008019000005090550009c000000000607c019000000000506004b000007660000c13d0000000405400039000000000551034f000000000505043b000900000005001d000005080550009c000007660000213d0000002405400039000800000005001d0000000904500029000000000224004b000007660000213d0000006401100370000000000101043b000700000001001d000000010110008c000007660000213d00000002013001900000000101100270000003370000c13d00000000010004110000052b0110009c00000000010000190000000101004039000000000101004b000003aa0000613d0000052c01000041000000800010043f0000000001000411000600000001001d000000840010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080030200003913cd13b80000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000003580000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000003500000413d000000000705004b000003670000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000006410000613d0000001f01400039000000600110018f00000080011001bf000000400010043f000000200130008c000007660000413d00000006010000290000000b020000290000000a030000290000000804000029000000090500002913cd0a4a0000040f0000000002010019000a00000002001d0000000b0100002900000007030000290000000804000029000000090500002913cd0f7a0000040f000004750000013d000000040420008a000000600440008c000007660000413d0000002404100370000000000404043b000b00000004001d0000000404100370000000000404043b000a00000004001d0000004404100370000000000404043b000005080540009c000007660000213d00000023054000390000050906000041000000000725004b000000000700001900000000070680190000050905500197000000000805004b0000000006008019000005090550009c000000000607c019000000000506004b000007660000c13d0000000405400039000000000151034f000000000101043b000900000001001d000005080110009c000007660000213d0000002404400039000800000004001d0000000901400029000000000121004b000007660000213d00000002013001900000000101100270000003a80000c13d00000000010004110000052b0110009c00000000010000190000000101004039000000000101004b000004330000c13d0000050b01000041000000800010043f0000002001000039000000840010043f0000002401000039000000a40010043f0000054501000041000000c40010043f0000054601000041000000e40010043f0000054701000041000013cf000104300000000003000416000000000303004b000007660000c13d000000040220008a000000200220008c000007660000413d0000000401100370000000000101043b0000050a0210009c000007660000213d000000c002000039000000400020043f000000800000043f000000a00000043f0000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d000000400200043d000005420320009c000004040000413d0000053b01000041000000000010043500000041010000390000041c0000013d0000050b01000041000000800010043f0000002001000039000000840010043f0000001401000039000000a40010043f0000053f01000041000000c40010043f0000050d01000041000013cf00010430000000400200043d0000001f0430018f0000000505300272000003ee0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000003e60000413d000000000604004b000003fd0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000004f501000041000004f50420009c000000000201801900000040012002100000006002300210000000000121019f000013cf00010430000000000101043b0000004003200039000000400030043f000000000301041a000000ff0130018f000000020410008c000004190000813d00000000011204360000000803300270000000ff0330018f000000010430008c000004190000213d00000000003104350000000003020433000000010230008c000004190000213d000000400200043d00000000033204360000000001010433000000010410008c0000071a0000a13d0000053b0100004100000000001004350000002101000039000000040010043f0000052001000041000013cf000104300000050b01000041000000800010043f0000002001000039000000840010043f0000004101000039000000a40010043f0000053401000041000000c40010043f0000053501000041000000e40010043f0000053601000041000006210000013d0000050b01000041000000800010043f0000002001000039000000840010043f0000001501000039000000a40010043f0000050c01000041000003de0000013d0000052c01000041000000800010043f0000000001000411000700000001001d000000840010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080030200003913cd13b80000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000004520000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b0000044a0000413d000000000705004b000004610000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000005e80000613d0000001f01400039000000600110018f00000080011001bf000000400010043f000000200130008c000007660000413d00000007010000290000000b020000290000000a030000290000000804000029000000090500002913cd0a4a0000040f0000000002010019000a00000002001d0000000b010000290000000803000029000000090400002913cd0b3d0000040f0000000a01000029000002fe0000013d0000000003000416000000000303004b000006050000c13d0000051201000041000000000010043900008002020000390000000400200443000004f5010000410000000003000414000004f50430009c0000000003018019000000c00130021000000513011001c713cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400400043d00000024014000390000000b02000029000000000021043500000527010000410000000000140435000000040140003900008010020000390000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000a00000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f0000000102200190000007680000613d0000000a01000029000005080110009c000003d30000213d0000000a01000029000000400010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000528011001c70000800d0200003900000004030000390000800705000039000080100700003900000529040000410000000b06000029000000ca0000013d000000050500002900000000045200490000008402500039000000c30440008a00000509060000410000000007000019000000000500001900000005087002100000000008e80019000000000881034f000000000808043b000000000948004b00000000090000190000000009068019000005090a400197000005090b800197000000000cab004b000000000c000019000000000c064019000000000aab013f000005090aa0009c000000000c09c01900000000090c004b000007660000c13d0000000008820019000000000881034f000000000808043b0000000005580019000000000885004b0000000008000019000000010800403900000001088001900000080f0000c13d00000001077000390000000008d7004b000004bb0000413d0000000001000416000000000151004b000006160000c13d0004050a0030019b0000050908000041000000000900001900080000000d001d00070000000e001d00000005019002100000000002e100190000000101000367000000000221034f000000000202043b00000005030000290000000003300079000000c30330008a000000000432004b0000000004000019000000000408801900000509033001970000050905200197000000000635004b00000000060000190000000006084019000000000335013f000005090330009c000000000604c019000000000306004b000007660000c13d000a00000009001d0000000002e20019000900000002001d0000006002200039000000000121034f000000000101043b000600000001001d000005120100004100000000001004390000000b0100002900000004001004430000000001000414000004f50210009c000004f501008041000000c00110021000000513011001c7000080020200003913cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000000080d000029000000070e00002900000509080000410000000a09000029000000090b000029000007660000613d000000400a00043d000005380100004100000000001a04350000000401a000390000004002000039000000000021043500000001010003670000000002b1034f000000000202043b0000004403a0003900000000002304350000002002b00039000000000321034f000000000303043b0000050a0430009c000007660000213d0000006404a0003900000000003404350000002002200039000000000321034f000000000303043b000000000403004b0000000004000019000000010400c039000000000443004b000007660000c13d0000008404a0003900000000003404350000002003200039000000000331034f000000000303043b000000a404a0003900000000003404350000004002200039000000000221034f000000000202043b00000000030000310000000004b300490000001f0440008a000000000542004b0000000005000019000000000508801900000509044001970000050906200197000000000746004b00000000070000190000000007084019000000000446013f000005090440009c000000000705c019000000000407004b000007660000c13d0000000004b20019000000000241034f000000000202043b000005080520009c000007660000213d00000020044000390000000003230049000000000534004b0000000005000019000000000508201900000509033001970000050906400197000000000736004b00000000070000190000000007084019000000000336013f000005090330009c000000000705c019000000000307004b000007660000c13d000000c403a00039000000a0050000390000000000530435000000e403a000390000000000230435000000000341034f0000010401a0003900000005042002720000056b0000613d000000000500001900000005065002100000000007610019000000000663034f000000000606043b00000000006704350000000105500039000000000645004b000005630000413d0000001f052001900000057a0000613d0000000504400210000000000343034f00000000044100190000000305500210000000000604043300000000065601cf000000000656022f000000000303043b0000010005500089000000000353022f00000000035301cf000000000363019f0000000000340435000000000112001900000000000104350000002401a000390000000403000029000000000031043500000000010004140000000b03000029000000040330008c000005a70000613d0000001f02200039000000200300008a000000000232016f000005390320009c0000053902008041000004f503a0009c000004f50400004100090000000a001d000000000304001900000000030a401900000040033002100000006002200210000000000232019f000004f50310009c0000000001048019000000c001100210000000000112019f0000053a011000410000000603000029000000000203004b0000059e0000613d00000528011001c700008009020000390000000b04000029000000000500001913cd13b80000040f000005a00000013d0000000b0200002913cd13b80000040f0000000102200190000000080d000029000000070e00002900000509080000410000000a09000029000000090a000029000007aa0000613d0000050801a0009c000003d30000213d0000004000a0043f00000001099000390000000001d9004b000004e00000413d000000cd0000013d000000400200043d0000001f0430018f0000000505300272000005bb0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000005b30000413d000000000604004b000005ca0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d0000001f0430018f0000000505300272000005d80000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000005d00000413d000000000604004b000005e70000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d0000001f0430018f0000000505300272000005f50000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000005ed0000413d000000000604004b000003fd0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d0000050b03000041000000000031043500000084032001bf00000020040000390000000000430435000000e40320003900000524040000410000000000430435000000c40320003900000525040000410000000000430435000000a40220003900000038030000390000000000320435000000400110021000000526011001c7000013cf000104300000050b01000041000000800010043f0000002001000039000000840010043f0000004501000039000000a40010043f0000053c01000041000000c40010043f0000053d01000041000000e40010043f0000053e01000041000001040010043f0000053701000041000013cf00010430000000400200043d0000001f0430018f0000000505300272000006310000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000006290000413d000000000604004b000006400000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d0000001f0430018f00000005053002720000064e0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000006460000413d000000000604004b0000065d0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400100043d00000084021000390000052e03000041000000000032043500000064021000390000052f0300004100000000003204350000004402100039000005300300004100000000003204350000002402100039000000430300003900000000003204350000050b020000410000000000210435000000040210003900000020030000390000000000320435000004f502000041000004f50310009c0000000001028019000000400110021000000531011001c7000013cf00010430000000c002100039000000400020043f00000005020000290000000000020435000000a001100039000400000001001d000000000001043500000007010000290000002001100039000300000001001d0000000101100367000000000101043b000700000001001d0000050a0110009c000007660000213d00000007010000290000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d00000005020000290000000002020433000000010320008c000004190000213d000000000101043b000000000301041a000001000400008a000000000343016f000000000223019f000000000021041b00000004030000290000000003030433000000010430008c000004190000213d0000051104000041000000000242016f00000008033002100000ff000330018f000000000223019f000000000021041b000000030100002900000060021000390000000101000367000000000321034f000000000303043b0000000904000029000000230440008a0000050905000041000000000643004b0000000006000019000000000605801900000509044001970000050907300197000000000847004b0000000005008019000000000447013f000005090440009c000000000506c019000000000405004b000007660000c13d0000000a033000290000000404300039000000000441034f000000000404043b000a00000004001d000005080440009c000007660000213d0000000a04000029000000000440007900000024063000390000050903000041000000000546004b000000000500001900000000050320190000050904400197000900000006001d0000050906600197000000000746004b0000000003008019000000000446013f000005090440009c000000000305c019000000000303004b000007660000c13d000000400220008a000000000121034f000000000101043b000000000201004b0000000002000019000000010200c039000000000221004b000007660000c13d0000000002000416000500000002001d000000000101004b000007ca0000c13d000000050100006b000008130000c13d0000051201000041000000000010043900008002020000390000000400200443000004f5010000410000000003000414000004f50430009c0000000003018019000000c00130021000000513011001c713cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400400043d00000024014000390000000602000029000000000021043500000527010000410000000000140435000000040140003900000007020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000b00000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f0000000102200190000008790000613d0000000b01000029000005080110009c000003d30000213d0000000b01000029000000400010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000528011001c70000800d0200003900000004030000390000052904000041000000080500002900000006060000290000000707000029000000ca0000013d0000000000130435000004f501000041000004f50320009c0000000002018019000000400120021000000543011001c7000013ce0001042e000000400400043d000a00000004001d0000054101000041000000000014043500000004014000390000000b020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c7000080020200003913cd13bd0000040f0000000a0a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000007470000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b0000073f0000413d00000000090a0019000000000705004b000007570000613d0000000506600210000000000761034f00000000066900190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000007880000613d0000001f01400039000000600210018f0000000001920019000000000221004b00000000020000190000000102004039000005080410009c000003d30000213d0000000102200190000003d30000c13d000000400010043f000000200130008c000007a50000813d0000000001000019000013cf00010430000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000007780000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000007700000413d000000000604004b000007870000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d0000001f0430018f0000000505300272000007950000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000078d0000413d000000000604004b000007a40000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d0000000001090433000000000101004b00000000010000190000000101006039000002ee0000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000007ba0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000007b20000413d000000000604004b000007c90000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000050100006b000008260000c13d0000051201000041000000000010043900008002020000390000000400200443000004f5010000410000000003000414000004f50430009c0000000003018019000000c00130021000000513011001c713cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400400043d0000051601000041000000000014043500000004024000390000000701000029000400000002001d00000000001204350000000601000029000005170110019700000518011001c70000002402400039000300000002001d0000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000b00000004001d00000000010440190002004000100218000000c00120021000000002011001af00000519011001c70000800202000039000100000002001d13cd13b80000040f0000000102200190000008590000613d0000000b01000029000005080110009c000003d30000213d0000000b01000029000000400010043f000000050100006b000008030000613d00000000010004160000051a011001970000000000010417000000000100041400000009040000290000000a024000290000000a0320006c00000000030000190000000103004039000004f50440019700000001033001900000080f0000c13d0000000003000031000000000523004b000008b90000813d0000053b01000041000000000010043500000011010000390000041c0000013d000000400100043d0000006402100039000005240300004100000000003204350000004402100039000005250300004100000000003204350000002402100039000000380300003900000000003204350000050b020000410000000000210435000000040210003900000020030000390000000000320435000004f502000041000004f50310009c0000000001028019000006130000013d000005120100004100000000001004390000800a010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c7000080020200003913cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400400043d000005140100004100000000001404350000004401400039000000000200041600000000002104350000002401400039000000070200002900000000002104350000000b010000290000050a0110019700000004024000390000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000b00000004001d00000000010440190000004001100210000000c002200210000000000112019f00000515011001c70000800a0200003913cd13b80000040f0000000102200190000008990000613d0000000b01000029000005080110009c000003d30000213d0000000b01000029000000400010043f000007cc0000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000008690000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000008610000413d000000000604004b000008780000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000008890000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000008810000413d000000000604004b000008980000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000008a90000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000008a10000413d000000000604004b000008b80000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d00000001044003670000051b0510009c000008cb0000413d0000050b010000410000000b020000290000000000120435000000200100003900000004030000290000000000130435000000080100003900000003030000290000000000130435000000440120003900000523020000410000000000210435000000020100002900000515011001c7000013cf000104300000000002230049000004f50220019700000000022403df000000c0011002100000051c011001970000051d011001c700000000011203af0000000702000029000000080d00002913cd13c70000040f00000000030100190000006003300270000004f5033001970000000102200190000009d50000613d0000003f023000390000051e02200197000000400400043d0000000002240019000b00000004001d000000000442004b00000000040000190000000104004039000005080520009c000003d30000213d0000000104400190000003d30000c13d000000400020043f0000000b0200002900000000083204360000001f023000390000000502200272000008f70000613d00000000040000310000000104400367000000000500001900000005065002100000000007680019000000000664034f000000000606043b00000000006704350000000105500039000000000625004b000008ef0000413d000900000008001d000000000200004b000008fa0000613d0000001f0230018f00000005033002720000000907000029000009070000613d000000000400001900000005054002100000000006570019000000000551034f000000000505043b00000000005604350000000104400039000000000534004b000008ff0000413d000000000402004b000009160000613d0000000503300210000000000131034f00000009033000290000000302200210000000000403043300000000042401cf000000000424022f000000000101043b0000010002200089000000000121022f00000000012101cf000000000141019f00000000001304350000051201000041000000000010043900000001020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400400043d0000051f010000410000000000140435000000040140003900000007020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000a00000004001d00000000010440190000004001100210000000c002200210000000000112019f00000520011001c7000080020200003913cd13b80000040f0000000102200190000009f00000613d0000000a01000029000005080110009c000003d30000213d0000000a01000029000000400010043f0000000b0100002900000000010104330000050902000041000000200310008c000000000300001900000000030240190000050904100197000000000504004b000000000200a019000005090440009c000000000203c019000000000202004b000007660000c13d00000009020000290000000002020433000005080320009c000007660000213d000000090110002900000009022000290000001f032000390000050904000041000000000513004b0000000005000019000000000504801900000509033001970000050906100197000000000763004b0000000004008019000000000363013f000005090330009c000000000405c019000000000304004b000007660000c13d0000000023020434000005080430009c000003d30000213d00000005043002100000003f04400039000000200500008a000000000454016f0000000a04400029000005080540009c000003d30000213d000000400040043f0000000a04000029000000000034043500000006033002100000000003230019000000000413004b000007660000213d000000000432004b000009900000813d00000509040000410000000a050000290000000006210049000000400760008c000000000700001900000000070440190000050906600197000000000806004b00000000080000190000000008042019000005090660009c000000000807c019000000000608004b000007660000c13d000000400600043d000005210760009c000003d30000213d00000020055000390000004007600039000000400070043f000000008702043400000000077604360000000008080433000000000087043500000000006504350000004002200039000000000632004b000009760000413d0000051201000041000000000010043900008005010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c7000080020200003913cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400300043d000000240130003900000040020000390000000000210435000005220100004100000000001304350000000401300039000000070200002900000000002104350000000a01000029000000000101043300000044023000390000000000120435000b00000003001d0000006402300039000000000301004b000009bf0000613d00000000030000190000000a040000290000002004400039000a00000004001d0000000004040433000000005404043400000000044204360000000005050433000000000054043500000040022000390000000103300039000000000413004b000009b30000413d0000000b040000290000000001420049000004f502000041000004f50340009c000000000302001900000000030440190000004003300210000004f50410009c00000000010280190000006001100210000000000131019f0000000003000414000004f50430009c0000000003028019000000c002300210000000000121019f000080050200003913cd13b80000040f000000010220019000000a100000613d000007080000013d000000000001042f0000001f0430018f0000000502300272000009e00000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000009d90000413d000000000504004b000009ee0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013cf00010430000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000a000000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000009f80000413d000000000604004b00000a0f0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000a200000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000a180000413d000000000604004b00000a2f0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d0000001f031000390000050904000041000000000523004b0000000005000019000000000504401900000509062001970000050903300197000000000763004b000000000400a019000000000363013f000005090330009c000000000405c019000000000304004b00000a480000613d0000000103100367000000000303043b000005080430009c00000a480000213d00000020011000390000000004310019000000000224004b00000a480000213d0000000002030019000000000001042d0000000001000019000013cf00010430000300000000000200000000070004140000000008450019000000000558004b00000000050000190000000105004039000004f504400197000000010550019000000ad20000c13d0000000006000031000000000586004b00000ad20000413d000200000002001d000300000001001d000100000003001d00000001044003670000051b0570009c00000adc0000813d0000000002860049000004f50220019700000000022403df000000c0017002100000051c0110019700000548011001c700000000011203af000080100200003913cd13c20000040f00000000030100190000006003300270000004f503300197000000010220019000000ae30000613d0000003f023000390000051e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000005080640009c00000ad60000213d000000010550019000000ad60000c13d000000400040043f00000000043204360000001f05300039000000050550027200000a850000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b00000a7d0000413d000000000500004b00000a870000613d0000001f0530018f000000050330027200000a930000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b00000a8b0000413d000000000605004b00000aa20000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f0000000000130435000000400100043d0000000002020433000000200220008c0000000305000029000000020600002900000afe0000c13d0000000002040433000000a0031000390000000000230435000000800210003900000000006204350000006002100039000000010300002900000000003204350000050a025001970000004003100039000000000023043500000020021000390000054a030000410000000000320435000000a00300003900000000003104350000054b0310009c00000ad60000213d000000c003100039000000400030043f000004f503000041000004f50420009c000000000203801900000040022002100000000001010433000004f50410009c00000000010380190000006001100210000000000121019f0000000002000414000004f50420009c0000000002038019000000c002200210000000000112019f00000528011001c7000080100200003913cd13bd0000040f000000010220019000000b0f0000613d000000000101043b0000050a01100197000000000001042d0000053b010000410000000000100435000000110100003900000ad90000013d0000053b0100004100000000001004350000004101000039000000040010043f0000052001000041000013cf00010430000000400100043d0000004402100039000005230300004100000000003204350000002402100039000000080300003900000b030000013d0000001f0430018f000000050230027200000aee0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b00000ae70000413d000000000504004b00000afc0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013cf0001043000000044021000390000054903000041000000000032043500000024021000390000001f0300003900000000003204350000050b020000410000000000210435000000040210003900000020030000390000000000320435000004f502000041000004f50310009c0000000001028019000000400110021000000515011001c7000013cf000104300000000001000019000013cf00010430000000400300043d000000600430003900000000002404350000050a0110019700000040023000390000000000120435000000600100003900000000011304360000054c0200004100000000002104350000054d0230009c00000b350000813d0000008002300039000000400020043f000004f502000041000004f50410009c000000000102801900000040011002100000000003030433000004f50430009c00000000030280190000006003300210000000000113019f0000000003000414000004f50430009c0000000003028019000000c002300210000000000112019f00000528011001c7000080100200003913cd13bd0000040f000000010220019000000b3b0000613d000000000101043b0000050a01100197000000000001042d0000053b0100004100000000001004350000004101000039000000040010043f0000052001000041000013cf000104300000000001000019000013cf000104300009000000000002000500000003001d000000400500043d0000000403500039000800000001001d000000000101004b00000e090000613d000400000004001d000300000002001d0000050a012001970000ffff0210008c00000e190000a13d0000054e020000410000000000250435000900000001001d0000000000130435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50350009c00000000010540190000004001100210000000c002200210000000000112019f00000520011001c70000800202000039000600000002001d000700000005001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000b6e0000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000b660000413d000000000705004b00000b7d0000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000000010220019000000e2c0000613d0000001f01400039000000600110018f0000000004a10019000000000114004b00000000010000190000000101004039000005080240009c00000dfa0000213d000000010110019000000dfa0000c13d000000400040043f0000001f0130008c00000df80000a13d000000040140003900000000020a0433000000000202004b00000e490000c13d0000055002000041000000000024043500000009020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c70000800302000039000700000004001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000bb40000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000bac0000413d000000000705004b00000bc30000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000000010220019000000e530000613d0000001f01400039000000600110018f0000000004a10019000005080140009c00000dfa0000213d000000400040043f000000200130008c00000df80000413d000000040140003900000000020a0433000000000202004b00000e700000c13d0000050e02000041000000000024043500000008020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c70000800402000039000700000004001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000bf50000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000bed0000413d000000000705004b00000c040000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000000010220019000000e7a0000613d0000001f01400039000000600110018f0000000004a10019000005080140009c00000dfa0000213d000000400040043f000000200130008c00000df80000413d00000000010a0433000000000101004b00000e970000613d000005210140009c00000dfa0000213d0000004001400039000000400010043f0000000001040436000200000001001d000000000001043500000009010000290000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c70000801002000039000700000004001d13cd13bd0000040f0000000703000029000000010220019000000df80000613d0000000002030433000000020320008c00000e010000813d000000000101043b000000000301041a000001000400008a000000000343016f000000000223019f000000000021041b00000002030000290000000003030433000000010430008c00000e010000213d0000051104000041000000000242016f00000008033002100000ff000330018f000000000223019f000000000021041b000000000100041600000512020000410000000000200439000000000101004b00000ca30000613d0000800a010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c70000800202000039000700000002001d13cd13bd0000040f000000010220019000000e000000613d000000000101043b000000000101004b00000df80000613d000000400400043d0000051401000041000000000014043500000044014000390000000002000416000000000021043500000024014000390000000902000029000000000021043500000000010004100000050a0110019700000004024000390000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000200000004001d00000000010440190000004001100210000000c002200210000000000112019f00000515011001c70000800a0200003913cd13b80000040f000000010220019000000f140000613d0000000202000029000005080120009c00000dfa0000213d000000400020043f0000051201000041000000000010043900000007020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f000000010220019000000e000000613d000000000101043b000000000101004b00000df80000613d000000400400043d0000051601000041000000000014043500000004024000390000000901000029000200000002001d00000000001204350000000801000029000005170110019700000518011001c70000002402400039000100000002001d0000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000700000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f000000010220019000000f340000613d0000000706000029000005080160009c00000dfa0000213d000000400060043f00000000010004160000051a01100197000000000001041700000cd10000013d00000006020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f000000010220019000000e000000613d000000000101043b000000000101004b00000df80000613d000000400400043d0000051601000041000000000014043500000004024000390000000901000029000200000002001d00000000001204350000000801000029000005170110019700000518011001c70000002402400039000100000002001d0000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000700000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f000000010220019000000f540000613d0000000706000029000005080160009c00000dfa0000213d000000400060043f000000000100041400000005040000290000000402400029000000040320006c00000000030000190000000103004039000004f504400197000000010330019000000e050000c13d0000000003000031000000000523004b00000e050000413d00000001044003670000051b0510009c00000ea80000813d00000000050004110000000002230049000004f50220019700000000022403df000000c0011002100000051c011001970000051d011001c700000000011203af000400000005001d0000050a0d500197000000030200002913cd13c70000040f00000000030100190000006003300270000004f503300197000000010220019000000eb90000613d0000003f023000390000051e02200197000000400600043d0000000002260019000000000462004b00000000040000190000000104004039000005080520009c00000dfa0000213d000000010440019000000dfa0000c13d000000400020043f000500000006001d00000000083604360000001f02300039000000050220027200000d0d0000613d00000000040000310000000104400367000000000500001900000005065002100000000007680019000000000664034f000000000606043b00000000006704350000000105500039000000000625004b00000d050000413d000000000200004b00000d0f0000613d0000001f0230018f000000050330027200000d1b0000613d000000000400001900000005054002100000000006580019000000000551034f000000000505043b00000000005604350000000104400039000000000534004b00000d130000413d000000000402004b00000d2a0000613d0000000503300210000000000131034f00000000033800190000000302200210000000000403043300000000042401cf000000000424022f000000000101043b0000010002200089000000000121022f00000000012101cf000000000141019f0000000000130435000700000008001d0000051201000041000000000010043900000006020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f000000010220019000000e000000613d000000000101043b000000000101004b00000df80000613d000000400400043d0000051f010000410000000000140435000000040140003900000009020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000600000004001d00000000010440190000004001100210000000c002200210000000000112019f00000520011001c7000080020200003913cd13b80000040f000000010220019000000ed40000613d0000000609000029000005080190009c000000050100002900000dfa0000213d000000400090043f00000000010104330000050902000041000000200310008c000000000300001900000000030240190000050904100197000000000504004b000000000200a019000005090440009c000000000203c019000000000202004b00000df80000c13d00000007020000290000000002020433000005080320009c00000df80000213d000000070110002900000007022000290000001f032000390000050904000041000000000513004b0000000005000019000000000504801900000509033001970000050906100197000000000763004b0000000004008019000000000363013f000005090330009c000000000405c019000000000304004b00000df80000c13d0000000023020434000005080430009c00000dfa0000213d00000005043002100000003f04400039000000200500008a000000000454016f0000000004940019000005080540009c00000dfa0000213d000000400040043f000000000039043500000006033002100000000003230019000000000413004b00000df80000213d000000000432004b00000da30000813d000005090400004100000000050900190000000006210049000000400760008c000000000700001900000000070440190000050906600197000000000806004b00000000080000190000000008042019000005090660009c000000000807c019000000000608004b00000df80000c13d000000400600043d000005210760009c00000dfa0000213d00000020055000390000004007600039000000400070043f000000008702043400000000077604360000000008080433000000000087043500000000006504350000004002200039000000000632004b00000d890000413d0000051201000041000000000010043900008005010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c7000080020200003913cd13bd0000040f000000010220019000000e000000613d000000000101043b000000000101004b000000060600002900000df80000613d000000400700043d000000240170003900000040020000390000000000210435000005220100004100000000001704350000000401700039000000090200002900000000002104350000000001060433000000440270003900000000001204350000006402700039000000000301004b00000dcf0000613d000000000300001900000020066000390000000004060433000000005404043400000000044204360000000005050433000000000054043500000040022000390000000103300039000000000413004b00000dc50000413d0000000001720049000004f502000041000004f50370009c000000000302001900000000030740190000004003300210000004f50410009c00000000010280190000006001100210000000000131019f0000000003000414000004f50430009c0000000003028019000000c002300210000000000121019f0000800502000039000700000007001d13cd13b80000040f000000010220019000000ef40000613d0000000702000029000005080120009c000000000102001900000dfa0000213d000000400010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000528011001c70000800d020000390000000403000039000005290400004100000004050000290000000806000029000000090700002913cd13b80000040f000000010120019000000df80000613d000000000001042d0000000001000019000013cf000104300000053b0100004100000000001004350000004101000039000000040010043f0000052001000041000013cf00010430000000000001042f0000053b010000410000000000100435000000210100003900000dfd0000013d0000053b010000410000000000100435000000110100003900000dfd0000013d0000050b0200004100000000002504350000002002000039000000000023043500000044015000390000055402000041000000000021043500000024015000390000001b020000390000000000210435000004f501000041000004f50250009c0000000005018019000000400150021000000515011001c7000013cf000104300000050b02000041000000000025043500000020020000390000000000230435000000640150003900000552020000410000000000210435000000440150003900000553020000410000000000210435000000240150003900000028020000390000000000210435000004f501000041000004f50250009c0000000005018019000000400150021000000526011001c7000013cf00010430000000400200043d0000001f0430018f000000050530027200000e390000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000e310000413d000000000604004b00000f730000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d0000050b0200004100000000002404350000002002000039000000000021043500000044014000390000054f0200004100000000002104350000002401400039000000150200003900000ea10000013d000000400200043d0000001f0430018f000000050530027200000e600000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000e580000413d000000000604004b00000e6f0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d0000050b020000410000000000240435000000200200003900000000002104350000004401400039000005510200004100000000002104350000002401400039000000130200003900000ea10000013d000000400200043d0000001f0430018f000000050530027200000e870000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000e7f0000413d000000000604004b00000e960000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d00000044014000390000052a02000041000000000021043500000024014000390000001a0200003900000000002104350000050b010000410000000000140435000000040140003900000020020000390000000000210435000004f501000041000004f50240009c0000000004018019000000400140021000000515011001c7000013cf000104300000050b010000410000000000160435000000200100003900000002020000290000000000120435000000080100003900000001020000290000000000120435000000440160003900000523020000410000000000210435000004f501000041000004f50260009c0000000006018019000000400160021000000515011001c7000013cf000104300000001f0430018f000000050230027200000ec40000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b00000ebd0000413d000000000504004b00000ed20000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013cf00010430000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000ee40000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000edc0000413d000000000604004b00000ef30000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000f040000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000efc0000413d000000000604004b00000f130000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000f240000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000f1c0000413d000000000604004b00000f330000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000f440000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000f3c0000413d000000000604004b00000f530000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000f640000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000f5c0000413d000000000604004b00000f730000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000004f501000041000004f50420009c000000000201801900000040012002100000006002300210000000000121019f000013cf000104300009000000000002000300000005001d000400000004001d000500000003001d000000400400043d0000000403400039000800000001001d000000000101004b0000124c0000613d000200000002001d0000050a012001970000ffff0210008c000012560000a13d0000054e020000410000000000240435000900000001001d0000000000130435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c70000800202000039000600000002001d000700000004001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000fac0000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000fa40000413d000000000705004b00000fbb0000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000012690000613d0000001f01400039000000600110018f0000000004a10019000000000114004b00000000010000190000000101004039000005080240009c0000123d0000213d00000001011001900000123d0000c13d000000400040043f0000001f0130008c0000123b0000a13d000000040140003900000000020a0433000000000202004b000012860000c13d0000055002000041000000000024043500000009020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c70000800302000039000700000004001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000ff20000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000fea0000413d000000000705004b000010010000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000012900000613d0000001f01400039000000600110018f0000000004a10019000005080140009c0000123d0000213d000000400040043f000000200130008c0000123b0000413d000000040140003900000000020a0433000000000202004b000012ad0000c13d0000050e02000041000000000024043500000008020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c70000800402000039000700000004001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000010330000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b0000102b0000413d000000000705004b000010420000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000012b70000613d0000001f01400039000000600110018f0000000004a10019000005080140009c0000123d0000213d000000400040043f000000200130008c0000123b0000413d00000000010a0433000000000101004b000012d40000613d000005210140009c0000123d0000213d0000004001400039000000400010043f000000000304043600000000000304350000000502000029000000020120008c000012440000813d0000000000240435000500000003001d000000000003043500000009010000290000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c70000801002000039000700000004001d13cd13bd0000040f000000070300002900000001022001900000123b0000613d0000000002030433000000010320008c0000000505000029000012440000213d000000000101043b000000000301041a000001000400008a000000000343016f000000000223019f000000000021041b0000000003050433000000010430008c000012440000213d0000051104000041000000000242016f00000008033002100000ff000330018f000000000223019f000000000021041b000000000100041600000512020000410000000000200439000000000101004b000010e60000613d0000800a010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c70000800202000039000700000002001d13cd13bd0000040f0000000102200190000012430000613d000000000101043b000000000101004b0000123b0000613d000000400400043d0000051401000041000000000014043500000044014000390000000002000416000000000021043500000024014000390000000902000029000000000021043500000000010004100000050a0110019700000004024000390000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000500000004001d00000000010440190000004001100210000000c002200210000000000112019f00000515011001c70000800a0200003913cd13b80000040f0000000102200190000013510000613d0000000502000029000005080120009c0000123d0000213d000000400020043f0000051201000041000000000010043900000007020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f0000000102200190000012430000613d000000000101043b000000000101004b0000123b0000613d000000400400043d0000051601000041000000000014043500000004024000390000000901000029000500000002001d00000000001204350000000801000029000005170110019700000518011001c70000002402400039000100000002001d0000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000700000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f0000000102200190000013710000613d0000000706000029000005080160009c0000123d0000213d000000400060043f00000000010004160000051a011001970000000000010417000011140000013d00000006020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f0000000102200190000012430000613d000000000101043b000000000101004b0000123b0000613d000000400400043d0000051601000041000000000014043500000004024000390000000901000029000500000002001d00000000001204350000000801000029000005170110019700000518011001c70000002402400039000100000002001d0000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000700000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f0000000102200190000013910000613d0000000706000029000005080160009c0000123d0000213d000000400060043f000000000100041400000004040000290000000302400029000000030320006c00000000030000190000000103004039000004f5044001970000000103300190000012480000c13d0000000003000031000000000523004b000012480000413d00000001044003670000051b0510009c000012e50000813d00000000050004110000000002230049000004f50220019700000000022403df000000c0011002100000051c011001970000051d011001c700000000011203af000400000005001d0000050a0d500197000000020200002913cd13c70000040f00000000030100190000006003300270000004f5033001970000000102200190000012f60000613d0000003f023000390000051e02200197000000400600043d0000000002260019000000000462004b00000000040000190000000104004039000005080520009c0000123d0000213d00000001044001900000123d0000c13d000000400020043f000500000006001d00000000083604360000001f023000390000000502200272000011500000613d00000000040000310000000104400367000000000500001900000005065002100000000007680019000000000664034f000000000606043b00000000006704350000000105500039000000000625004b000011480000413d000000000200004b000011520000613d0000001f0230018f00000005033002720000115e0000613d000000000400001900000005054002100000000006580019000000000551034f000000000505043b00000000005604350000000104400039000000000534004b000011560000413d000000000402004b0000116d0000613d0000000503300210000000000131034f00000000033800190000000302200210000000000403043300000000042401cf000000000424022f000000000101043b0000010002200089000000000121022f00000000012101cf000000000141019f0000000000130435000700000008001d0000051201000041000000000010043900000006020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f0000000102200190000012430000613d000000000101043b000000000101004b0000123b0000613d000000400400043d0000051f010000410000000000140435000000040140003900000009020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000600000004001d00000000010440190000004001100210000000c002200210000000000112019f00000520011001c7000080020200003913cd13b80000040f0000000102200190000013110000613d0000000609000029000005080190009c00000005010000290000123d0000213d000000400090043f00000000010104330000050902000041000000200310008c000000000300001900000000030240190000050904100197000000000504004b000000000200a019000005090440009c000000000203c019000000000202004b0000123b0000c13d00000007020000290000000002020433000005080320009c0000123b0000213d000000070110002900000007022000290000001f032000390000050904000041000000000513004b0000000005000019000000000504801900000509033001970000050906100197000000000763004b0000000004008019000000000363013f000005090330009c000000000405c019000000000304004b0000123b0000c13d0000000023020434000005080430009c0000123d0000213d00000005043002100000003f04400039000000200500008a000000000454016f0000000004940019000005080540009c0000123d0000213d000000400040043f000000000039043500000006033002100000000003230019000000000413004b0000123b0000213d000000000432004b000011e60000813d000005090400004100000000050900190000000006210049000000400760008c000000000700001900000000070440190000050906600197000000000806004b00000000080000190000000008042019000005090660009c000000000807c019000000000608004b0000123b0000c13d000000400600043d000005210760009c0000123d0000213d00000020055000390000004007600039000000400070043f000000008702043400000000077604360000000008080433000000000087043500000000006504350000004002200039000000000632004b000011cc0000413d0000051201000041000000000010043900008005010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c7000080020200003913cd13bd0000040f0000000102200190000012430000613d000000000101043b000000000101004b00000006060000290000123b0000613d000000400700043d000000240170003900000040020000390000000000210435000005220100004100000000001704350000000401700039000000090200002900000000002104350000000001060433000000440270003900000000001204350000006402700039000000000301004b000012120000613d000000000300001900000020066000390000000004060433000000005404043400000000044204360000000005050433000000000054043500000040022000390000000103300039000000000413004b000012080000413d0000000001720049000004f502000041000004f50370009c000000000302001900000000030740190000004003300210000004f50410009c00000000010280190000006001100210000000000131019f0000000003000414000004f50430009c0000000003028019000000c002300210000000000121019f0000800502000039000700000007001d13cd13b80000040f0000000102200190000013310000613d0000000702000029000005080120009c00000000010200190000123d0000213d000000400010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000528011001c70000800d020000390000000403000039000005290400004100000004050000290000000806000029000000090700002913cd13b80000040f00000001012001900000123b0000613d000000000001042d0000000001000019000013cf000104300000053b0100004100000000001004350000004101000039000000040010043f0000052001000041000013cf00010430000000000001042f0000053b0100004100000000001004350000002101000039000012400000013d0000053b0100004100000000001004350000001101000039000012400000013d0000050b0200004100000000002404350000002002000039000000000023043500000044014000390000055402000041000000000021043500000024014000390000001b02000039000012de0000013d0000050b02000041000000000024043500000020020000390000000000230435000000640140003900000552020000410000000000210435000000440140003900000553020000410000000000210435000000240140003900000028020000390000000000210435000004f501000041000004f50240009c0000000004018019000000400140021000000526011001c7000013cf00010430000000400200043d0000001f0430018f0000000505300272000012760000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000126e0000413d000000000604004b000013b00000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d0000050b0200004100000000002404350000002002000039000000000021043500000044014000390000054f02000041000000000021043500000024014000390000001502000039000012de0000013d000000400200043d0000001f0430018f00000005053002720000129d0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000012950000413d000000000604004b000012ac0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d0000050b0200004100000000002404350000002002000039000000000021043500000044014000390000055102000041000000000021043500000024014000390000001302000039000012de0000013d000000400200043d0000001f0430018f0000000505300272000012c40000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000012bc0000413d000000000604004b000012d30000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d00000044014000390000052a02000041000000000021043500000024014000390000001a0200003900000000002104350000050b010000410000000000140435000000040140003900000020020000390000000000210435000004f501000041000004f50240009c0000000004018019000000400140021000000515011001c7000013cf000104300000050b010000410000000000160435000000200100003900000005020000290000000000120435000000080100003900000001020000290000000000120435000000440160003900000523020000410000000000210435000004f501000041000004f50260009c0000000006018019000000400160021000000515011001c7000013cf000104300000001f0430018f0000000502300272000013010000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000012fa0000413d000000000504004b0000130f0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013cf00010430000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000013210000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013190000413d000000000604004b000013300000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000013410000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013390000413d000000000604004b000013500000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000013610000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013590000413d000000000604004b000013700000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000013810000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013790000413d000000000604004b000013900000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000013a10000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013990000413d000000000604004b000013b00000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000004f501000041000004f50420009c000000000201801900000040012002100000006002300210000000000121019f000013cf00010430000000000001042f000013bb002104210000000102000039000000000001042d0000000002000019000000000001042d000013c0002104230000000102000039000000000001042d0000000002000019000000000001042d000013c5002104230000000102000039000000000001042d0000000002000019000000000001042d000000000f0d0019000013cb002104290000000102000039000000000001042d0000000002000019000000000001042d000013cd00000432000013ce0001042e000013cf00010430000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000000000000000000000000000000000000000000000000000000000009c4d535a00000000000000000000000000000000000000000000000000000000e9f18c1600000000000000000000000000000000000000000000000000000000ecf95b8900000000000000000000000000000000000000000000000000000000ecf95b8a00000000000000000000000000000000000000000000000000000000f3385fb600000000000000000000000000000000000000000000000000000000e9f18c1700000000000000000000000000000000000000000000000000000000ec8067c7000000000000000000000000000000000000000000000000000000009c4d535b00000000000000000000000000000000000000000000000000000000bb0fd61000000000000000000000000000000000000000000000000000000000da37f07f000000000000000000000000000000000000000000000000000000005d3826ff000000000000000000000000000000000000000000000000000000005d382700000000000000000000000000000000000000000000000000000000007b510fe80000000000000000000000000000000000000000000000000000000084da1fb400000000000000000000000000000000000000000000000000000000187598a5000000000000000000000000000000000000000000000000000000003cda33510000000000000000000000000000000000000000000000000000000057180981000000000000000000000000000000000000000000000000ffffffffffffffff8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff08c379a00000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c792062792073656c66000000000000000000000000000000000000000000000000000000000000640000008000000000000000004c6314f00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000240000008000000000000000000200000000000000000000000000000000000040000000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00ff1806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b830200000200000000000000000000000000000024000000000000000000000000579952fc0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000004f1e1be000000000000000000000000000000000000000000000000000000000ff00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0001000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004400000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffff000000000000000000000000000000000000000000000000000000010000000000000000ffffffff000000000000000000000000000000000000000000000000000100010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001ffffffe0c2e4ff97000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffbfad7e232e000000000000000000000000000000000000000000000000000000004f766572666c6f770000000000000000000000000000000000000000000000006e6f742063616c6c2074686520636f6e7374727563746f7200000000000000005468652076616c7565206d757374206265207a65726f20696620776520646f2000000000000000000000000000000000000000840000000000000000000000000d4651aa000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000290afdae231a3fc0bbae8b1af63698b0a1d79b21ad17df0342dfb952fe74f8e554686520636f64652068617368206973206e6f74206b6e6f776e0000000000000000000000000000000000000000000000000000000000000000000000010000306395c6000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000696e6700000000000000000000000000000000000000000000000000000000006f6d2073657175656e7469616c20746f20617262697472617279206f726465724974206973206f6e6c7920706f737369626c6520746f206368616e676520667200000000000000000000000000000000000000a40000000000000000000000000200000000000000000000000000000000000020000000000000000000000000c7544194dab38b1652f35439b9b4806d8b71e113f2cf5c1351cb2ecf7c83959a43616e206f6e6c792062652063616c6c656420627920464f5243455f4445504c4f594552206f7220434f4d504c45585f55504752414445525f434f4e54524143540000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000a4000000800000000000000000f3385fb60000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000fffffefb00000000000000000000000000000000000001040000000000000000000000004e487b71000000000000000000000000000000000000000000000000000000006076616c7565602070726f7669646564206973206e6f7420657175616c20746f2074686520636f6d62696e6564206076616c75656073206f66206465706c6f796d656e7473000000000000000000000000000000000000000000000000000000496e617070726f7072696174652063616c6c6572000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffff00004de2e46800000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffc000000000000000000000000000000000000000400000000000000000000000003fb6f4f15ddd4a75588ca934894ad2cdcab25a5012e2515e1783433d0128611a54686973206d6574686f6420726571756972652073797374656d2063616c6c20666c616700000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000008400000080000000000000000000000001000000000000000000000000000000000000000000000000000000006b656363616b3235362072657475726e656420696e76616c69642064617461002020dba91b30cc0006188af794c2fb30dd8520db7e2c088b7fc7c103c00ca494000000000000000000000000000000000000000000000000ffffffffffffff3f63bae3a9951d38e8a3fbb7b70909afc1200610fc5bc55ade242f815974674f23000000000000000000000000000000000000000000000000ffffffffffffff80e03fe17700000000000000000000000000000000000000000000000000000000436f64652068617368206973206e6f6e2d7a65726f00000000000000000000005aa9b6b5000000000000000000000000000000000000000000000000000000004163636f756e74206973206f6363757069656400000000000000000000000000656c20737061636500000000000000000000000000000000000000000000000043616e206e6f74206465706c6f7920636f6e74726163747320696e206b65726e42797465636f6465486173682063616e6e6f74206265207a65726f00000000000000000000000000000000000000000000000000000000000000000000000000c6bfca40024beb29b89193d12075c4c65e1e59922af8b8619fa7a3e6faea8523", + "deployedBytecode": "0x0002000000000002000b0000000000020000000003020019000100000001035500000000020100190000006002200270000004f50020019d0000008004000039000000400040043f000004f5022001970000000104300190000000860000c13d000000040420008c000007660000413d000000000401043b000000e004400270000004f70540009c0000008e0000a13d000004f80540009c000000cf0000a13d000004f90540009c0000000005000410000b00000005001d000001470000213d000004fc0540009c000001b40000613d000004fd0440009c000007660000c13d0000000004000416000000000404004b000007660000c13d000000040220008a000000200220008c000007660000413d0000000401100370000000000101043b000b00000001001d000000010110008c000007660000213d000000000200041100000002013001900000002c0000c13d0000ffff0120008c000003aa0000213d000a00000002001d0000000000200435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d000000400400043d000005210240009c000003d30000213d000000000101043b0000004002400039000000400020043f000000000101041a000000ff0210018f000000010320008c000004190000213d00000000032404360000000801100270000000ff0110018f000000010210008c000004190000213d000900000004001d00000000001304350000000b02000029000000010220008c0000065e0000c13d000000000101004b0000065e0000c13d0000000101000039000b00000003001d000800000001001d00000000001304350000000a010000290000050a011001970000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d00000009020000290000000002020433000000010320008c0000000b05000029000004190000213d000000000101043b000000000301041a000001000400008a000000000343016f000000000223019f000000000021041b0000000003050433000000010430008c000004190000213d0000051104000041000000000242016f00000008033002100000ff000330018f000000000223019f000000000021041b000000400100043d00000008020000290000000000210435000004f5020000410000000003000414000004f50430009c0000000003028019000004f50410009c00000000010280190000004001100210000000c002300210000000000112019f00000532011001c70000800d0200003900000002030000390000053304000041000000c90000013d0000000001000416000000000101004b000007660000c13d000000200100003900000100001004430000012000000443000004f601000041000013ce0001042e000005010540009c000001230000213d000005050540009c000002f00000613d000005060540009c0000037d0000613d000005070440009c000007660000c13d0000000004000416000000000404004b000007660000c13d000000040220008a000000200220008c000007660000413d0000000401100370000000000101043b000b00000001001d000000010110008c000007660000213d00000000020004110000000201300190000000a60000c13d0000ffff0120008c000003aa0000213d000a00000002001d0000000000200435000000200000043f000004f5030000410000000001000414000004f50210009c0000000001038019000000c00110021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d000000000101043b000000000201041a000001000300008a000000000232016f0000000b03000029000000000232019f000000000021041b000000400100043d00000000003104350000000002000414000004f50320009c000004f5040000410000000002048019000004f50310009c00000000010480190000004001100210000000c002200210000000000112019f00000532011001c70000800d02000039000000020300003900000544040000410000000a0500002913cd13b80000040f0000000101200190000007660000613d0000000001000019000013ce0001042e000004fe0540009c000002510000613d000004ff0340009c000002bc0000613d000005000340009c000007660000c13d000000040220008a000000200220008c000007660000413d0000000401100370000000000201043b0000000001000411000080070110008c000003d70000c13d0000050e01000041000000800010043f000b00000002001d000000840020043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080040200003913cd13bd0000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000000fb0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000000f30000413d000000000705004b0000010a0000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000003e10000613d0000001f01400039000000600210018f00000080012001bf000000400010043f000000200330008c000007660000413d000000800300043d000000000303004b000004770000c13d0000050b03000041000000000031043500000084032001bf00000020040000390000000000430435000000c4032000390000052a040000410000000000430435000000a4022000390000001a030000390000000000320435000000400110021000000515011001c7000013cf00010430000005020540009c000003070000613d000005030340009c000003b60000613d000005040340009c000007660000c13d0000000003000416000000000303004b000007660000c13d000000040320008a000000800330008c000007660000413d0000000403100370000000000303043b000b00000003001d0000050a0330009c000007660000213d0000006401100370000000000101043b000005080310009c000007660000213d000000040110003913cd0a300000040f00000001040003670000004403400370000000000303043b0000002404400370000000000404043b000000000501001900000000060200190000000b0100002900000000020400190000000004050019000000000506001913cd0a4a0000040f000002fe0000013d000004fa0540009c000001e00000613d000004fb0340009c000007660000c13d000000040320008a000000400330008c000007660000413d0000000403100370000000000303043b000a00000003001d000005080330009c000007660000213d0000000a0420006a0000050902000041000000a40340008c00000000030000190000000003024019000900000004001d0000050904400197000000000504004b000000000200a019000005090440009c000000000203c019000000000202004b000007660000c13d0000002402100370000000000202043b000800000002001d0000050a0220009c000007660000213d00000000020004110000000b0220006c0000042b0000c13d0000000a02000029000700040020003d0000000701100360000000000201043b0000050e01000041000000800010043f000600000002001d000000840020043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080040200003913cd13bd0000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000018a0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000001820000413d000000000705004b000001990000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000005ae0000613d0000001f01400039000000600110018f00000080021001bf000500000002001d000000400020043f000000200230008c000007660000413d000000800200043d000000000202004b000006760000c13d0000050b020000410000000504000029000000000024043500000084021001bf00000020030000390000000000320435000000c4021000390000052a030000410000000000320435000000a4011000390000001a020000390000000000210435000000400140021000000515011001c7000013cf00010430000000040320008a000000200330008c000007660000413d0000000403100370000000000303043b000500000003001d000005080330009c000007660000213d000000050300002900000023033000390000050904000041000000000523004b000000000500001900000000050480190000050903300197000000000603004b0000000004008019000005090330009c000000000405c019000000000304004b000007660000c13d00000005030000290000000403300039000000000331034f000000000d03043b0000050803d0009c000007660000213d0000000503000029000000240e3000390000000503d002100000000003e30019000000000323004b000007660000213d000000090400008a0000000003000411000000000443016f000080070440008c0000041f0000c13d00000000040d004b000004b40000c13d0000000001000416000000000101004b000000cd0000613d000006160000013d000000040420008a000000800440008c000007660000413d0000002404100370000000000404043b000b00000004001d0000004404100370000000000404043b000005080540009c000007660000213d00000023054000390000050906000041000000000725004b000000000700001900000000070680190000050905500197000000000805004b0000000006008019000005090550009c000000000607c019000000000506004b000007660000c13d0000000405400039000000000551034f000000000505043b000a00000005001d000005080550009c000007660000213d0000002405400039000900000005001d0000000a04500029000000000224004b000007660000213d0000006401100370000000000101043b000800000001001d000000010110008c000007660000213d000000020130019000000001011002700000020d0000c13d00000000010004110000052b0110009c00000000010000190000000101004039000000000101004b000003aa0000613d0000052c01000041000000800010043f0000000001000411000700000001001d000000840010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080030200003913cd13b80000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000022e0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000002260000413d000000000705004b0000023d0000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000006240000613d0000001f01400039000000600110018f00000080011001bf000000400010043f000000200130008c000007660000413d000000800200043d000000070100002913cd0b110000040f0000000002010019000700000002001d0000000b01000029000000080300002900000009040000290000000a0500002913cd0f7a0000040f0000000701000029000002fe0000013d000000040420008a000000600440008c000007660000413d0000002404100370000000000404043b000b00000004001d0000004404100370000000000404043b000005080540009c000007660000213d00000023054000390000050906000041000000000725004b000000000700001900000000070680190000050905500197000000000805004b0000000006008019000005090550009c000000000607c019000000000506004b000007660000c13d0000000405400039000000000151034f000000000101043b000a00000001001d000005080110009c000007660000213d0000002404400039000900000004001d0000000a01400029000000000121004b000007660000213d00000002013001900000000101100270000002790000c13d00000000010004110000052b0110009c00000000010000190000000101004039000000000101004b000003aa0000613d0000052c01000041000000800010043f0000000001000411000800000001001d000000840010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080030200003913cd13b80000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000029a0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000002920000413d000000000705004b000002a90000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000005cb0000613d0000001f01400039000000600110018f00000080011001bf000000400010043f000000200130008c000007660000413d000000800200043d000000080100002913cd0b110000040f0000000002010019000800000002001d0000000b0100002900000009030000290000000a0400002913cd0b3d0000040f0000000801000029000002fe0000013d0000000003000416000000000303004b000007660000c13d000000040220008a000000200220008c000007660000413d0000000401100370000000000101043b000b00000001001d0000050a0110009c000007660000213d0000000b010000290000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d000000400200043d000005210320009c000003d30000213d000000000101043b0000004003200039000000400030043f000000000101041a000000ff0310018f000000010430008c000004190000213d00000000033204360000000801100270000000ff0110018f000000010410008c000004190000213d00000000001304350000000002020433000000010120008c000004190000213d0000000101000039000000000202004b000002ff0000c13d0000000b0100002900000540011001980000000001000019000007210000c13d000000010110018f000002ff0000013d0000000003000416000000000303004b000007660000c13d000000040220008a000000400220008c000007660000413d0000000402100370000000000302043b0000050a0230009c000007660000213d0000002401100370000000000201043b000000000103001913cd0b110000040f0000050a01100197000000400200043d0000000000120435000004f501000041000004f50320009c000000000201801900000040012002100000052d011001c7000013ce0001042e000000040420008a000000800440008c000007660000413d0000002404100370000000000404043b000b00000004001d0000000404100370000000000404043b000a00000004001d0000004404100370000000000404043b000005080540009c000007660000213d00000023054000390000050906000041000000000725004b000000000700001900000000070680190000050905500197000000000805004b0000000006008019000005090550009c000000000607c019000000000506004b000007660000c13d0000000405400039000000000551034f000000000505043b000900000005001d000005080550009c000007660000213d0000002405400039000800000005001d0000000904500029000000000224004b000007660000213d0000006401100370000000000101043b000700000001001d000000010110008c000007660000213d00000002013001900000000101100270000003370000c13d00000000010004110000052b0110009c00000000010000190000000101004039000000000101004b000003aa0000613d0000052c01000041000000800010043f0000000001000411000600000001001d000000840010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080030200003913cd13b80000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000003580000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000003500000413d000000000705004b000003670000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000006410000613d0000001f01400039000000600110018f00000080011001bf000000400010043f000000200130008c000007660000413d00000006010000290000000b020000290000000a030000290000000804000029000000090500002913cd0a4a0000040f0000000002010019000a00000002001d0000000b0100002900000007030000290000000804000029000000090500002913cd0f7a0000040f000004750000013d000000040420008a000000600440008c000007660000413d0000002404100370000000000404043b000b00000004001d0000000404100370000000000404043b000a00000004001d0000004404100370000000000404043b000005080540009c000007660000213d00000023054000390000050906000041000000000725004b000000000700001900000000070680190000050905500197000000000805004b0000000006008019000005090550009c000000000607c019000000000506004b000007660000c13d0000000405400039000000000151034f000000000101043b000900000001001d000005080110009c000007660000213d0000002404400039000800000004001d0000000901400029000000000121004b000007660000213d00000002013001900000000101100270000003a80000c13d00000000010004110000052b0110009c00000000010000190000000101004039000000000101004b000004330000c13d0000050b01000041000000800010043f0000002001000039000000840010043f0000002401000039000000a40010043f0000054501000041000000c40010043f0000054601000041000000e40010043f0000054701000041000013cf000104300000000003000416000000000303004b000007660000c13d000000040220008a000000200220008c000007660000413d0000000401100370000000000101043b0000050a0210009c000007660000213d000000c002000039000000400020043f000000800000043f000000a00000043f0000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d000000400200043d000005420320009c000004040000413d0000053b01000041000000000010043500000041010000390000041c0000013d0000050b01000041000000800010043f0000002001000039000000840010043f0000001401000039000000a40010043f0000053f01000041000000c40010043f0000050d01000041000013cf00010430000000400200043d0000001f0430018f0000000505300272000003ee0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000003e60000413d000000000604004b000003fd0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000004f501000041000004f50420009c000000000201801900000040012002100000006002300210000000000121019f000013cf00010430000000000101043b0000004003200039000000400030043f000000000301041a000000ff0130018f000000020410008c000004190000813d00000000011204360000000803300270000000ff0330018f000000010430008c000004190000213d00000000003104350000000003020433000000010230008c000004190000213d000000400200043d00000000033204360000000001010433000000010410008c0000071a0000a13d0000053b0100004100000000001004350000002101000039000000040010043f0000052001000041000013cf000104300000050b01000041000000800010043f0000002001000039000000840010043f0000004101000039000000a40010043f0000053401000041000000c40010043f0000053501000041000000e40010043f0000053601000041000006210000013d0000050b01000041000000800010043f0000002001000039000000840010043f0000001501000039000000a40010043f0000050c01000041000003de0000013d0000052c01000041000000800010043f0000000001000411000700000001001d000000840010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000050f011001c7000080030200003913cd13b80000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000004520000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b0000044a0000413d000000000705004b000004610000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000005e80000613d0000001f01400039000000600110018f00000080011001bf000000400010043f000000200130008c000007660000413d00000007010000290000000b020000290000000a030000290000000804000029000000090500002913cd0a4a0000040f0000000002010019000a00000002001d0000000b010000290000000803000029000000090400002913cd0b3d0000040f0000000a01000029000002fe0000013d0000000003000416000000000303004b000006050000c13d0000051201000041000000000010043900008002020000390000000400200443000004f5010000410000000003000414000004f50430009c0000000003018019000000c00130021000000513011001c713cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400400043d00000024014000390000000b02000029000000000021043500000527010000410000000000140435000000040140003900008010020000390000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000a00000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f0000000102200190000007680000613d0000000a01000029000005080110009c000003d30000213d0000000a01000029000000400010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000528011001c70000800d0200003900000004030000390000800705000039000080100700003900000529040000410000000b06000029000000ca0000013d000000050500002900000000045200490000008402500039000000c30440008a00000509060000410000000007000019000000000500001900000005087002100000000008e80019000000000881034f000000000808043b000000000948004b00000000090000190000000009068019000005090a400197000005090b800197000000000cab004b000000000c000019000000000c064019000000000aab013f000005090aa0009c000000000c09c01900000000090c004b000007660000c13d0000000008820019000000000881034f000000000808043b0000000005580019000000000885004b0000000008000019000000010800403900000001088001900000080f0000c13d00000001077000390000000008d7004b000004bb0000413d0000000001000416000000000151004b000006160000c13d0004050a0030019b0000050908000041000000000900001900080000000d001d00070000000e001d00000005019002100000000002e100190000000101000367000000000221034f000000000202043b00000005030000290000000003300079000000c30330008a000000000432004b0000000004000019000000000408801900000509033001970000050905200197000000000635004b00000000060000190000000006084019000000000335013f000005090330009c000000000604c019000000000306004b000007660000c13d000a00000009001d0000000002e20019000900000002001d0000006002200039000000000121034f000000000101043b000600000001001d000005120100004100000000001004390000000b0100002900000004001004430000000001000414000004f50210009c000004f501008041000000c00110021000000513011001c7000080020200003913cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000000080d000029000000070e00002900000509080000410000000a09000029000000090b000029000007660000613d000000400a00043d000005380100004100000000001a04350000000401a000390000004002000039000000000021043500000001010003670000000002b1034f000000000202043b0000004403a0003900000000002304350000002002b00039000000000321034f000000000303043b0000050a0430009c000007660000213d0000006404a0003900000000003404350000002002200039000000000321034f000000000303043b000000000403004b0000000004000019000000010400c039000000000443004b000007660000c13d0000008404a0003900000000003404350000002003200039000000000331034f000000000303043b000000a404a0003900000000003404350000004002200039000000000221034f000000000202043b00000000030000310000000004b300490000001f0440008a000000000542004b0000000005000019000000000508801900000509044001970000050906200197000000000746004b00000000070000190000000007084019000000000446013f000005090440009c000000000705c019000000000407004b000007660000c13d0000000004b20019000000000241034f000000000202043b000005080520009c000007660000213d00000020044000390000000003230049000000000534004b0000000005000019000000000508201900000509033001970000050906400197000000000736004b00000000070000190000000007084019000000000336013f000005090330009c000000000705c019000000000307004b000007660000c13d000000c403a00039000000a0050000390000000000530435000000e403a000390000000000230435000000000341034f0000010401a0003900000005042002720000056b0000613d000000000500001900000005065002100000000007610019000000000663034f000000000606043b00000000006704350000000105500039000000000645004b000005630000413d0000001f052001900000057a0000613d0000000504400210000000000343034f00000000044100190000000305500210000000000604043300000000065601cf000000000656022f000000000303043b0000010005500089000000000353022f00000000035301cf000000000363019f0000000000340435000000000112001900000000000104350000002401a000390000000403000029000000000031043500000000010004140000000b03000029000000040330008c000005a70000613d0000001f02200039000000200300008a000000000232016f000005390320009c0000053902008041000004f503a0009c000004f50400004100090000000a001d000000000304001900000000030a401900000040033002100000006002200210000000000232019f000004f50310009c0000000001048019000000c001100210000000000112019f0000053a011000410000000603000029000000000203004b0000059e0000613d00000528011001c700008009020000390000000b04000029000000000500001913cd13b80000040f000005a00000013d0000000b0200002913cd13b80000040f0000000102200190000000080d000029000000070e00002900000509080000410000000a09000029000000090a000029000007aa0000613d0000050801a0009c000003d30000213d0000004000a0043f00000001099000390000000001d9004b000004e00000413d000000cd0000013d000000400200043d0000001f0430018f0000000505300272000005bb0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000005b30000413d000000000604004b000005ca0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d0000001f0430018f0000000505300272000005d80000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000005d00000413d000000000604004b000005e70000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d0000001f0430018f0000000505300272000005f50000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000005ed0000413d000000000604004b000003fd0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d0000050b03000041000000000031043500000084032001bf00000020040000390000000000430435000000e40320003900000524040000410000000000430435000000c40320003900000525040000410000000000430435000000a40220003900000038030000390000000000320435000000400110021000000526011001c7000013cf000104300000050b01000041000000800010043f0000002001000039000000840010043f0000004501000039000000a40010043f0000053c01000041000000c40010043f0000053d01000041000000e40010043f0000053e01000041000001040010043f0000053701000041000013cf00010430000000400200043d0000001f0430018f0000000505300272000006310000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000006290000413d000000000604004b000006400000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d0000001f0430018f00000005053002720000064e0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000006460000413d000000000604004b0000065d0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400100043d00000084021000390000052e03000041000000000032043500000064021000390000052f0300004100000000003204350000004402100039000005300300004100000000003204350000002402100039000000430300003900000000003204350000050b020000410000000000210435000000040210003900000020030000390000000000320435000004f502000041000004f50310009c0000000001028019000000400110021000000531011001c7000013cf00010430000000c002100039000000400020043f00000005020000290000000000020435000000a001100039000400000001001d000000000001043500000007010000290000002001100039000300000001001d0000000101100367000000000101043b000700000001001d0000050a0110009c000007660000213d00000007010000290000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c7000080100200003913cd13bd0000040f0000000102200190000007660000613d00000005020000290000000002020433000000010320008c000004190000213d000000000101043b000000000301041a000001000400008a000000000343016f000000000223019f000000000021041b00000004030000290000000003030433000000010430008c000004190000213d0000051104000041000000000242016f00000008033002100000ff000330018f000000000223019f000000000021041b000000030100002900000060021000390000000101000367000000000321034f000000000303043b0000000904000029000000230440008a0000050905000041000000000643004b0000000006000019000000000605801900000509044001970000050907300197000000000847004b0000000005008019000000000447013f000005090440009c000000000506c019000000000405004b000007660000c13d0000000a033000290000000404300039000000000441034f000000000404043b000a00000004001d000005080440009c000007660000213d0000000a04000029000000000440007900000024063000390000050903000041000000000546004b000000000500001900000000050320190000050904400197000900000006001d0000050906600197000000000746004b0000000003008019000000000446013f000005090440009c000000000305c019000000000303004b000007660000c13d000000400220008a000000000121034f000000000101043b000000000201004b0000000002000019000000010200c039000000000221004b000007660000c13d0000000002000416000500000002001d000000000101004b000007ca0000c13d000000050100006b000008130000c13d0000051201000041000000000010043900008002020000390000000400200443000004f5010000410000000003000414000004f50430009c0000000003018019000000c00130021000000513011001c713cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400400043d00000024014000390000000602000029000000000021043500000527010000410000000000140435000000040140003900000007020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000b00000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f0000000102200190000008790000613d0000000b01000029000005080110009c000003d30000213d0000000b01000029000000400010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000528011001c70000800d0200003900000004030000390000052904000041000000080500002900000006060000290000000707000029000000ca0000013d0000000000130435000004f501000041000004f50320009c0000000002018019000000400120021000000543011001c7000013ce0001042e000000400400043d000a00000004001d0000054101000041000000000014043500000004014000390000000b020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c7000080020200003913cd13bd0000040f0000000a0a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000007470000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b0000073f0000413d00000000090a0019000000000705004b000007570000613d0000000506600210000000000761034f00000000066900190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000007880000613d0000001f01400039000000600210018f0000000001920019000000000221004b00000000020000190000000102004039000005080410009c000003d30000213d0000000102200190000003d30000c13d000000400010043f000000200130008c000007a50000813d0000000001000019000013cf00010430000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000007780000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000007700000413d000000000604004b000007870000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d0000001f0430018f0000000505300272000007950000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000078d0000413d000000000604004b000007a40000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d0000000001090433000000000101004b00000000010000190000000101006039000002ee0000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000007ba0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000007b20000413d000000000604004b000007c90000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000050100006b000008260000c13d0000051201000041000000000010043900008002020000390000000400200443000004f5010000410000000003000414000004f50430009c0000000003018019000000c00130021000000513011001c713cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400400043d0000051601000041000000000014043500000004024000390000000701000029000400000002001d00000000001204350000000601000029000005170110019700000518011001c70000002402400039000300000002001d0000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000b00000004001d00000000010440190002004000100218000000c00120021000000002011001af00000519011001c70000800202000039000100000002001d13cd13b80000040f0000000102200190000008590000613d0000000b01000029000005080110009c000003d30000213d0000000b01000029000000400010043f000000050100006b000008030000613d00000000010004160000051a011001970000000000010417000000000100041400000009040000290000000a024000290000000a0320006c00000000030000190000000103004039000004f50440019700000001033001900000080f0000c13d0000000003000031000000000523004b000008b90000813d0000053b01000041000000000010043500000011010000390000041c0000013d000000400100043d0000006402100039000005240300004100000000003204350000004402100039000005250300004100000000003204350000002402100039000000380300003900000000003204350000050b020000410000000000210435000000040210003900000020030000390000000000320435000004f502000041000004f50310009c0000000001028019000006130000013d000005120100004100000000001004390000800a010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c7000080020200003913cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400400043d000005140100004100000000001404350000004401400039000000000200041600000000002104350000002401400039000000070200002900000000002104350000000b010000290000050a0110019700000004024000390000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000b00000004001d00000000010440190000004001100210000000c002200210000000000112019f00000515011001c70000800a0200003913cd13b80000040f0000000102200190000008990000613d0000000b01000029000005080110009c000003d30000213d0000000b01000029000000400010043f000007cc0000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000008690000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000008610000413d000000000604004b000008780000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000008890000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000008810000413d000000000604004b000008980000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000008a90000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000008a10000413d000000000604004b000008b80000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d00000001044003670000051b0510009c000008cb0000413d0000050b010000410000000b020000290000000000120435000000200100003900000004030000290000000000130435000000080100003900000003030000290000000000130435000000440120003900000523020000410000000000210435000000020100002900000515011001c7000013cf000104300000000002230049000004f50220019700000000022403df000000c0011002100000051c011001970000051d011001c700000000011203af0000000702000029000000080d00002913cd13c70000040f00000000030100190000006003300270000004f5033001970000000102200190000009d50000613d0000003f023000390000051e02200197000000400400043d0000000002240019000b00000004001d000000000442004b00000000040000190000000104004039000005080520009c000003d30000213d0000000104400190000003d30000c13d000000400020043f0000000b0200002900000000083204360000001f023000390000000502200272000008f70000613d00000000040000310000000104400367000000000500001900000005065002100000000007680019000000000664034f000000000606043b00000000006704350000000105500039000000000625004b000008ef0000413d000900000008001d000000000200004b000008fa0000613d0000001f0230018f00000005033002720000000907000029000009070000613d000000000400001900000005054002100000000006570019000000000551034f000000000505043b00000000005604350000000104400039000000000534004b000008ff0000413d000000000402004b000009160000613d0000000503300210000000000131034f00000009033000290000000302200210000000000403043300000000042401cf000000000424022f000000000101043b0000010002200089000000000121022f00000000012101cf000000000141019f00000000001304350000051201000041000000000010043900000001020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400400043d0000051f010000410000000000140435000000040140003900000007020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000a00000004001d00000000010440190000004001100210000000c002200210000000000112019f00000520011001c7000080020200003913cd13b80000040f0000000102200190000009f00000613d0000000a01000029000005080110009c000003d30000213d0000000a01000029000000400010043f0000000b0100002900000000010104330000050902000041000000200310008c000000000300001900000000030240190000050904100197000000000504004b000000000200a019000005090440009c000000000203c019000000000202004b000007660000c13d00000009020000290000000002020433000005080320009c000007660000213d000000090110002900000009022000290000001f032000390000050904000041000000000513004b0000000005000019000000000504801900000509033001970000050906100197000000000763004b0000000004008019000000000363013f000005090330009c000000000405c019000000000304004b000007660000c13d0000000023020434000005080430009c000003d30000213d00000005043002100000003f04400039000000200500008a000000000454016f0000000a04400029000005080540009c000003d30000213d000000400040043f0000000a04000029000000000034043500000006033002100000000003230019000000000413004b000007660000213d000000000432004b000009900000813d00000509040000410000000a050000290000000006210049000000400760008c000000000700001900000000070440190000050906600197000000000806004b00000000080000190000000008042019000005090660009c000000000807c019000000000608004b000007660000c13d000000400600043d000005210760009c000003d30000213d00000020055000390000004007600039000000400070043f000000008702043400000000077604360000000008080433000000000087043500000000006504350000004002200039000000000632004b000009760000413d0000051201000041000000000010043900008005010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c7000080020200003913cd13bd0000040f0000000102200190000009d40000613d000000000101043b000000000101004b000007660000613d000000400300043d000000240130003900000040020000390000000000210435000005220100004100000000001304350000000401300039000000070200002900000000002104350000000a01000029000000000101043300000044023000390000000000120435000b00000003001d0000006402300039000000000301004b000009bf0000613d00000000030000190000000a040000290000002004400039000a00000004001d0000000004040433000000005404043400000000044204360000000005050433000000000054043500000040022000390000000103300039000000000413004b000009b30000413d0000000b040000290000000001420049000004f502000041000004f50340009c000000000302001900000000030440190000004003300210000004f50410009c00000000010280190000006001100210000000000131019f0000000003000414000004f50430009c0000000003028019000000c002300210000000000121019f000080050200003913cd13b80000040f000000010220019000000a100000613d000007080000013d000000000001042f0000001f0430018f0000000502300272000009e00000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000009d90000413d000000000504004b000009ee0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013cf00010430000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000a000000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000009f80000413d000000000604004b00000a0f0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000a200000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000a180000413d000000000604004b00000a2f0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000003fd0000013d0000001f031000390000050904000041000000000523004b0000000005000019000000000504401900000509062001970000050903300197000000000763004b000000000400a019000000000363013f000005090330009c000000000405c019000000000304004b00000a480000613d0000000103100367000000000303043b000005080430009c00000a480000213d00000020011000390000000004310019000000000224004b00000a480000213d0000000002030019000000000001042d0000000001000019000013cf00010430000300000000000200000000070004140000000008450019000000000558004b00000000050000190000000105004039000004f504400197000000010550019000000ad20000c13d0000000006000031000000000586004b00000ad20000413d000200000002001d000300000001001d000100000003001d00000001044003670000051b0570009c00000adc0000813d0000000002860049000004f50220019700000000022403df000000c0017002100000051c0110019700000548011001c700000000011203af000080100200003913cd13c20000040f00000000030100190000006003300270000004f503300197000000010220019000000ae30000613d0000003f023000390000051e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000005080640009c00000ad60000213d000000010550019000000ad60000c13d000000400040043f00000000043204360000001f05300039000000050550027200000a850000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b00000a7d0000413d000000000500004b00000a870000613d0000001f0530018f000000050330027200000a930000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b00000a8b0000413d000000000605004b00000aa20000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f0000000000130435000000400100043d0000000002020433000000200220008c0000000305000029000000020600002900000afe0000c13d0000000002040433000000a0031000390000000000230435000000800210003900000000006204350000006002100039000000010300002900000000003204350000050a025001970000004003100039000000000023043500000020021000390000054a030000410000000000320435000000a00300003900000000003104350000054b0310009c00000ad60000213d000000c003100039000000400030043f000004f503000041000004f50420009c000000000203801900000040022002100000000001010433000004f50410009c00000000010380190000006001100210000000000121019f0000000002000414000004f50420009c0000000002038019000000c002200210000000000112019f00000528011001c7000080100200003913cd13bd0000040f000000010220019000000b0f0000613d000000000101043b0000050a01100197000000000001042d0000053b010000410000000000100435000000110100003900000ad90000013d0000053b0100004100000000001004350000004101000039000000040010043f0000052001000041000013cf00010430000000400100043d0000004402100039000005230300004100000000003204350000002402100039000000080300003900000b030000013d0000001f0430018f000000050230027200000aee0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b00000ae70000413d000000000504004b00000afc0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013cf0001043000000044021000390000054903000041000000000032043500000024021000390000001f0300003900000000003204350000050b020000410000000000210435000000040210003900000020030000390000000000320435000004f502000041000004f50310009c0000000001028019000000400110021000000515011001c7000013cf000104300000000001000019000013cf00010430000000400300043d000000600430003900000000002404350000050a0110019700000040023000390000000000120435000000600100003900000000011304360000054c0200004100000000002104350000054d0230009c00000b350000813d0000008002300039000000400020043f000004f502000041000004f50410009c000000000102801900000040011002100000000003030433000004f50430009c00000000030280190000006003300210000000000113019f0000000003000414000004f50430009c0000000003028019000000c002300210000000000112019f00000528011001c7000080100200003913cd13bd0000040f000000010220019000000b3b0000613d000000000101043b0000050a01100197000000000001042d0000053b0100004100000000001004350000004101000039000000040010043f0000052001000041000013cf000104300000000001000019000013cf000104300009000000000002000500000003001d000000400500043d0000000403500039000800000001001d000000000101004b00000e090000613d000400000004001d000300000002001d0000050a012001970000ffff0210008c00000e190000a13d0000054e020000410000000000250435000900000001001d0000000000130435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50350009c00000000010540190000004001100210000000c002200210000000000112019f00000520011001c70000800202000039000600000002001d000700000005001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000b6e0000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000b660000413d000000000705004b00000b7d0000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000000010220019000000e2c0000613d0000001f01400039000000600110018f0000000004a10019000000000114004b00000000010000190000000101004039000005080240009c00000dfa0000213d000000010110019000000dfa0000c13d000000400040043f0000001f0130008c00000df80000a13d000000040140003900000000020a0433000000000202004b00000e490000c13d0000055002000041000000000024043500000009020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c70000800302000039000700000004001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000bb40000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000bac0000413d000000000705004b00000bc30000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000000010220019000000e530000613d0000001f01400039000000600110018f0000000004a10019000005080140009c00000dfa0000213d000000400040043f000000200130008c00000df80000413d000000040140003900000000020a0433000000000202004b00000e700000c13d0000050e02000041000000000024043500000008020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c70000800402000039000700000004001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000bf50000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000bed0000413d000000000705004b00000c040000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000000010220019000000e7a0000613d0000001f01400039000000600110018f0000000004a10019000005080140009c00000dfa0000213d000000400040043f000000200130008c00000df80000413d00000000010a0433000000000101004b00000e970000613d000005210140009c00000dfa0000213d0000004001400039000000400010043f0000000001040436000200000001001d000000000001043500000009010000290000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c70000801002000039000700000004001d13cd13bd0000040f0000000703000029000000010220019000000df80000613d0000000002030433000000020320008c00000e010000813d000000000101043b000000000301041a000001000400008a000000000343016f000000000223019f000000000021041b00000002030000290000000003030433000000010430008c00000e010000213d0000051104000041000000000242016f00000008033002100000ff000330018f000000000223019f000000000021041b000000000100041600000512020000410000000000200439000000000101004b00000ca30000613d0000800a010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c70000800202000039000700000002001d13cd13bd0000040f000000010220019000000e000000613d000000000101043b000000000101004b00000df80000613d000000400400043d0000051401000041000000000014043500000044014000390000000002000416000000000021043500000024014000390000000902000029000000000021043500000000010004100000050a0110019700000004024000390000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000200000004001d00000000010440190000004001100210000000c002200210000000000112019f00000515011001c70000800a0200003913cd13b80000040f000000010220019000000f140000613d0000000202000029000005080120009c00000dfa0000213d000000400020043f0000051201000041000000000010043900000007020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f000000010220019000000e000000613d000000000101043b000000000101004b00000df80000613d000000400400043d0000051601000041000000000014043500000004024000390000000901000029000200000002001d00000000001204350000000801000029000005170110019700000518011001c70000002402400039000100000002001d0000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000700000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f000000010220019000000f340000613d0000000706000029000005080160009c00000dfa0000213d000000400060043f00000000010004160000051a01100197000000000001041700000cd10000013d00000006020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f000000010220019000000e000000613d000000000101043b000000000101004b00000df80000613d000000400400043d0000051601000041000000000014043500000004024000390000000901000029000200000002001d00000000001204350000000801000029000005170110019700000518011001c70000002402400039000100000002001d0000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000700000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f000000010220019000000f540000613d0000000706000029000005080160009c00000dfa0000213d000000400060043f000000000100041400000005040000290000000402400029000000040320006c00000000030000190000000103004039000004f504400197000000010330019000000e050000c13d0000000003000031000000000523004b00000e050000413d00000001044003670000051b0510009c00000ea80000813d00000000050004110000000002230049000004f50220019700000000022403df000000c0011002100000051c011001970000051d011001c700000000011203af000400000005001d0000050a0d500197000000030200002913cd13c70000040f00000000030100190000006003300270000004f503300197000000010220019000000eb90000613d0000003f023000390000051e02200197000000400600043d0000000002260019000000000462004b00000000040000190000000104004039000005080520009c00000dfa0000213d000000010440019000000dfa0000c13d000000400020043f000500000006001d00000000083604360000001f02300039000000050220027200000d0d0000613d00000000040000310000000104400367000000000500001900000005065002100000000007680019000000000664034f000000000606043b00000000006704350000000105500039000000000625004b00000d050000413d000000000200004b00000d0f0000613d0000001f0230018f000000050330027200000d1b0000613d000000000400001900000005054002100000000006580019000000000551034f000000000505043b00000000005604350000000104400039000000000534004b00000d130000413d000000000402004b00000d2a0000613d0000000503300210000000000131034f00000000033800190000000302200210000000000403043300000000042401cf000000000424022f000000000101043b0000010002200089000000000121022f00000000012101cf000000000141019f0000000000130435000700000008001d0000051201000041000000000010043900000006020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f000000010220019000000e000000613d000000000101043b000000000101004b00000df80000613d000000400400043d0000051f010000410000000000140435000000040140003900000009020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000600000004001d00000000010440190000004001100210000000c002200210000000000112019f00000520011001c7000080020200003913cd13b80000040f000000010220019000000ed40000613d0000000609000029000005080190009c000000050100002900000dfa0000213d000000400090043f00000000010104330000050902000041000000200310008c000000000300001900000000030240190000050904100197000000000504004b000000000200a019000005090440009c000000000203c019000000000202004b00000df80000c13d00000007020000290000000002020433000005080320009c00000df80000213d000000070110002900000007022000290000001f032000390000050904000041000000000513004b0000000005000019000000000504801900000509033001970000050906100197000000000763004b0000000004008019000000000363013f000005090330009c000000000405c019000000000304004b00000df80000c13d0000000023020434000005080430009c00000dfa0000213d00000005043002100000003f04400039000000200500008a000000000454016f0000000004940019000005080540009c00000dfa0000213d000000400040043f000000000039043500000006033002100000000003230019000000000413004b00000df80000213d000000000432004b00000da30000813d000005090400004100000000050900190000000006210049000000400760008c000000000700001900000000070440190000050906600197000000000806004b00000000080000190000000008042019000005090660009c000000000807c019000000000608004b00000df80000c13d000000400600043d000005210760009c00000dfa0000213d00000020055000390000004007600039000000400070043f000000008702043400000000077604360000000008080433000000000087043500000000006504350000004002200039000000000632004b00000d890000413d0000051201000041000000000010043900008005010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c7000080020200003913cd13bd0000040f000000010220019000000e000000613d000000000101043b000000000101004b000000060600002900000df80000613d000000400700043d000000240170003900000040020000390000000000210435000005220100004100000000001704350000000401700039000000090200002900000000002104350000000001060433000000440270003900000000001204350000006402700039000000000301004b00000dcf0000613d000000000300001900000020066000390000000004060433000000005404043400000000044204360000000005050433000000000054043500000040022000390000000103300039000000000413004b00000dc50000413d0000000001720049000004f502000041000004f50370009c000000000302001900000000030740190000004003300210000004f50410009c00000000010280190000006001100210000000000131019f0000000003000414000004f50430009c0000000003028019000000c002300210000000000121019f0000800502000039000700000007001d13cd13b80000040f000000010220019000000ef40000613d0000000702000029000005080120009c000000000102001900000dfa0000213d000000400010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000528011001c70000800d020000390000000403000039000005290400004100000004050000290000000806000029000000090700002913cd13b80000040f000000010120019000000df80000613d000000000001042d0000000001000019000013cf000104300000053b0100004100000000001004350000004101000039000000040010043f0000052001000041000013cf00010430000000000001042f0000053b010000410000000000100435000000210100003900000dfd0000013d0000053b010000410000000000100435000000110100003900000dfd0000013d0000050b0200004100000000002504350000002002000039000000000023043500000044015000390000055402000041000000000021043500000024015000390000001b020000390000000000210435000004f501000041000004f50250009c0000000005018019000000400150021000000515011001c7000013cf000104300000050b02000041000000000025043500000020020000390000000000230435000000640150003900000552020000410000000000210435000000440150003900000553020000410000000000210435000000240150003900000028020000390000000000210435000004f501000041000004f50250009c0000000005018019000000400150021000000526011001c7000013cf00010430000000400200043d0000001f0430018f000000050530027200000e390000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000e310000413d000000000604004b00000f730000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d0000050b0200004100000000002404350000002002000039000000000021043500000044014000390000054f0200004100000000002104350000002401400039000000150200003900000ea10000013d000000400200043d0000001f0430018f000000050530027200000e600000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000e580000413d000000000604004b00000e6f0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d0000050b020000410000000000240435000000200200003900000000002104350000004401400039000005510200004100000000002104350000002401400039000000130200003900000ea10000013d000000400200043d0000001f0430018f000000050530027200000e870000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000e7f0000413d000000000604004b00000e960000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d00000044014000390000052a02000041000000000021043500000024014000390000001a0200003900000000002104350000050b010000410000000000140435000000040140003900000020020000390000000000210435000004f501000041000004f50240009c0000000004018019000000400140021000000515011001c7000013cf000104300000050b010000410000000000160435000000200100003900000002020000290000000000120435000000080100003900000001020000290000000000120435000000440160003900000523020000410000000000210435000004f501000041000004f50260009c0000000006018019000000400160021000000515011001c7000013cf000104300000001f0430018f000000050230027200000ec40000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b00000ebd0000413d000000000504004b00000ed20000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013cf00010430000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000ee40000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000edc0000413d000000000604004b00000ef30000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000f040000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000efc0000413d000000000604004b00000f130000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000f240000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000f1c0000413d000000000604004b00000f330000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000f440000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000f3c0000413d000000000604004b00000f530000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f000000000015043500000f730000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f503300197000000050530027200000f640000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000f5c0000413d000000000604004b00000f730000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000004f501000041000004f50420009c000000000201801900000040012002100000006002300210000000000121019f000013cf000104300009000000000002000300000005001d000400000004001d000500000003001d000000400400043d0000000403400039000800000001001d000000000101004b0000124c0000613d000200000002001d0000050a012001970000ffff0210008c000012560000a13d0000054e020000410000000000240435000900000001001d0000000000130435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c70000800202000039000600000002001d000700000004001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000fac0000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000fa40000413d000000000705004b00000fbb0000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000012690000613d0000001f01400039000000600110018f0000000004a10019000000000114004b00000000010000190000000101004039000005080240009c0000123d0000213d00000001011001900000123d0000c13d000000400040043f0000001f0130008c0000123b0000a13d000000040140003900000000020a0433000000000202004b000012860000c13d0000055002000041000000000024043500000009020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c70000800302000039000700000004001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000ff20000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000fea0000413d000000000705004b000010010000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000012900000613d0000001f01400039000000600110018f0000000004a10019000005080140009c0000123d0000213d000000400040043f000000200130008c0000123b0000413d000000040140003900000000020a0433000000000202004b000012ad0000c13d0000050e02000041000000000024043500000008020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c00000000010440190000004001100210000000c002200210000000000112019f00000520011001c70000800402000039000700000004001d13cd13bd0000040f000000070a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000010330000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b0000102b0000413d000000000705004b000010420000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000012b70000613d0000001f01400039000000600110018f0000000004a10019000005080140009c0000123d0000213d000000400040043f000000200130008c0000123b0000413d00000000010a0433000000000101004b000012d40000613d000005210140009c0000123d0000213d0000004001400039000000400010043f000000000304043600000000000304350000000502000029000000020120008c000012440000813d0000000000240435000500000003001d000000000003043500000009010000290000000000100435000000200000043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000510011001c70000801002000039000700000004001d13cd13bd0000040f000000070300002900000001022001900000123b0000613d0000000002030433000000010320008c0000000505000029000012440000213d000000000101043b000000000301041a000001000400008a000000000343016f000000000223019f000000000021041b0000000003050433000000010430008c000012440000213d0000051104000041000000000242016f00000008033002100000ff000330018f000000000223019f000000000021041b000000000100041600000512020000410000000000200439000000000101004b000010e60000613d0000800a010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c70000800202000039000700000002001d13cd13bd0000040f0000000102200190000012430000613d000000000101043b000000000101004b0000123b0000613d000000400400043d0000051401000041000000000014043500000044014000390000000002000416000000000021043500000024014000390000000902000029000000000021043500000000010004100000050a0110019700000004024000390000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000500000004001d00000000010440190000004001100210000000c002200210000000000112019f00000515011001c70000800a0200003913cd13b80000040f0000000102200190000013510000613d0000000502000029000005080120009c0000123d0000213d000000400020043f0000051201000041000000000010043900000007020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f0000000102200190000012430000613d000000000101043b000000000101004b0000123b0000613d000000400400043d0000051601000041000000000014043500000004024000390000000901000029000500000002001d00000000001204350000000801000029000005170110019700000518011001c70000002402400039000100000002001d0000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000700000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f0000000102200190000013710000613d0000000706000029000005080160009c0000123d0000213d000000400060043f00000000010004160000051a011001970000000000010417000011140000013d00000006020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f0000000102200190000012430000613d000000000101043b000000000101004b0000123b0000613d000000400400043d0000051601000041000000000014043500000004024000390000000901000029000500000002001d00000000001204350000000801000029000005170110019700000518011001c70000002402400039000100000002001d0000000000120435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000700000004001d00000000010440190000004001100210000000c002200210000000000112019f00000519011001c7000080020200003913cd13b80000040f0000000102200190000013910000613d0000000706000029000005080160009c0000123d0000213d000000400060043f000000000100041400000004040000290000000302400029000000030320006c00000000030000190000000103004039000004f5044001970000000103300190000012480000c13d0000000003000031000000000523004b000012480000413d00000001044003670000051b0510009c000012e50000813d00000000050004110000000002230049000004f50220019700000000022403df000000c0011002100000051c011001970000051d011001c700000000011203af000400000005001d0000050a0d500197000000020200002913cd13c70000040f00000000030100190000006003300270000004f5033001970000000102200190000012f60000613d0000003f023000390000051e02200197000000400600043d0000000002260019000000000462004b00000000040000190000000104004039000005080520009c0000123d0000213d00000001044001900000123d0000c13d000000400020043f000500000006001d00000000083604360000001f023000390000000502200272000011500000613d00000000040000310000000104400367000000000500001900000005065002100000000007680019000000000664034f000000000606043b00000000006704350000000105500039000000000625004b000011480000413d000000000200004b000011520000613d0000001f0230018f00000005033002720000115e0000613d000000000400001900000005054002100000000006580019000000000551034f000000000505043b00000000005604350000000104400039000000000534004b000011560000413d000000000402004b0000116d0000613d0000000503300210000000000131034f00000000033800190000000302200210000000000403043300000000042401cf000000000424022f000000000101043b0000010002200089000000000121022f00000000012101cf000000000141019f0000000000130435000700000008001d0000051201000041000000000010043900000006020000290000000400200443000004f5010000410000000004000414000004f50340009c0000000004018019000000c00140021000000513011001c713cd13bd0000040f0000000102200190000012430000613d000000000101043b000000000101004b0000123b0000613d000000400400043d0000051f010000410000000000140435000000040140003900000009020000290000000000210435000004f5010000410000000002000414000004f50320009c0000000002018019000004f50340009c000600000004001d00000000010440190000004001100210000000c002200210000000000112019f00000520011001c7000080020200003913cd13b80000040f0000000102200190000013110000613d0000000609000029000005080190009c00000005010000290000123d0000213d000000400090043f00000000010104330000050902000041000000200310008c000000000300001900000000030240190000050904100197000000000504004b000000000200a019000005090440009c000000000203c019000000000202004b0000123b0000c13d00000007020000290000000002020433000005080320009c0000123b0000213d000000070110002900000007022000290000001f032000390000050904000041000000000513004b0000000005000019000000000504801900000509033001970000050906100197000000000763004b0000000004008019000000000363013f000005090330009c000000000405c019000000000304004b0000123b0000c13d0000000023020434000005080430009c0000123d0000213d00000005043002100000003f04400039000000200500008a000000000454016f0000000004940019000005080540009c0000123d0000213d000000400040043f000000000039043500000006033002100000000003230019000000000413004b0000123b0000213d000000000432004b000011e60000813d000005090400004100000000050900190000000006210049000000400760008c000000000700001900000000070440190000050906600197000000000806004b00000000080000190000000008042019000005090660009c000000000807c019000000000608004b0000123b0000c13d000000400600043d000005210760009c0000123d0000213d00000020055000390000004007600039000000400070043f000000008702043400000000077604360000000008080433000000000087043500000000006504350000004002200039000000000632004b000011cc0000413d0000051201000041000000000010043900008005010000390000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000513011001c7000080020200003913cd13bd0000040f0000000102200190000012430000613d000000000101043b000000000101004b00000006060000290000123b0000613d000000400700043d000000240170003900000040020000390000000000210435000005220100004100000000001704350000000401700039000000090200002900000000002104350000000001060433000000440270003900000000001204350000006402700039000000000301004b000012120000613d000000000300001900000020066000390000000004060433000000005404043400000000044204360000000005050433000000000054043500000040022000390000000103300039000000000413004b000012080000413d0000000001720049000004f502000041000004f50370009c000000000302001900000000030740190000004003300210000004f50410009c00000000010280190000006001100210000000000131019f0000000003000414000004f50430009c0000000003028019000000c002300210000000000121019f0000800502000039000700000007001d13cd13b80000040f0000000102200190000013310000613d0000000702000029000005080120009c00000000010200190000123d0000213d000000400010043f000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000528011001c70000800d020000390000000403000039000005290400004100000004050000290000000806000029000000090700002913cd13b80000040f00000001012001900000123b0000613d000000000001042d0000000001000019000013cf000104300000053b0100004100000000001004350000004101000039000000040010043f0000052001000041000013cf00010430000000000001042f0000053b0100004100000000001004350000002101000039000012400000013d0000053b0100004100000000001004350000001101000039000012400000013d0000050b0200004100000000002404350000002002000039000000000023043500000044014000390000055402000041000000000021043500000024014000390000001b02000039000012de0000013d0000050b02000041000000000024043500000020020000390000000000230435000000640140003900000552020000410000000000210435000000440140003900000553020000410000000000210435000000240140003900000028020000390000000000210435000004f501000041000004f50240009c0000000004018019000000400140021000000526011001c7000013cf00010430000000400200043d0000001f0430018f0000000505300272000012760000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000126e0000413d000000000604004b000013b00000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d0000050b0200004100000000002404350000002002000039000000000021043500000044014000390000054f02000041000000000021043500000024014000390000001502000039000012de0000013d000000400200043d0000001f0430018f00000005053002720000129d0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000012950000413d000000000604004b000012ac0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d0000050b0200004100000000002404350000002002000039000000000021043500000044014000390000055102000041000000000021043500000024014000390000001302000039000012de0000013d000000400200043d0000001f0430018f0000000505300272000012c40000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000012bc0000413d000000000604004b000012d30000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d00000044014000390000052a02000041000000000021043500000024014000390000001a0200003900000000002104350000050b010000410000000000140435000000040140003900000020020000390000000000210435000004f501000041000004f50240009c0000000004018019000000400140021000000515011001c7000013cf000104300000050b010000410000000000160435000000200100003900000005020000290000000000120435000000080100003900000001020000290000000000120435000000440160003900000523020000410000000000210435000004f501000041000004f50260009c0000000006018019000000400160021000000515011001c7000013cf000104300000001f0430018f0000000502300272000013010000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000012fa0000413d000000000504004b0000130f0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013cf00010430000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000013210000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013190000413d000000000604004b000013300000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000013410000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013390000413d000000000604004b000013500000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000013610000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013590000413d000000000604004b000013700000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000013810000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013790000413d000000000604004b000013900000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000013b00000013d000000400200043d000000000301001900000060033002700000001f0430018f000004f5033001970000000505300272000013a10000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013990000413d000000000604004b000013b00000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000004f501000041000004f50420009c000000000201801900000040012002100000006002300210000000000121019f000013cf00010430000000000001042f000013bb002104210000000102000039000000000001042d0000000002000019000000000001042d000013c0002104230000000102000039000000000001042d0000000002000019000000000001042d000013c5002104230000000102000039000000000001042d0000000002000019000000000001042d000000000f0d0019000013cb002104290000000102000039000000000001042d0000000002000019000000000001042d000013cd00000432000013ce0001042e000013cf00010430000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000000000000000000000000000000000000000000000000000000000009c4d535a00000000000000000000000000000000000000000000000000000000e9f18c1600000000000000000000000000000000000000000000000000000000ecf95b8900000000000000000000000000000000000000000000000000000000ecf95b8a00000000000000000000000000000000000000000000000000000000f3385fb600000000000000000000000000000000000000000000000000000000e9f18c1700000000000000000000000000000000000000000000000000000000ec8067c7000000000000000000000000000000000000000000000000000000009c4d535b00000000000000000000000000000000000000000000000000000000bb0fd61000000000000000000000000000000000000000000000000000000000da37f07f000000000000000000000000000000000000000000000000000000005d3826ff000000000000000000000000000000000000000000000000000000005d382700000000000000000000000000000000000000000000000000000000007b510fe80000000000000000000000000000000000000000000000000000000084da1fb400000000000000000000000000000000000000000000000000000000187598a5000000000000000000000000000000000000000000000000000000003cda33510000000000000000000000000000000000000000000000000000000057180981000000000000000000000000000000000000000000000000ffffffffffffffff8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff08c379a00000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c792062792073656c66000000000000000000000000000000000000000000000000000000000000640000008000000000000000004c6314f00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000240000008000000000000000000200000000000000000000000000000000000040000000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00ff1806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b830200000200000000000000000000000000000024000000000000000000000000579952fc0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000004f1e1be000000000000000000000000000000000000000000000000000000000ff00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0001000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004400000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffff000000000000000000000000000000000000000000000000000000010000000000000000ffffffff000000000000000000000000000000000000000000000000000100010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001ffffffe0c2e4ff97000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffbfad7e232e000000000000000000000000000000000000000000000000000000004f766572666c6f770000000000000000000000000000000000000000000000006e6f742063616c6c2074686520636f6e7374727563746f7200000000000000005468652076616c7565206d757374206265207a65726f20696620776520646f2000000000000000000000000000000000000000840000000000000000000000000d4651aa000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000290afdae231a3fc0bbae8b1af63698b0a1d79b21ad17df0342dfb952fe74f8e554686520636f64652068617368206973206e6f74206b6e6f776e0000000000000000000000000000000000000000000000000000000000000000000000010000306395c6000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000696e6700000000000000000000000000000000000000000000000000000000006f6d2073657175656e7469616c20746f20617262697472617279206f726465724974206973206f6e6c7920706f737369626c6520746f206368616e676520667200000000000000000000000000000000000000a40000000000000000000000000200000000000000000000000000000000000020000000000000000000000000c7544194dab38b1652f35439b9b4806d8b71e113f2cf5c1351cb2ecf7c83959a43616e206f6e6c792062652063616c6c656420627920464f5243455f4445504c4f594552206f7220434f4d504c45585f55504752414445525f434f4e54524143540000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000a4000000800000000000000000f3385fb60000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000fffffefb00000000000000000000000000000000000001040000000000000000000000004e487b71000000000000000000000000000000000000000000000000000000006076616c7565602070726f7669646564206973206e6f7420657175616c20746f2074686520636f6d62696e6564206076616c75656073206f66206465706c6f796d656e7473000000000000000000000000000000000000000000000000000000496e617070726f7072696174652063616c6c6572000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffff00004de2e46800000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffc000000000000000000000000000000000000000400000000000000000000000003fb6f4f15ddd4a75588ca934894ad2cdcab25a5012e2515e1783433d0128611a54686973206d6574686f6420726571756972652073797374656d2063616c6c20666c616700000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000008400000080000000000000000000000001000000000000000000000000000000000000000000000000000000006b656363616b3235362072657475726e656420696e76616c69642064617461002020dba91b30cc0006188af794c2fb30dd8520db7e2c088b7fc7c103c00ca494000000000000000000000000000000000000000000000000ffffffffffffff3f63bae3a9951d38e8a3fbb7b70909afc1200610fc5bc55ade242f815974674f23000000000000000000000000000000000000000000000000ffffffffffffff80e03fe17700000000000000000000000000000000000000000000000000000000436f64652068617368206973206e6f6e2d7a65726f00000000000000000000005aa9b6b5000000000000000000000000000000000000000000000000000000004163636f756e74206973206f6363757069656400000000000000000000000000656c20737061636500000000000000000000000000000000000000000000000043616e206e6f74206465706c6f7920636f6e74726163747320696e206b65726e42797465636f6465486173682063616e6e6f74206265207a65726f00000000000000000000000000000000000000000000000000000000000000000000000000c6bfca40024beb29b89193d12075c4c65e1e59922af8b8619fa7a3e6faea8523", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/DefaultAccount.json b/.test-node-subtree/src/deps/contracts/DefaultAccount.json new file mode 100644 index 00000000..8c75a1a0 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/DefaultAccount.json @@ -0,0 +1,547 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "DefaultAccount", + "sourceName": "cache-zk/solpp-generated-contracts/DefaultAccount.sol", + "abi": [ + { + "stateMutability": "payable", + "type": "fallback" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "executeTransaction", + "outputs": [ + { + "internalType": "bytes", + "name": "returnData", + "type": "bytes" + } + ], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "executeTransactionFromOutside", + "outputs": [], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "payForTransaction", + "outputs": [], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "prepareForPaymaster", + "outputs": [], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "_suggestedSignedHash", + "type": "bytes32" + }, + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "validateTransaction", + "outputs": [ + { + "internalType": "bytes4", + "name": "magic", + "type": "bytes4" + } + ], + "stateMutability": "payable", + "type": "function" + }, + { + "stateMutability": "payable", + "type": "receive" + } + ], + "bytecode": "0x0004000000000002000b000000000002000000000301001900000060073002700000050b06700197000300000061035500020000000103550000050b0070019d0000008004000039000000400040043f00000001022001900000002c0000c13d000000040260008c000000340000413d000000000201043b000000e0022002700000050d0320009c000000440000a13d0000050e0320009c000000980000613d0000050f0320009c000000c70000613d000005100220009c000000360000c13d000000040260008a000000200320008c000001290000413d0000000401100370000000000101043b000005130310009c000001290000213d00000000011200490000051402000041000002600310008c000000000300001900000000030240190000051401100197000000000401004b000000000200a019000005140110009c000000000203c019000000000102004b000010340000613d000001290000013d0000000001000416000000000101004b000001290000c13d0000002001000039000001000010044300000120000004430000050c01000041000014280001042e000000000106004b000010340000613d000000000100041200000515011001970000000002000410000000000121004b000010340000c13d0000000001000411000080010110008c000010340000c13d000005620100004100000000001004350000000101000039000000040010043f00000563010000410000142900010430000005110320009c000001130000613d000900000004001d000005120220009c000000360000c13d000000040260008a000000600220008c000001290000413d0000004402100370000000000302043b000005130230009c000001290000213d000000040430003900000000054600490000051402000041000002600750008c000000000700001900000000070240190000051408500197000000000908004b000000000200a019000005140880009c000000000207c019000000000202004b000001290000c13d0000000002000411000080010220008c000010340000c13d000000000200041200000515072001970000000002000410000000000727004b000010340000c13d0000022403300039000000000731034f000000000707043b0000001f0550008a0000051408000041000000000957004b000000000900001900000000090880190000051405500197000005140a700197000000000b5a004b000000000800801900000000055a013f000005140550009c000000000809c019000000000508004b000001290000c13d0000000005470019000000000451034f000000000404043b000005130740009c000001290000213d000000000746004900000020055000390000051408000041000000000975004b000000000900001900000000090820190000051407700197000005140a500197000000000b7a004b000000000800801900000000077a013f000005140770009c000000000809c019000000000708004b000001290000c13d000000030740008c0000024c0000213d0000051901000041000000800010043f0000002001000039000000840010043f0000003a01000039000000a40010043f0000053d01000041000000c40010043f0000053e01000041000000e40010043f0000053b010000410000142900010430000000040260008a000000600220008c000001290000413d0000004402100370000000000302043b000005130230009c000001290000213d000000040230003900000000052600490000051404000041000002600850008c000000000800001900000000080440190000051409500197000000000a09004b000000000400a019000005140990009c000000000408c019000000000404004b000001290000c13d0000000004000411000080010440008c000010340000c13d000000000400041200000515044001970000000008000410000000000484004b000010340000c13d0000004404300039000000000441034f0000012408300039000000000381034f000000000404043b0000051504400197000000000303043b0000051b0930009c000002080000413d0000051901000041000000800010043f0000002001000039000000840010043f0000000801000039000000a40010043f0000052601000041000000c40010043f00000527010000410000142900010430000000040360008a000000600230008c000001290000413d0000004402100370000000000202043b000005130420009c000001290000213d00000000032300490000051404000041000002600530008c000000000500001900000000050440190000051403300197000000000603004b000000000400a019000005140330009c000000000405c019000000000304004b000001290000c13d0000000003000411000080010330008c000010340000c13d000000000300041200000515033001970000000004000410000000000343004b000010340000c13d000000a403200039000000000331034f0000006402200039000000000121034f000000000101043b000000000203043b000000000302004b000001f00000c13d00000000040004150000000b0440008a00000020044000c90000000001000414000b00000000001d000900000004001d0000050b020000410000050b0310009c0000000001028019000000c0011002100000800102000039142714130000040f0000000903000029000300000001035500000060011002700001050b0010019d000000050130027000000001012001950000000101200190000010340000c13d000000400100043d000000640210003900000517030000410000000000320435000000440210003900000518030000410000000000320435000000240210003900000025030000390000000000320435000005190200004100000000002104350000000402100039000000200300003900000000003204350000050b020000410000050b0310009c000000000102801900000040011002100000051a011001c70000142900010430000000040260008a000000600220008c000001290000413d0000004402100370000000000202043b000900000002001d000005130220009c000001290000213d0000000902000029000800040020003d000000080260006a0000051403000041000002600420008c000000000400001900000000040340190000051402200197000000000502004b000000000300a019000005140220009c000000000304c019000000000203004b0000012b0000613d000000000100001900001429000104300000002402100370000000000202043b000700000002001d0000000002000411000080010220008c000010340000c13d000000000200041200000515022001970000000003000410000600000003001d000000000232004b000010340000c13d00000000020004140000053f03000041000000a00030043f0000000903000029000501040030003d0000000501100360000000000101043b000000a40010043f0000002401000039000000800010043f000000e001000039000000400010043f000000c001200210000005220110019700000540011001c700008003020000390000000003000019000000000400001900000000050000190000000006000019142714130000040f0003000000010355000000000301001900000060033002700001050b0030019d0000050b083001970000003f038000390000054104300197000000400600043d0000000003640019000000000443004b00000000040000190000000104004039000005130530009c000013490000213d0000000104400190000013490000c13d000000400030043f000000000786043600000002030003670000000004000031000000000543034f0000001f0980003900000005099002720000016d0000613d000000000a000019000000050ba00210000000000cb70019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000001650000413d000000000900004b0000016f0000613d0000001f0980018f00000005088002720000017b0000613d000000000a000019000000050ba00210000000000cb70019000000000bb1034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b000001730000413d000000000a09004b0000018a0000613d0000000508800210000000000181034f00000000088700190000000309900210000000000a080433000000000a9a01cf000000000a9a022f000000000101043b0000010009900089000000000191022f00000000019101cf0000000001a1019f00000000001804350000000101200190000002420000613d000000070100006b0000120f0000c13d0000000501000029000001000110008a000000000113034f000000000101043b000000010210008c0000025f0000213d000000000201004b000002ae0000613d000000010110008c0000029c0000c13d000005420100004100000000001004390000050b0100004100000000020004140000050b0320009c0000000002018019000000c00120021000000543011001c70000800b02000039142714180000040f00000001022001900000124f0000613d000000400300043d000000000401043b000000800140008c000004490000413d0000008001400270000005460240009c000000000104a019000005460240009c0000000002000019000000100200203900000008052001bf000005130610009c000000000502a0190000004002100270000005130610009c000000000201a01900000004015001bf0000050b0620009c000000000105a01900000020062002700000050b0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000005130610009c000013490000213d0000000102200190000013490000c13d000000400010043f000000020150003900000000061304360000000201000367000000000200003100000021075000390000000507700272000001de0000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000001d60000413d000000000700004b000001e00000613d0000000007030433000000000707004b000009cb0000613d00000000070604330000054507700197000000f808500210000000000778019f000005470770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c000000000400201900000021053000390000045c0000013d00000000431200a900000000422300d9000000000112004b0000122b0000c13d00000000040004150000000a0440008a00000020044000c90000000001000414000a00000000001d000000000203004b000000ef0000613d0000050b020000410000050b0410009c0000000001028019000000c00110021000000516011001c7000080090200003900008001040000390000000005000019142714130000040f00000000030004150000000a0330008a00000020033000c9000000f70000013d000000a008800039000000000881034f000000000808043b0000001f0550008a0000051409000041000000000a58004b000000000a000019000000000a0980190000051405500197000005140b800197000000000c5b004b000000000900801900000000055b013f000005140550009c00000000090ac019000000000509004b000001290000c13d0000000002280019000000000521034f000000000805043b000005130580009c000001290000213d000000000586004900000020092000390000051402000041000000000a59004b000000000a000019000000000a0220190000051405500197000005140b900197000000000c5b004b000000000200801900000000055b013f000005140550009c00000000020ac019000000000202004b000001290000c13d00000000020004140000050b0520009c000000bd0000213d000080060540008c0000000005000019000003de0000c13d000000040580008c0000000005000019000003de0000413d000000000a91034f0000000105000039000000000a0a043b0000051c0aa001970000051d0ba0009c000003da0000213d000005200ba0009c000003de0000613d000005210aa0009c000003de0000613d0000000005000019000003de0000013d00000000010604330000050b020000410000050b0310009c00000000010280190000050b0370009c000000000702801900000040027002100000006001100210000000000121019f0000142900010430000000000751034f000000000707043b0000051c07700197000005280870009c000010340000613d000005290770009c000003540000c13d000000430440008c000003bb0000213d0000051901000041000000800010043f0000002001000039000000840010043f0000004001000039000000a40010043f0000053901000041000000c40010043f0000053a01000041000000950000013d000000020210008c000002fc0000613d000000710110008c0000029c0000c13d0000000902000029000001c401200039000000000113034f0000000002240049000000230220008a000000000101043b0000051405000041000000000621004b0000000006000019000000000605801900000514022001970000051407100197000000000827004b0000000005008019000000000227013f000005140220009c000000000506c019000000000205004b000001290000c13d0000000801100029000000000213034f000000000202043b000005130520009c000001290000213d000000000524004900000020011000390000051406000041000000000751004b0000000007000019000000000706201900000514055001970000051408100197000000000958004b0000000006008019000000000558013f000005140550009c000000000607c019000000000506004b000001290000c13d00000000050004140000000006120019000000000226004b0000000002000019000000010200403900000001022001900000122b0000c13d000000000264004b0000122b0000413d0000054d0250009c000006970000413d000000400100043d00000044021000390000052603000041000000000032043500000024021000390000000803000039000002a20000013d000000400100043d000000440210003900000564030000410000000000320435000000240210003900000017030000390000000000320435000005190200004100000000002104350000000402100039000000200300003900000000003204350000050b020000410000050b0310009c0000000001028019000000400110021000000538011001c700001429000104300000000501300360000000400200043d000700000002001d000000000101043b000000800210008c0000035c0000413d0000008002100270000005460610009c000000000201a019000005460610009c0000000006000019000000100600203900000008076001bf000005130820009c000000000706a0190000004006200270000005130820009c000000000602a01900000004087001bf0000050b0260009c000000000807a01900000020076002700000050b0260009c000000000706a01900000002028001bf0000ffff0670008c000000000208a0190000001006700270000000000607a019000000ff0660008c0000000102202039000000200600008a0000004107200039000000000667016f0000000706600029000000070760006c00000000070000190000000107004039000005130860009c000013490000213d0000000107700190000013490000c13d000000400060043f00000002062000390000000707000029000000000667043600000021072000390000000507700272000002e80000613d00000000080000190000000509800210000000000a960019000000000995034f000000000909043b00000000009a04350000000108800039000000000978004b000002e00000413d000000000700004b000002ea0000613d00000007070000290000000007070433000000000707004b000009cb0000613d00000000070604330000054507700197000000f808200210000000000778019f000005470770004100000000007604350000000302200210000000f80220008900000000012101cf000000ff0220008c0000000001002019000000070200002900000021022000390000036e0000013d000005420100004100000000001004390000050b0100004100000000020004140000050b0320009c0000000002018019000000c00120021000000543011001c70000800b02000039142714180000040f00000001022001900000124f0000613d000000400300043d000000000401043b000000800140008c000004a80000413d0000008001400270000005460240009c000000000104a019000005460240009c0000000002000019000000100200203900000008052001bf000005130610009c000000000502a0190000004002100270000005130610009c000000000201a01900000004015001bf0000050b0620009c000000000105a01900000020062002700000050b0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000005130610009c000013490000213d0000000102200190000013490000c13d000000400010043f000000020150003900000000061304360000000201000367000000000200003100000021075000390000000507700272000003420000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b0000033a0000413d000000000700004b000003440000613d0000000007030433000000000707004b000009cb0000613d00000000070604330000054507700197000000f808500210000000000778019f000005470770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c00000000040020190000002105300039000004bb0000013d0000051901000041000000800010043f0000002001000039000000840010043f0000001a01000039000000a40010043f0000053c01000041000000c40000013d0000000702000029000005440220009c000013490000213d00000007060000290000004002600039000000400020043f000000010200003a00000000022604360000000006500350000000000606043b0000000000620435000009cb0000613d000000f8071002100000051408000041000000000101004b000000000807c0190000054501600197000000000181019f0000000000120435000000400100043d0000000502000029000000600220008a000000000623034f000000000606043b000000800760008c000005070000413d0000008007600270000005460860009c000000000706a019000005460860009c0000000008000019000000100800203900000008098001bf000005130a70009c000000000908a0190000004008700270000005130a70009c000000000807a019000000040a9001bf0000050b0780009c000000000a09a01900000020098002700000050b0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008810019000000000918004b00000000090000190000000109004039000005130a80009c000013490000213d0000000109900190000013490000c13d000000400080043f0000000208700039000000000881043600000021097000390000000509900272000003a90000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000003a10000413d000000000900004b000003ab0000613d0000000009010433000000000909004b000009cb0000613d00000000090804330000054509900197000000f80a70021000000000099a019f000005470990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c00000000060020190000002107100039000005170000013d0000000404500039000000000541034f000000000505043b000800000005001d000005150550009c000001290000213d000001400330008a000000000331034f0000002004400039000000000441034f000000000404043b000700000004001d000000000303043b0000052a04000041000000800040043f0000051502200197000500000002001d000000840020043f0000051502300197000600000002001d000000a40020043f00000000020004140000000803000029000000040330008c000005630000c13d000000000161034f0000000103000031000000200230008c000000000403001900000020040080390000058f0000013d0000051e0ba0009c000003de0000613d0000051f0aa0009c000000000500c019000000000a9800190000000006a6004b0000000006000019000000010600403900000000088a004b00000001066041bf0000050b08900197000000000181034f000000000803004b000003f70000c13d00000001036001900000122b0000c13d00000523030000410000052406000041000000000505004b000000000603c019000000c0022002100000052202200197000000000226019f0000000003a700490000050b0330019700000000013103df00000000012103af0000000002040019000004020000013d00000001066001900000122b0000c13d0000000006a700490000050b0660019700000000016103df000000c002200210000005220220019700000523022001c700000000012103af000080090200003900000000060000191427141d0000040f0003000000010355000000000301001900000060033002700001050b0030019d0000050b0330019700000001022001900000042e0000613d000000400200043d000005250120009c000013490000213d0000002001200039000000400010043f00000000000204350000002003000039000000400100043d0000000004310436000000000302043300000000003404350000004004100039000000000503004b000004200000613d000000000500001900000000064500190000002005500039000000000725001900000000070704330000000000760435000000000635004b000004190000413d000000000243001900000000000204350000005f02300039000000200300008a000000000232016f0000050b030000410000050b0420009c00000000020380190000050b0410009c000000000103801900000040011002100000006002200210000000000112019f000014280001042e0000001f0430018f0000000502300272000004390000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000004320000413d000000000504004b000004470000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000142900010430000005440130009c000013490000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000201000367000000000621034f0000000006600350000000000606043b0000000000650435000009cb0000613d000000f8074002100000051408000041000000000404004b000000000807c0190000054504600197000000000484019f00000000004504350000000505100360000000400400043d000000000505043b000000800650008c000005b60000413d0000008006500270000005460750009c000000000605a019000005460750009c0000000007000019000000100700203900000008087001bf000005130960009c000000000807a0190000004007600270000005130960009c000000000706a01900000004098001bf0000050b0670009c000000000908a01900000020087002700000050b0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007740019000000000847004b00000000080000190000000108004039000005130970009c000013490000213d0000000108800190000013490000c13d000000400070043f0000000207600039000000000774043600000021086000390000000508800272000004960000613d000000000921034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b0000048e0000413d000000000800004b000004980000613d0000000008040433000000000808004b000009cb0000613d00000000080704330000054508800197000000f809600210000000000889019f000005470880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106400039000005c70000013d000005440130009c000013490000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000201000367000000000621034f0000000006600350000000000606043b0000000000650435000009cb0000613d000000f8074002100000051408000041000000000404004b000000000807c0190000054504600197000000000484019f00000000004504350000000505100360000000400400043d000000000505043b000000800650008c000006150000413d0000008006500270000005460750009c000000000605a019000005460750009c0000000007000019000000100700203900000008087001bf000005130960009c000000000807a0190000004007600270000005130960009c000000000706a01900000004098001bf0000050b0670009c000000000908a01900000020087002700000050b0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007740019000000000847004b00000000080000190000000108004039000005130970009c000013490000213d0000000108800190000013490000c13d000000400070043f0000000207600039000000000774043600000021086000390000000508800272000004f50000613d000000000921034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b000004ed0000413d000000000800004b000004f70000613d0000000008040433000000000808004b000009cb0000613d00000000080704330000054508800197000000f809600210000000000889019f000005470880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106400039000006260000013d000005440710009c000013490000213d0000004007100039000000400070043f000000010700003a00000000077104360000000008500350000000000808043b0000000000870435000009cb0000613d000000f809600210000005140a000041000000000606004b000000000a09c01900000545068001970000000006a6019f0000000000670435000000400220008a000000000623034f000000400200043d000000000606043b000000800760008c0000086e0000413d0000008007600270000005460860009c000000000706a019000005460860009c0000000008000019000000100800203900000008098001bf000005130a70009c000000000908a0190000004008700270000005130a70009c000000000807a019000000040a9001bf0000050b0780009c000000000a09a01900000020098002700000050b0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008820019000000000928004b00000000090000190000000109004039000005130a80009c000013490000213d0000000109900190000013490000c13d000000400080043f0000000208700039000000000882043600000021097000390000000509900272000005510000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000005490000413d000000000900004b000005530000613d0000000009020433000000000909004b000009cb0000613d00000000090804330000054509900197000000f80a70021000000000099a019f000005470990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c000000000600201900000021072000390000087e0000013d0000050b010000410000050b0320009c0000000002018019000000c0012002100000052b011001c70000000802000029142714180000040f000000000301001900000060033002700000050b03300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000057c0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000005740000413d000000000705004b0000058b0000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f00030000000103550000000102200190000006740000613d0000001f02400039000000600520018f00000080025001bf000000400020043f000000200430008c000001290000413d000000800400043d000000070440006c000010340000813d000000a0045000390000052c060000410000000000640435000000a40650003900000006070000290000000000760435000000c40650003900000000000604350000004406000039000100000006001d00000000006204350000014006500039000000400060043f00000120065000390000052d07000041000000000076043500000100065001bf0000002005000039000300000005001d000200000006001d0000000000560435000000000502043300000000020004140000000806000029000000040660008c0000090c0000c13d0000000102000039000005130430009c000013490000213d000009200000013d000005440640009c000013490000213d0000004006400039000000400060043f000000000721034f000000010600003a00000000066404360000000007700350000000000707043b0000000000760435000009cb0000613d000000f8085002100000051409000041000000000505004b000000000908c0190000054505700197000000000595019f0000000000560435000000400500043d0000000506000029000000600660008a000000000761034f000000000707043b000000800870008c000009620000413d0000008008700270000005460970009c000000000807a019000005460970009c00000000090000190000001009002039000000080a9001bf000005130b80009c000000000a09a0190000004009800270000005130b80009c000000000908a019000000040ba001bf0000050b0890009c000000000b0aa019000000200a9002700000050b0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000005130b90009c000013490000213d000000010aa00190000013490000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa00272000006030000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000005fb0000413d000000000a00004b000006050000613d000000000a050433000000000a0a004b000009cb0000613d000000000a090433000005450aa00197000000f80b800210000000000aab019f000005470aa000410000000000a904350000000308800210000000f80880008900000000078701cf000000ff0880008c00000000070020190000002108500039000009730000013d000005440640009c000013490000213d0000004006400039000000400060043f000000000721034f000000010600003a00000000066404360000000007700350000000000707043b0000000000760435000009cb0000613d000000f8085002100000051409000041000000000505004b000000000908c0190000054505700197000000000595019f0000000000560435000000400500043d0000000506000029000000400760008a000000000671034f000000000606043b000000800860008c000009c00000413d0000008008600270000005460960009c000000000806a019000005460960009c00000000090000190000001009002039000000080a9001bf000005130b80009c000000000a09a0190000004009800270000005130b80009c000000000908a019000000040ba001bf0000050b0890009c000000000b0aa019000000200a9002700000050b0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000005130b90009c000013490000213d000000010aa00190000013490000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa00272000006620000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b0000065a0000413d000000000a00004b000006640000613d000000000a050433000000000a0a004b000009cb0000613d000000000a090433000005450aa00197000000f80b800210000000000aab019f000005470aa000410000000000a904350000000308800210000000f80880008900000000068601cf000000ff0880008c0000000006002019000000210850003900000a8f0000013d000000400200043d0000001f0430018f0000000505300272000006810000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000006790000413d000000000604004b000006900000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f00000000001504350000050b010000410000050b0420009c000000000201801900000040012002100000006002300210000000000121019f00001429000104300000050b01100197000000000113034f00000000026400490000050b0220019700000000012103df000000c002500210000005220220019700000524022001c700000000012103af0000801002000039142714220000040f000000000301001900000060033002700001050b0030019d0000050b0530019700030000000103550000000102200190000009cf0000613d0000003f025000390000054102200197000000400600043d0000000002260019000000000362004b00000000030000190000000103004039000005130420009c000013490000213d0000000103300190000013490000c13d000000400020043f0000000004560436000000020200036700000000030000310000001f075000390000000507700272000006c50000613d000000000832034f0000000009000019000000050a900210000000000ba40019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000006bd0000413d000000000700004b000006c70000613d0000001f0750018f0000000505500272000006d30000613d00000000080000190000000509800210000000000a940019000000000991034f000000000909043b00000000009a04350000000108800039000000000958004b000006cb0000413d000000000807004b000006e20000613d0000000505500210000000000151034f00000000055400190000000307700210000000000805043300000000087801cf000000000878022f000000000101043b0000010007700089000000000171022f00000000017101cf000000000181019f00000000001504350000000001060433000000200110008c00000a110000c13d00000009060000290000000001630049000000230510008a000702040060003d0000000701200360000000000101043b0000051406000041000000000751004b0000000007000019000000000706801900000514055001970000051408100197000000000958004b0000000006008019000000000558013f000005140550009c000000000607c019000000000506004b000001290000c13d0000000004040433000400000004001d0000000801100029000000000412034f000000000504043b000005130450009c000001290000213d0000000504500210000000000343004900000020061000390000051401000041000000000736004b0000000007000019000000000701201900000514033001970000051408600197000000000938004b0000000001008019000000000338013f000005140330009c000000000107c019000000000101004b000001290000c13d000000400100043d00000020031000390000054e055001980000071d0000613d000000000262034f000000000600001900000005076002100000000008730019000000000772034f000000000707043b00000000007804350000000106600039000000000756004b000007150000413d000000000200004b0000071f0000613d00000000004104350000003f02400039000000200400008a000000000242016f0000000002210019000000000412004b00000000040000190000000104004039000005130520009c000013490000213d0000000104400190000013490000c13d000000400020043f0000050b020000410000050b0430009c0000000003028019000000400330021000000000010104330000050b0410009c00000000010280190000006001100210000000000131019f00000000030004140000050b0430009c0000000003028019000000c002300210000000000112019f00000516011001c70000801002000039142714180000040f0000000102200190000001290000613d0000000002000031000000090320006a000000230530008a000000070300002900000020043000390000000203000367000000000443034f000000000404043b0000051406000041000000000754004b0000000007000019000000000706801900000514055001970000051408400197000000000958004b0000000006008019000000000558013f000005140550009c000000000607c019000000000101043b000700000001001d000000000106004b000001290000c13d0000000801400029000000000413034f000000000404043b000005130540009c000001290000213d000000000542004900000020011000390000051406000041000000000751004b0000000007000019000000000706201900000514055001970000051408100197000000000958004b0000000006008019000000000558013f000005140550009c000000000607c019000000000506004b000001290000c13d00000000050004140000000006140019000000000446004b0000000004000019000000010400403900000001044001900000122b0000c13d000000000462004b0000122b0000413d0000050b0450009c000002950000213d0000050b01100197000000000113034f00000000026200490000050b0220019700000000012103df000000c002500210000005220220019700000524022001c700000000012103af0000801002000039142714220000040f000000000301001900000060033002700001050b0030019d0000050b03300197000300000001035500000001022001900000113c0000613d0000003f023000390000054102200197000000400500043d0000000002250019000000000452004b00000000040000190000000104004039000005130620009c000013490000213d0000000104400190000013490000c13d000000400020043f000000000235043600000002040003670000001f063000390000000506600272000007a20000613d000000000740036800000000080000190000000509800210000000000a920019000000000997034f000000000909043b00000000009a04350000000108800039000000000968004b0000079a0000413d000000000600004b000007a40000613d0000001f0630018f0000000503300272000007b00000613d000000000700001900000005087002100000000009820019000000000881034f000000000808043b00000000008904350000000107700039000000000837004b000007a80000413d000000000706004b000007bf0000613d0000000503300210000000000131034f00000000033200190000000306600210000000000703043300000000076701cf000000000767022f000000000101043b0000010006600089000000000161022f00000000016101cf000000000171019f00000000001304350000000001050433000000200110008c00000a110000c13d000000090c0000290000006401c00039000000000114034f0000004403c00039000000000534034f0000002403c00039000000000634034f0000012403c00039000000000734034f0000000508400360000000e403c00039000000000934034f000000c403c00039000000000a34034f000000a403c00039000000000b34034f0000008403c00039000000000c34034f0000000803400360000000000303043b000000000406043b000000000505043b000000000601043b000000000c0c043b000000000b0b043b000000000a0a043b000000000909043b000000000808043b000000000707043b0000000002020433000000400100043d000001c00d10003900000000002d0435000001a002100039000000070d0000290000000000d204350000018002100039000000040d0000290000000000d2043500000160021000390000000000720435000001400210003900000000008204350000012002100039000000000092043500000100021000390000000000a20435000000e0021000390000000000b20435000000c0021000390000000000c20435000000a0021000390000000000620435000000800210003900000000005204350000006002100039000000000042043500000040021000390000000000320435000000200210003900000550030000410000000000320435000001c0030000390000000000310435000005510310009c000013490000213d000001e003100039000000400030043f0000050b040000410000050b0320009c0000000002048019000000400220021000000000010104330000050b0310009c00000000010480190000006001100210000000000121019f00000000020004140000050b0320009c0000000002048019000000c002200210000000000112019f00000516011001c70000801002000039142714180000040f0000000102200190000001290000613d000000000101043b000500000001001d000000400100043d000700000001001d0000054201000041000000000010043900000000010004140000050b0210009c0000050b01008041000000c00110021000000543011001c70000800b02000039142714180000040f00000001022001900000124f0000613d00000007040000290000002002400039000000000101043b000005520300004100000000003204350000008003400039000000000013043500000060014000390000055303000041000000000031043500000040014000390000055403000041000000000031043500000080010000390000000000140435000005550140009c000013490000213d0000000704000029000000a001400039000000400010043f0000050b010000410000050b0320009c0000000002018019000000400220021000000000030404330000050b0430009c00000000030180190000006003300210000000000223019f00000000030004140000050b0430009c0000000003018019000000c001300210000000000121019f00000516011001c70000801002000039142714180000040f0000000102200190000001290000613d000000000301043b000000400100043d0000004202100039000000050400002900000000004204350000002002100039000005560400004100000000004204350000002204100039000000000034043500000042030000390000000000310435000005330310009c000013490000213d0000008003100039000000400030043f0000050b030000410000050b0420009c0000000002038019000000400220021000000000010104330000050b0410009c00000000010380190000006001100210000000000121019f00000000020004140000050b0420009c0000000002038019000000c002200210000000000112019f000012070000013d000005440720009c000013490000213d0000004007200039000000400070043f000000010700003a00000000077204360000000008500350000000000808043b0000000000870435000009cb0000613d000000f809600210000005140a000041000000000606004b000000000a09c01900000545068001970000000006a6019f0000000000670435000000400600043d000500000006001d00000020076000390000000006010433000000000806004b0000088d0000613d000000000800001900000000097800190000002008800039000000000a180019000000000a0a04330000000000a90435000000000968004b000008860000413d000000000176001900000000000104350000000007020433000000000807004b0000089a0000613d000000000800001900000000091800190000002008800039000000000a280019000000000a0a04330000000000a90435000000000978004b000008930000413d000000000117001900000000000104350000000001670019000000050600002900000000001604350000003f011000390001002000000092000000010110017f0000000002610019000000000112004b00000000010000190000000101004039000400000002001d000005130220009c000013490000213d0000000101100190000013490000c13d0000000401000029000000400010043f000005440110009c000013490000213d00000009070000290000004401700039000000000113034f000000000101043b00000004080000290000004002800039000000400020043f000000200280003900000548060000410000000000620435000000150200003900000000002804350000006001100210000000210280003900000000001204350000012401700039000000000213034f000000400600043d000300000006001d000000000202043b000000800620008c00000b3b0000413d0000008006200270000005460720009c000000000602a019000005460720009c0000000007000019000000100700203900000008087001bf000005130960009c000000000807a0190000004007600270000005130960009c000000000706a01900000004098001bf0000050b0670009c000000000908a01900000020087002700000050b0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c00000001066020390000004107600039000000010770017f0000000307700029000000030870006c00000000080000190000000108004039000005130970009c000013490000213d0000000108800190000013490000c13d000000400070043f00000002076000390000000308000029000000000778043600000021086000390000000508800272000008f80000613d0000000009000019000000050a900210000000000ba70019000000000aa5034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b000008f00000413d000000000800004b000008fa0000613d00000003080000290000000008080433000000000808004b000009cb0000613d00000000080704330000054508800197000000f809600210000000000889019f000005470880004100000000008704350000000306600210000000f80660008900000000026201cf000000ff0660008c00000000020020190000000306000029000000210660003900000b4d0000013d0000050b010000410000050b0350009c000000000501801900000060035002100000004004400210000000000343019f0000050b0420009c0000000002018019000000c001200210000000000113019f0000000802000029142714130000040f000400600000003d000000010220018f0003000000010355000000000301001900000060033002700001050b0030019d0000050b033001980000094c0000613d0000003f04300039000000200500008a000000000454016f000000400500043d0000000004450019000400000005001d000000000554004b00000000050000190000000105004039000005130640009c000013490000213d0000000105500190000013490000c13d000000400040043f0000001f0430018f0000000405000029000000000835043600000005033002720000093c0000613d000000000500001900000005065002100000000007680019000000000661034f000000000606043b00000000006704350000000105500039000000000635004b000009340000413d000900000008001d000000000504004b0000094c0000613d0000000503300210000000000131034f00000009033000290000000304400210000000000503043300000000054501cf000000000545022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000013043500000004010000290000000001010433000000000202004b000009ea0000c13d000000000201004b00000a090000c13d000000400300043d000900000003001d0000051901000041000000000013043500000004013000390000000302000029000000000021043500000024023000390000000201000029142713ff0000040f000000090400002900000000014100490000050b020000410000050b0310009c000000000102801900000a0d0000013d000005440850009c000013490000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b0000000000980435000009cb0000613d000000f80a700210000005140b000041000000000707004b000000000b0ac01900000545079001970000000007b7019f0000000000780435000000400700043d000000400660008a000000000861034f000000000808043b000000800980008c00000a180000413d0000008009800270000005460a80009c000000000908a019000005460a80009c000000000a000019000000100a002039000000080ba001bf000005130c90009c000000000b0aa019000000400a900270000005130c90009c000000000a09a019000000040cb001bf0000050b09a0009c000000000c0ba019000000200ba002700000050b09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa70019000000000b7a004b000000000b000019000000010b004039000005130ca0009c000013490000213d000000010bb00190000013490000c13d0000004000a0043f000000020a900039000000000aa70436000000210b900039000000050bb00272000009ae0000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b000009a60000413d000000000b00004b000009b00000613d000000000b070433000000000b0b004b000009cb0000613d000000000b0a0433000005450bb00197000000f80c900210000000000bbc019f000005470bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c0000000008002019000000210970003900000a290000013d000005440850009c000013490000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b000000000098043500000a890000c13d000005620100004100000000001004350000003201000039000000410000013d0000001f0350018f0000000502500272000009da0000613d00000000040000190000000506400210000000000761034f000000000707043b00000000007604350000000104400039000000000624004b000009d30000413d000000000403004b000009e80000613d00000003033002100000000502200210000000000402043300000000043401cf000000000434022f000000000121034f000000000101043b0000010003300089000000000131022f00000000013101cf000000000141019f000000000012043500000060015002100000142900010430000000000201004b00000b970000c13d0000052e010000410000000000100439000000080100002900000004001004430000050b0100004100000000020004140000050b0320009c0000000002018019000000c0012002100000052f011001c70000800202000039142714180000040f00000001022001900000124f0000613d000000000101043b000000000101004b00000b930000c13d000000400100043d00000044021000390000053703000041000000000032043500000024021000390000001d0300003900000000003204350000051902000041000000000021043500000004021000390000000303000029000002a70000013d0000050b020000410000050b0310009c000000000102801900000009040000290000050b0340009c00000000040280190000004002400210000002490000013d000000400100043d00000044021000390000054f03000041000000000032043500000024021000390000001f03000039000002a20000013d000005440970009c000013490000213d0000004009700039000000400090043f000000000a21034f000000010900003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000009cb0000613d000000f80b800210000005140c000041000000000808004b000000000c0bc0190000054508a001970000000008c8019f0000000000890435000000400900043d000005440890009c000013490000213d000000200860008a000000000881034f000000000808043b000000400a9000390000004000a0043f000000200a900039000005480b0000410000000000ba0435000000150a0000390000000000a904350000006008800210000000210a90003900000000008a0435000000c006600039000000000661034f000000400800043d000000000606043b000700000006001d000000800a60008c00000ca80000413d0000000706000029000000800a600270000005460b60009c000000000a06a019000005460b60009c000000000b000019000000100b002039000000080cb001bf000005130da0009c000000000c0ba019000000400ba00270000005130da0009c000000000b0aa019000000040dc001bf0000050b0ab0009c000000000d0ca019000000200cb002700000050b0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000005130db0009c000013490000213d000000010cc00190000013490000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc0027200000a760000613d000000000d21034f000000000e000019000000050fe002100000000006fb0019000000000ffd034f000000000f0f043b0000000000f60435000000010ee000390000000006ce004b00000a6e0000413d000000000600004b00000a780000613d0000000006080433000000000606004b000009cb0000613d00000000060b04330000054506600197000000f80ca0021000000000066c019f000005470660004100000000006b04350000000306a00210000000f806600089000000070a6001ef000000ff0660008c000000000a00201900000021068000390000000000a6043500000cbb0000013d000000f80a600210000005140b000041000000000606004b000000000b0ac01900000545069001970000000006b6019f0000000000680435000000400600043d000000200770008a000000000871034f000000000808043b000000800980008c00000adc0000413d0000008009800270000005460a80009c000000000908a019000005460a80009c000000000a000019000000100a002039000000080ba001bf000005130c90009c000000000b0aa019000000400a900270000005130c90009c000000000a09a019000000040cb001bf0000050b09a0009c000000000c0ba019000000200ba002700000050b09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa60019000000000b6a004b000000000b000019000000010b004039000005130ca0009c000013490000213d000000010bb00190000013490000c13d0000004000a0043f000000020a900039000000000aa60436000000210b900039000000050bb0027200000aca0000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b00000ac20000413d000000000b00004b00000acc0000613d000000000b060433000000000b0b004b000009cb0000613d000000000b0a0433000005450bb00197000000f80c900210000000000bbc019f000005470bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c0000000008002019000000210960003900000aed0000013d000005440960009c000013490000213d0000004009600039000000400090043f000000000a21034f000000010900003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000009cb0000613d000000f80b800210000005140c000041000000000808004b000000000c0bc0190000054508a001970000000008c8019f0000000000890435000000400800043d00070040007000920000000709100360000000000909043b000000800a90008c00000bcd0000413d000000800a900270000005460b90009c000000000a09a019000005460b90009c000000000b000019000000100b002039000000080cb001bf000005130da0009c000000000c0ba019000000400ba00270000005130da0009c000000000b0aa019000000040dc001bf0000050b0ab0009c000000000d0ca019000000200cb002700000050b0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000005130db0009c000013490000213d000000010cc00190000013490000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc0027200000b280000613d000000000d21034f000000000e000019000000050fe002100000000007fb0019000000000ffd034f000000000f0f043b0000000000f70435000000010ee000390000000007ce004b00000b200000413d000000000700004b00000b2a0000613d0000000007080433000000000707004b000009cb0000613d00000000070b04330000054507700197000000f80ca0021000000000077c019f000005470770004100000000007b04350000000307a00210000000f80770008900000000097901cf000000ff0770008c00000000090020190000002107800039000000000097043500000bdf0000013d0000000306000029000005440660009c000013490000213d00000003070000290000004006700039000000400060043f000000010600003a00000000066704360000000007500350000000000707043b0000000000760435000009cb0000613d000000f8082002100000051409000041000000000202004b000000000908c0190000054502700197000000000292019f0000000000260435000000080640006a000000a001100039000000000213034f000000000202043b0000001f0660008a000005140760019700000514082001970000051409000041000000000a78004b000000000a000019000000000a094019000000000778013f000000000862004b0000000009004019000005140770009c000000000a09c01900000000070a004b000001290000c13d0000000808200029000000000783034f000000000707043b000005130970009c000001290000213d00000000097400490000002008800039000005140a000041000000000b98004b000000000b000019000000000b0a20190000051409900197000005140c800197000000000d9c004b000000000a00801900000000099c013f000005140990009c000000000a0bc01900000000090a004b000001290000c13d000000010970008c00000e600000c13d000000000583034f000000000505043b000000010700008a0000051408000041000000000775004b000000000700001900000000070820190000051405500197000005140950009c00000000080080190000051405500167000005140550009c000000000807c019000200600000003d000000000508004b00000e9c0000c13d000000400500043d000200000005001d000005440550009c000013490000213d00000002080000290000004005800039000000400050043f0000002005800039000005470700004100000000007504350000000105000039000000000058043500000e9c0000013d00000004010000290000000001010433000000000201004b00000bba0000613d0000051402000041000000200310008c000000000300001900000000030240190000051401100197000000000401004b000000000200a019000005140110009c000000000203c019000000000102004b000001290000c13d00000009010000290000000001010433000000000201004b0000000002000019000000010200c039000000000221004b000001290000c13d000000000101004b00000bba0000c13d000000400100043d00000064021000390000053503000041000000000032043500000044021000390000053603000041000000000032043500000024021000390000002a03000039000000000032043500000519020000410000000000210435000000040210003900000003030000290000010c0000013d000000400300043d0000002401300039000000060200002900000000002104350000052a010000410000000000130435000900000003001d00000004013000390000000502000029000000000021043500000000010004140000000802000029000000040220008c00000c420000c13d0000000103000031000000200130008c0000000004030019000000200400803900000c740000013d000005440780009c000013490000213d0000004007800039000000400070043f000000000721034f000000010a00003a000000000aa804360000000007700350000000000b07043b0000000000ba0435000009cb0000613d000000f807900210000005140c000041000000000909004b000000000c07c0190000054507b001970000000007c7019f00000000007a0435000000400a00043d0000054407a0009c000013490000213d000000070c0000290000002007c0008a000000000771034f000000000707043b0000004009a00039000000400090043f0000002009a00039000005480b0000410000000000b90435000000150900003900000000009a043500000060077002100000002109a000390000000000790435000000c007c00039000000000771034f000000400900043d000000000707043b000700000007001d000000800b70008c00000d850000413d0000000707000029000000800b700270000005460c70009c000000000b07a019000005460c70009c000000000c000019000000100c002039000000080dc001bf000005130eb0009c000000000d0ca019000000400cb00270000005130eb0009c000000000c0ba019000000040ed001bf0000050b0bc0009c000000000e0da019000000200dc002700000050b0bc0009c000000000d0ca0190000000207e001bf0000ffff0cd0008c00000000070ea019000000100cd00270000000000c0da019000000ff0cc0008c0000000107702039000000200c00008a000500000007001d000000410d700039000000000ccd016f000000000cc90019000000000d9c004b000000000d000019000000010d004039000005130ec0009c000013490000213d000000010dd00190000013490000c13d0000004000c0043f0000000507000029000000020c700039000000000cc90436000000210d700039000000050dd0027200000c2e0000613d000000000e21034f000000000f0000190000000507f00210000000000b7c001900000000077e034f000000000707043b00000000007b0435000000010ff000390000000007df004b00000c260000413d000000000700004b00000c300000613d0000000007090433000000000707004b000009cb0000613d00000000070c04330000054507700197000000050d000029000000f80bd0021000000000077b019f000005470770004100000000007c04350000000307d00210000000f807700089000000070b7001ef000000ff0770008c000000000b00201900000021079000390000000000b7043500000d980000013d0000050b020000410000050b0310009c000000000102801900000009040000290000050b0340009c00000000020440190000004002200210000000c001100210000000000121019f00000530011001c70000000802000029142714180000040f000000090a000029000000000301001900000060033002700000050b03300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000c610000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000c590000413d000000000705004b00000c700000613d0000000506600210000000000761034f00000009066000290000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f0003000000010355000000010220019000000d680000613d0000001f01400039000000600210018f0000000901200029000000000221004b00000000020000190000000102004039000005130410009c000013490000213d0000000102200190000013490000c13d000000400010043f000000200230008c000001290000413d0000004404100039000000240510003900000009020000290000000002020433000000000202004b00000e540000c13d00000020021000390000052c060000410000000000620435000000060600002900000000006504350000000705000029000000000054043500000001040000290000000000410435000005330410009c000013490000213d0000008004100039000900000004001d000000400040043f000005340410009c000013490000213d000000c004100039000000400040043f000000030400002900000009050000290000000000450435000000a0041000390000052d050000410000000000540435000000000401043300000000010004140000000805000029000000040550008c00000f540000c13d0000000102000039000005130130009c000013490000213d00000f6a0000013d000005440680009c000013490000213d0000004006800039000000400060043f000000000621034f000000010a00003a000000000aa804360000000006600350000000000b06043b0000000000ba0435000009cb0000613d000000070d000029000000f806d00210000005140c000041000000000d0d004b000000000c06c0190000054506b001970000000006c6019f00000000006a0435000000400600043d000000200b600039000000000a030433000000000c0a004b00000cc80000613d000000000c000019000000000dbc0019000000200cc00039000000000e3c0019000000000e0e04330000000000ed0435000000000dac004b00000cc10000413d0000000003ba0019000000000003043500000000036a0019000000200b300039000000000a040433000000000c0a004b00000cd70000613d000000000c000019000000000dbc0019000000200cc00039000000000e4c0019000000000e0e04330000000000ed0435000000000dac004b00000cd00000413d0000000004ba0019000000000004043500000000033a0019000000200a3000390000000004050433000000000b04004b00000ce60000613d000000000b000019000000000cab0019000000200bb00039000000000d5b0019000000000d0d04330000000000dc0435000000000c4b004b00000cdf0000413d0000000005a400190000000000050435000000000334001900000020053000390000000004070433000000000a04004b00000cf50000613d000000000a000019000000000b5a0019000000200aa00039000000000c7a0019000000000c0c04330000000000cb0435000000000b4a004b00000cee0000413d00000000055400190000000000050435000000000334001900000020053000390000000004090433000000000704004b00000d040000613d0000000007000019000000000a5700190000002007700039000000000b970019000000000b0b04330000000000ba0435000000000a47004b00000cfd0000413d00000000055400190000000000050435000000000334001900000020053000390000000004080433000000000704004b00000d130000613d000000000700001900000000095700190000002007700039000000000a870019000000000a0a04330000000000a90435000000000947004b00000d0c0000413d000000000554001900000000000504350000000003630049000000000334001900000000003604350000003f04300039000000200300008a000000000434016f0000000007640019000000000447004b00000000040000190000000104004039000005130570009c000013490000213d0000000104400190000013490000c13d000000400070043f0000000905000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b0000051408000041000000000954004b000000000900001900000000090880190000051405500197000005140a400197000000000b5a004b000000000800801900000000055a013f000005140550009c000000000809c019000000000508004b000001290000c13d0000000805400029000000000451034f000000000404043b000005130840009c000001290000213d000000000842004900000020055000390000051409000041000000000a85004b000000000a000019000000000a0920190000051408800197000005140b500197000000000c8b004b000000000900801900000000088b013f000005140880009c00000000090ac019000000000809004b000001290000c13d000000010840008c00000fa90000c13d000000000851034f000000000808043b000000010900008a000005140a000041000000000998004b000000000900001900000000090a20190000051408800197000005140b80009c000000000a0080190000051408800167000005140880009c000000000a09c019000000600800003900000000090a004b000010470000c13d000005440870009c000013490000213d0000004008700039000000400080043f000000200870003900000547090000410000000000980435000000010800003900000000008704350000000008070019000010470000013d000000400200043d0000001f0430018f000000050530027200000d750000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000d6d0000413d000000000604004b00000d840000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000006900000013d000005440790009c000013490000213d0000004007900039000000400070043f000000000721034f000000010b00003a000000000bb904360000000007700350000000000c07043b0000000000cb0435000009cb0000613d000000070e000029000000f807e00210000005140d000041000000000e0e004b000000000d07c0190000054507c001970000000007d7019f00000000007b0435000000400700043d000000200c700039000000000b030433000000000d0b004b00000da50000613d000000000d000019000000000ecd0019000000200dd00039000000000f3d0019000000000f0f04330000000000fe0435000000000ebd004b00000d9e0000413d0000000003cb0019000000000003043500000000037b0019000000200c300039000000000b040433000000000d0b004b00000db40000613d000000000d000019000000000ecd0019000000200dd00039000000000f4d0019000000000f0f04330000000000fe0435000000000ebd004b00000dad0000413d0000000004cb0019000000000004043500000000033b0019000000200b3000390000000004050433000000000c04004b00000dc30000613d000000000c000019000000000dbc0019000000200cc00039000000000e5c0019000000000e0e04330000000000ed0435000000000d4c004b00000dbc0000413d0000000005b400190000000000050435000000000334001900000020053000390000000004060433000000000b04004b00000dd20000613d000000000b000019000000000c5b0019000000200bb00039000000000d6b0019000000000d0d04330000000000dc0435000000000c4b004b00000dcb0000413d00000000055400190000000000050435000000000334001900000020053000390000000004080433000000000604004b00000de10000613d0000000006000019000000000b5600190000002006600039000000000c860019000000000c0c04330000000000cb0435000000000b46004b00000dda0000413d000000000554001900000000000504350000000003340019000000200530003900000000040a0433000000000604004b00000df00000613d000000000600001900000000085600190000002006600039000000000ba60019000000000b0b04330000000000b80435000000000846004b00000de90000413d00000000055400190000000000050435000000000334001900000020053000390000000004090433000000000604004b00000dff0000613d000000000600001900000000085600190000002006600039000000000a960019000000000a0a04330000000000a80435000000000846004b00000df80000413d000000000554001900000000000504350000000003730049000000000334001900000000003704350000003f04300039000000200300008a000000000434016f0000000006740019000000000446004b00000000040000190000000104004039000005130560009c000013490000213d0000000104400190000013490000c13d000000400060043f0000000905000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b0000051408000041000000000954004b000000000900001900000000090880190000051405500197000005140a400197000000000b5a004b000000000800801900000000055a013f000005140550009c000000000809c019000000000508004b000001290000c13d0000000805400029000000000451034f000000000404043b000005130840009c000001290000213d000000000842004900000020055000390000051409000041000000000a85004b000000000a000019000000000a0920190000051408800197000005140b500197000000000c8b004b000000000900801900000000088b013f000005140880009c00000000090ac019000000000809004b000001290000c13d000000010840008c000011570000c13d000000000851034f000000000808043b000000010900008a000005140a000041000000000998004b000000000900001900000000090a20190000051408800197000005140b80009c000000000a0080190000051408800167000005140880009c000000000a09c019000000600800003900000000090a004b000013460000c13d000005440860009c000013490000213d0000004008600039000000400080043f000000200860003900000547090000410000000000980435000000010800003900000000008604350000000008060019000013460000013d000005190200004100000000002104350000000402100039000000030300002900000000003204350000003602000039000000000025043500000531020000410000000000240435000000640210003900000532030000410000010c0000013d000000400800043d000200000008001d000000380870008c00000e8b0000413d00000020097002700000050b0870009c000000000907a0190000050b0870009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000000020a000029000005440aa0009c000013490000213d000000000898019f000000020a0000290000004009a00039000000400090043f000000020980003a00000000099a04360000000005500350000000000505043b0000000000590435000009cb0000613d0000054505500197000000f80a80021000000000055a019f00000549055001c700000000005904350000000305800210000000f80550015f00000000055701cf00000002070000290000002107700039000000000057043500000e9c0000013d0000000208000029000005440880009c000013490000213d00000002090000290000004008900039000000400080043f000000010800003a00000000088904360000000005500350000000000505043b0000000000580435000009cb0000613d000000f8077002100000054505500197000000000575019f00000514055001670000000000580435000000800110008a000000000513034f0000006001000039000000000505043b000000000505004b00000efd0000c13d0000051405000041000000000762004b0000000007000019000000000705801900000514066001970000051408200197000000000968004b0000000005008019000000000668013f000005140660009c000000000507c019000000000505004b000001290000c13d000000070500002900000000060504330000000505000029000000000705043300000004050000290000000008050433000000030500002900000000090504330000000205000029000000000a0504330000000805200029000000000253034f000000000202043b000005130b20009c000001290000213d000000000b2400490000002005500039000005140c000041000000000db5004b000000000d000019000000000d0c2019000005140bb00197000005140e500197000000000fbe004b000000000c008019000000000bbe013f000005140bb0009c000000000c0dc019000000000b0c004b000001290000c13d0000000006670019000000000686001900000000069600190000000006a60019000000000626001900000000070104330000000006760019000000400700043d0000051306600197000000380860008c000010870000413d00000020096002700000050b0860009c000000000906a0190000050b0860009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000005440a70009c000013490000213d000000000898019f0000004009700039000000400090043f000000000943034f000000020480003a00000000044704360000000009900350000000000909043b0000000000940435000009cb0000613d0000054509900197000000f80a80021000000000099a019f0000054b099001c700000000009404350000000304800210000000f80440015f00000000044601cf00000021067000390000000000460435000010970000013d000005420100004100000000001004390000050b0100004100000000020004140000050b0320009c0000000002018019000000c00120021000000543011001c70000800b02000039142714180000040f00000001022001900000124f0000613d000000400200043d000000000101043b000000800310008c00000fd10000413d0000008003100270000005460410009c000000000301a019000005460410009c0000000004000019000000100400203900000008054001bf000005130630009c000000000504a0190000004004300270000005130630009c000000000403a01900000004035001bf0000050b0640009c000000000305a01900000020064002700000050b0540009c000000000604a01900000002053001bf0000ffff0460008c000000000503a0190000001003600270000000000306a019000000ff0330008c00000001055020390000004103500039000000010330017f0000000003320019000000000423004b00000000040000190000000104004039000005130630009c000013490000213d0000000104400190000013490000c13d000000400030043f00000002035000390000000006320436000000020300036700000000040000310000002107500039000000050770027200000f420000613d000000000843034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000f3a0000413d000000000700004b00000f440000613d0000000007020433000000000707004b000009cb0000613d00000000070604330000054507700197000000f808500210000000000778019f000005470770004100000000007604350000000305500210000000f80550008900000000015101cf000000ff0550008c0000000001002019000000210520003900000fe40000013d0000050b030000410000050b0520009c000000000203801900000040022002100000050b0540009c00000000040380190000006004400210000000000224019f0000050b0410009c0000000001038019000000c001100210000000000112019f0000000802000029142714130000040f000700600000003d000600800000003d000000010220018f000300000001035500000060011002700001050b0010019d0000050b0310019800000f970000613d0000003f01300039000000200400008a000000000141016f000000400400043d0000000001140019000700000004001d000000000441004b00000000040000190000000104004039000005130510009c000013490000213d0000000104400190000013490000c13d000000400010043f0000001f0130018f000000070400002900000000083404360000000304000367000000050330027200000f870000613d000000000500001900000005065002100000000007680019000000000664034f000000000606043b00000000006704350000000105500039000000000635004b00000f7f0000413d000600000008001d000000000501004b00000f970000613d0000000503300210000000000434034f00000006033000290000000301100210000000000503043300000000051501cf000000000515022f000000000404043b0000010001100089000000000414022f00000000011401cf000000000151019f000000000013043500000007010000290000000001010433000000000202004b000010090000c13d000000000201004b000010820000c13d000000400300043d000800000003001d0000051901000041000000000013043500000004013000390000000302000029000000000021043500000024023000390000000901000029142713ff0000040f00000008040000290000095d0000013d000000380840008c000010360000413d00000020094002700000050b0840009c000000000904a0190000050b0840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000005440a70009c000013490000213d000000000898019f0000004009700039000000400090043f000000000a21034f000000020980003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000009cb0000613d000005450aa00197000000f80b800210000000000aab019f000005490aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf000000210970003900000000008904350000000008070019000010470000013d000005440320009c000013490000213d0000004003200039000000400030043f000000010300003a000000000532043600000000040000310000000203000367000000000643034f0000000006600350000000000606043b0000000000650435000009cb0000613d000000f8071002100000051408000041000000000101004b000000000807c0190000054501600197000000000181019f0000000000150435000000400100043d00000020061000390000000005020433000000000705004b00000ff20000613d000000000700001900000000086700190000002007700039000000000927001900000000090904330000000000980435000000000857004b00000feb0000413d000000000265001900000557060000410000000000620435000000020250003900000000002104350000004102500039000000010520017f0000000002150019000000000552004b00000000050000190000000105004039000005130620009c000013490000213d0000000105500190000013490000c13d0000000906000029000001c405600039000000400020043f000000000253034f0000000005640049000000230650008a000000000202043b00000ea20000013d000000000201004b000010200000c13d0000052e010000410000000000100439000000080100002900000004001004430000050b0100004100000000020004140000050b0320009c0000000002018019000000c0012002100000052f011001c70000800202000039142714180000040f00000001022001900000124f0000613d000000000101043b000000000101004b000009fd0000613d00000007010000290000000001010433000000000201004b000010340000613d0000051402000041000000200310008c000000000300001900000000030240190000051401100197000000000401004b000000000200a019000005140110009c000000000203c019000000000102004b000001290000c13d00000006010000290000000001010433000000000201004b0000000002000019000000010200c039000000000221004b000001290000c13d000000000101004b00000bab0000613d0000000001000019000014280001042e000005440870009c000013490000213d0000004008700039000000400080043f000000000921034f000000010800003a00000000088704360000000009900350000000000909043b0000000000980435000009cb0000613d000000f80a40021000000545099001970000000009a9019f000005140990016700000000009804350000000008070019000000400700043d000005440970009c000013490000213d0000004009700039000000400090043f000000000221034f000000010c00003a0000000009c704360000000002200350000000000b02043b0000000000b90435000009cb0000613d0000054502b001970000054a0a2001c70000000000a9043500000000090604330000000009490019000000000a0804330000000009a90019000000000a0704330000000009a90019000000400a00043d0000051309900197000000380d90008c0000117f0000413d000000200d9002700000050b0c90009c000000000d09a0190000050b0c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d002039000005440ea0009c000013490000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000009cb0000613d000000f80bc0021000000000022b019f0000054b022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a0003900000000002904350000118c0000013d0000050b020000410000050b0310009c0000000001028019000000060400002900000a0d0000013d000005440870009c000013490000213d0000004008700039000000400080043f000000000843034f000000010400003a00000000044704360000000008800350000000000808043b0000000000840435000009cb0000613d0000054508800197000000f806600210000000000686019f0000054a066000410000000000640435000000400400043d00000020064000390000000008070433000000000908004b000010a40000613d0000000009000019000000000a6900190000002009900039000000000b790019000000000b0b04330000000000ba0435000000000a89004b0000109d0000413d000000000768001900000000000704350000000007480019000000200970003900000007080000290000000008080433000000000a08004b000010b40000613d000000000a000019000000000b9a0019000000200aa00039000000070ca00029000000000c0c04330000000000cb0435000000000b8a004b000010ad0000413d000000000998001900000000000904350000000007780019000000200970003900000005080000290000000008080433000000000a08004b000010c40000613d000000000a000019000000000b9a0019000000200aa00039000000050ca00029000000000c0c04330000000000cb0435000000000b8a004b000010bd0000413d000000000998001900000000000904350000000007780019000000200970003900000004080000290000000008080433000000000a08004b000010d40000613d000000000a000019000000000b9a0019000000200aa00039000000040ca00029000000000c0c04330000000000cb0435000000000b8a004b000010cd0000413d000000000998001900000000000904350000000007780019000000200970003900000003080000290000000008080433000000000a08004b000010e40000613d000000000a000019000000000b9a0019000000200aa00039000000030ca00029000000000c0c04330000000000cb0435000000000b8a004b000010dd0000413d000000000998001900000000000904350000000007780019000000200970003900000002080000290000000008080433000000000a08004b000010f40000613d000000000a000019000000000b9a0019000000200aa00039000000020ca00029000000000c0c04330000000000cb0435000000000b8a004b000010ed0000413d00000000099800190000000000090435000000000553034f00000000037800190000001f0720018f00000020083000390000000509200272000011050000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000010fd0000413d000000000a07004b000011140000613d0000000509900210000000000595034f00000000089800190000000307700210000000000908043300000000097901cf000000000979022f000000000505043b0000010007700089000000000575022f00000000057501cf000000000595019f00000000005804350000000002230019000000200520003900000000000504350000000003010433000000000703004b000011220000613d000000000700001900000000085700190000002007700039000000000917001900000000090904330000000000980435000000000837004b0000111b0000413d000000000153001900000000000104350000000001420049000000000113001900000000001404350000003f01100039000000010210017f0000000001420019000000000221004b00000000020000190000000102004039000005130310009c000013490000213d0000000102200190000013490000c13d000000400010043f0000050b010000410000050b0260009c0000000006018019000000400260021000000000030404330000050b0430009c00000000030180190000006003300210000000000223019f000012020000013d0000001f0430018f0000000502300272000011470000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000011400000413d000000000504004b000011550000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000142900010430000000380840008c000013350000413d00000020094002700000050b0840009c000000000904a0190000050b0840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000005440a60009c000013490000213d000000000898019f0000004009600039000000400090043f000000000a21034f000000020980003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000009cb0000613d000005450aa00197000000f80b800210000000000aab019f000005490aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf000000210960003900000000008904350000000008060019000013460000013d000005440da0009c000013490000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000009cb0000613d000000f809900210000000000229019f0000054a0220004100000000002d0435000000400200043d00000020092000390000054c0b0000410000000000b90435000000210c200039000000000b0a0433000000000d0b004b0000119c0000613d000000000d000019000000000ecd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ebd004b000011950000413d000000000acb001900000000000a0435000000000a2b0019000000210ca00039000000000b060433000000000d0b004b000011ab0000613d000000000d000019000000000ecd0019000000200dd00039000000000f6d0019000000000f0f04330000000000fe0435000000000ebd004b000011a40000413d0000000006cb001900000000000604350000000006ab0019000000210b600039000000000a080433000000000c0a004b000011ba0000613d000000000c000019000000000dbc0019000000200cc00039000000000e8c0019000000000e0e04330000000000ed0435000000000dac004b000011b30000413d0000000008ba00190000000000080435000000000551034f00000000016a00190000001f0640018f0000002108100039000000050a400272000011cb0000613d000000000b000019000000050cb00210000000000dc80019000000000cc5034f000000000c0c043b0000000000cd0435000000010bb00039000000000cab004b000011c30000413d000000000b06004b000011da0000613d000000050aa002100000000005a5034f0000000008a800190000000306600210000000000a080433000000000a6a01cf000000000a6a022f000000000505043b0000010006600089000000000565022f00000000056501cf0000000005a5019f00000000005804350000000001410019000000210510003900000000000504350000000004070433000000000604004b000011e80000613d000000000600001900000000085600190000002006600039000000000a760019000000000a0a04330000000000a80435000000000846004b000011e10000413d0000000005540019000000000005043500000000012100490000000001140019000000010410003900000000004204350000004001100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000005130410009c000013490000213d0000000103300190000013490000c13d000000400010043f0000050b010000410000050b0390009c0000000009018019000000400390021000000000020204330000050b0420009c00000000020180190000006002200210000000000232019f00000000030004140000050b0430009c0000000003018019000000c001300210000000000121019f00000516011001c70000801002000039142714180000040f0000000102200190000001290000613d0000000203000367000000000101043b000700000001001d0000000901000029000000e404100039000000000143034f000000000101043b0000051501100198000400000004001d0000122f0000c13d000000800140008a000000000213034f000000400140008a000000000513034f000000000402043b000000000505043b00000000624500a9000000000605004b000012220000613d00000000655200d9000000000445004b0000122b0000c13d0000008001100039000000000113034f000000000101043b000500000021001d000000050110006b000000000100001900000001010040390000000101100190000012340000613d000005620100004100000000001004350000001101000039000000410000013d00000009010000290000012401100039000000000113034f000000000101043b000500000001001d00000558010000410000000000100439000000060100002900000004001004430000050b0100004100000000020004140000050b0320009c0000000002018019000000c0012002100000052f011001c70000800a02000039142714180000040f00000001022001900000124f0000613d000000000101043b000000050110006b000012500000a13d000000400100043d00000064021000390000056003000041000000000032043500000044021000390000056103000041000000000032043500000024021000390000002203000039000001070000013d000000000001042f0000000004000031000000090140006a000000230210008a000000040100002900000100011000390000000203000367000000000113034f000000000101043b0000051405000041000000000621004b0000000006000019000000000605801900000514022001970000051407100197000000000827004b0000000005008019000000000227013f000005140220009c000000000506c019000000000205004b000001290000c13d0000000802100029000000000123034f000000000101043b000005130510009c000001290000213d000000000514004900000020062000390000051402000041000000000756004b0000000007000019000000000702201900000514055001970000051408600197000000000958004b0000000002008019000000000558013f000005140550009c000000000207c019000000000202004b000001290000c13d0000003f02100039000000200500008a000000000552016f000000400200043d0000000005520019000000000725004b00000000070000190000000107004039000005130850009c000013490000213d0000000107700190000013490000c13d000000400050043f00000000051204360000000007610019000000000447004b000001290000213d000000000463034f0000001f0310018f0000000506100272000012970000613d000000000700001900000005087002100000000009850019000000000884034f000000000808043b00000000008904350000000107700039000000000867004b0000128f0000413d000000000703004b000012a60000613d0000000506600210000000000464034f00000000066500190000000303300210000000000706043300000000073701cf000000000737022f000000000404043b0000010003300089000000000434022f00000000033401cf000000000373019f000000000036043500000000011500190000000000010435000000400100043d0000000003020433000000410330008c000012b90000c13d00000041032000390000000003030433000000ff0330018f0000001d0430008a000000030600008a000000000464004b000012bf0000213d00000044021000390000055f03000041000000000032043500000024021000390000001603000039000002a20000013d00000044021000390000055903000041000000000032043500000024021000390000001d03000039000002a20000013d0000000004050433000000400220003900000000020204330000055a0520009c000012ca0000413d00000044021000390000055e03000041000000000032043500000024021000390000000903000039000002a20000013d0000006005100039000000000025043500000040021000390000000000420435000000200210003900000000003204350000000702000029000000000021043500000000000004350000050b0200004100000000030004140000050b0430009c00000000030280190000050b0410009c00000000010280190000004001100210000000c002300210000000000112019f0000055b011001c70000000102000039142714180000040f000000000301001900000060033002700000050b03300197000000200430008c000000000403001900000020040080390000001f0540018f0000000504400272000012f00000613d00000000060000190000000507600210000000000871034f000000000808043b00000000008704350000000106600039000000000746004b000012e90000413d000000000605004b000012fe0000613d00000003055002100000000504400210000000000604043300000000065601cf000000000656022f000000000741034f000000000707043b0000010005500089000000000757022f00000000055701cf000000000565019f0000000000540435000100000003001f0003000000010355000000400400043d0000000102200190000013150000613d00000000010004330000051501100197000000060210006c0000000002000019000000010200c039000000000101004b0000000001000019000000010100603900000000011201a00000055c01000041000000000100c01900000000001404350000050b010000410000050b0240009c000000000401801900000040014002100000055d011001c7000014280001042e0000001f0230018f0000000505300272000013210000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013190000413d000000000602004b000013300000613d0000000505500210000000000151034f00000000055400190000000302200210000000000605043300000000062601cf000000000626022f000000000101043b0000010002200089000000000121022f00000000012101cf000000000161019f00000000001504350000050b010000410000050b0240009c00000000040180190000004001400210000006940000013d000005440860009c000013490000213d0000004008600039000000400080043f000000000921034f000000010800003a00000000088604360000000009900350000000000909043b0000000000980435000009cb0000613d000000f80a40021000000545099001970000000009a9019f000005140990016700000000009804350000000008060019000000400600043d000005440960009c0000134d0000a13d000005620100004100000000001004350000004101000039000000410000013d0000004009600039000000400090043f000000000221034f000000010c00003a0000000009c604360000000002200350000000000b02043b0000000000b90435000009cb0000613d0000054502b001970000054a0a2001c70000000000a9043500000000090704330000000009490019000000000a0804330000000009a90019000000000a0604330000000009a90019000000400a00043d0000051309900197000000380d90008c000013850000413d000000200d9002700000050b0c90009c000000000d09a0190000050b0c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d002039000005440ea0009c000013490000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000009cb0000613d000000f80bc0021000000000022b019f0000054b022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a000390000000000290435000013920000013d000005440da0009c000013490000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000009cb0000613d000000f809900210000000000229019f0000054a0220004100000000002d0435000000400200043d0000002009200039000005160b0000410000000000b90435000000210c200039000000000b0a0433000000000d0b004b000013a20000613d000000000d000019000000000ecd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ebd004b0000139b0000413d000000000acb001900000000000a0435000000000a2b0019000000210ca00039000000000b070433000000000d0b004b000013b10000613d000000000d000019000000000ecd0019000000200dd00039000000000f7d0019000000000f0f04330000000000fe0435000000000ebd004b000013aa0000413d0000000007cb001900000000000704350000000007ab0019000000210b700039000000000a080433000000000c0a004b000013c00000613d000000000c000019000000000dbc0019000000200cc00039000000000e8c0019000000000e0e04330000000000ed0435000000000dac004b000013b90000413d0000000008ba00190000000000080435000000000551034f00000000017a00190000001f0740018f0000002108100039000000050a400272000013d10000613d000000000b000019000000050cb00210000000000dc80019000000000cc5034f000000000c0c043b0000000000cd0435000000010bb00039000000000cab004b000013c90000413d000000000b07004b000013e00000613d000000050aa002100000000005a5034f0000000008a800190000000307700210000000000a080433000000000a7a01cf000000000a7a022f000000000505043b0000010007700089000000000575022f00000000057501cf0000000005a5019f00000000005804350000000001410019000000210510003900000000000504350000000004060433000000000704004b000013ee0000613d000000000700001900000000085700190000002007700039000000000a670019000000000a0a04330000000000a80435000000000847004b000013e70000413d0000000005540019000000000005043500000000012100490000000001140019000000010410003900000000004204350000004001100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000005130410009c000013490000213d0000000103300190000013490000c13d000011f80000013d00000000030104330000000002320436000000000403004b0000140b0000613d000000000400001900000000052400190000002004400039000000000614001900000000060604330000000000650435000000000534004b000014040000413d000000000123001900000000000104350000001f01300039000000200300008a000000000131016f0000000001120019000000000001042d000000000001042f00001416002104210000000102000039000000000001042d0000000002000019000000000001042d0000141b002104230000000102000039000000000001042d0000000002000019000000000001042d00001420002104210000000102000039000000000001042d0000000002000019000000000001042d00001425002104230000000102000039000000000001042d0000000002000019000000000001042d0000142700000432000014280001042e00001429000104300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000df9c158800000000000000000000000000000000000000000000000000000000df9c158900000000000000000000000000000000000000000000000000000000e2f318e300000000000000000000000000000000000000000000000000000000eeb8cb0900000000000000000000000000000000000000000000000000000000202bcce700000000000000000000000000000000000000000000000000000000a28c1aee000000000000000000000000000000000000000000000000ffffffffffffffff8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff02000000000000000000000000000000000000000000000000000000000000007261746f720000000000000000000000000000000000000000000000000000004661696c656420746f20706179207468652066656520746f20746865206f706508c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000840000000000000000000000000000000000000000000000000000000100000000000000000000000000000000ffffffff000000000000000000000000000000000000000000000000000000009c4d535affffffffffffffffffffffffffffffffffffffffffffffffffffffff9c4d535b00000000000000000000000000000000000000000000000000000000ecf95b8a000000000000000000000000000000000000000000000000000000003cda3351000000000000000000000000000000000000000000000000000000005d3827000000000000000000000000000000000000000000000000000000000000000000ffffffff00000000000000000000000000000000000000000000000001000001000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffdf4f766572666c6f7700000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000008000000000000000008c5a344500000000000000000000000000000000000000000000000000000000949431dc00000000000000000000000000000000000000000000000000000000dd62ed3e000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000044000000800000000000000000095ea7b3000000000000000000000000000000000000000000000000000000005361666545524332303a206c6f772d6c6576656c2063616c6c206661696c65641806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b83020000020000000000000000000000000000002400000000000000000000000000000000000000000000000000000000000000440000000000000000000000005361666545524332303a20617070726f76652066726f6d206e6f6e2d7a65726f20746f206e6f6e2d7a65726f20616c6c6f77616e636500000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff7f000000000000000000000000000000000000000000000000ffffffffffffff3f6f742073756363656564000000000000000000000000000000000000000000005361666545524332303a204552433230206f7065726174696f6e20646964206e416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000000000000000000000000000000000000000006400000000000000000000000054686520617070726f76616c4261736564207061796d617374657220696e707574206d757374206265206174206c65617374203638206279746573206c6f6e670000000000000000000000000000000000000084000000800000000000000000556e737570706f72746564207061796d617374657220666c6f77000000000000546865207374616e64617264207061796d617374657220696e707574206d757374206265206174206c656173742034206279746573206c6f6e67000000000000e1239cd8000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000024000000a0000000000000000000000000000000000000000000000000000000000000000000000001ffffffe09a8a0592ac89c5ad3bc6df8224c17b485976f597df104ee20d0df415241f670b0200000200000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffbf00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00000000000000000000000000000000ffffffffffffffffffffffffffffffff81000000000000000000000000000000000000000000000000000000000000009400000000000000000000000000000000000000000000000000000000000000b800000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000000f8000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000007ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff6b656363616b3235362072657475726e656420696e76616c6964206461746100848e1bfa1ac4e3576b728bda6721b215c70a7799a5b4866282a71bab954baac8000000000000000000000000000000000000000000000000fffffffffffffe1fc2f8787176b8ac6bf7215b4adcc1e069bf4ab82d9ab1df05a57a91d425935b6ead7c5bef027816a800da1736444fb58a807ef4c9603b7848673f7e3a68eb14a519b453ce45aaaaf3a300f5a9ec95869b4f28ab10430b572ee218c3a6a5e07d6f000000000000000000000000000000000000000000000000ffffffffffffff5f190100000000000000000000000000000000000000000000000000000000000080800000000000000000000000000000000000000000000000000000000000009cc7f708afc65944829bd487b90b72536b1951864fbfc14e125fc972a6507f395369676e6174757265206c656e67746820697320696e636f72726563740000007fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a10000000000000000000000000000000000000080000000000000000000000000202bcce7000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000496e76616c69642073000000000000000000000000000000000000000000000076206973206e656974686572203237206e6f722032380000000000000000000075650000000000000000000000000000000000000000000000000000000000004e6f7420656e6f7567682062616c616e636520666f7220666565202b2076616c4e487b71000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000456e636f64696e6720756e737570706f7274656420747800000000000000000000000000000000000000000000000000000000000000000000000000000000009ca42e6981d147c944c67468396472d007d7f04ef9344c9f6cf97a796a6536cd", + "deployedBytecode": "0x0004000000000002000b000000000002000000000301001900000060073002700000050b06700197000300000061035500020000000103550000050b0070019d0000008004000039000000400040043f00000001022001900000002c0000c13d000000040260008c000000340000413d000000000201043b000000e0022002700000050d0320009c000000440000a13d0000050e0320009c000000980000613d0000050f0320009c000000c70000613d000005100220009c000000360000c13d000000040260008a000000200320008c000001290000413d0000000401100370000000000101043b000005130310009c000001290000213d00000000011200490000051402000041000002600310008c000000000300001900000000030240190000051401100197000000000401004b000000000200a019000005140110009c000000000203c019000000000102004b000010340000613d000001290000013d0000000001000416000000000101004b000001290000c13d0000002001000039000001000010044300000120000004430000050c01000041000014280001042e000000000106004b000010340000613d000000000100041200000515011001970000000002000410000000000121004b000010340000c13d0000000001000411000080010110008c000010340000c13d000005620100004100000000001004350000000101000039000000040010043f00000563010000410000142900010430000005110320009c000001130000613d000900000004001d000005120220009c000000360000c13d000000040260008a000000600220008c000001290000413d0000004402100370000000000302043b000005130230009c000001290000213d000000040430003900000000054600490000051402000041000002600750008c000000000700001900000000070240190000051408500197000000000908004b000000000200a019000005140880009c000000000207c019000000000202004b000001290000c13d0000000002000411000080010220008c000010340000c13d000000000200041200000515072001970000000002000410000000000727004b000010340000c13d0000022403300039000000000731034f000000000707043b0000001f0550008a0000051408000041000000000957004b000000000900001900000000090880190000051405500197000005140a700197000000000b5a004b000000000800801900000000055a013f000005140550009c000000000809c019000000000508004b000001290000c13d0000000005470019000000000451034f000000000404043b000005130740009c000001290000213d000000000746004900000020055000390000051408000041000000000975004b000000000900001900000000090820190000051407700197000005140a500197000000000b7a004b000000000800801900000000077a013f000005140770009c000000000809c019000000000708004b000001290000c13d000000030740008c0000024c0000213d0000051901000041000000800010043f0000002001000039000000840010043f0000003a01000039000000a40010043f0000053d01000041000000c40010043f0000053e01000041000000e40010043f0000053b010000410000142900010430000000040260008a000000600220008c000001290000413d0000004402100370000000000302043b000005130230009c000001290000213d000000040230003900000000052600490000051404000041000002600850008c000000000800001900000000080440190000051409500197000000000a09004b000000000400a019000005140990009c000000000408c019000000000404004b000001290000c13d0000000004000411000080010440008c000010340000c13d000000000400041200000515044001970000000008000410000000000484004b000010340000c13d0000004404300039000000000441034f0000012408300039000000000381034f000000000404043b0000051504400197000000000303043b0000051b0930009c000002080000413d0000051901000041000000800010043f0000002001000039000000840010043f0000000801000039000000a40010043f0000052601000041000000c40010043f00000527010000410000142900010430000000040360008a000000600230008c000001290000413d0000004402100370000000000202043b000005130420009c000001290000213d00000000032300490000051404000041000002600530008c000000000500001900000000050440190000051403300197000000000603004b000000000400a019000005140330009c000000000405c019000000000304004b000001290000c13d0000000003000411000080010330008c000010340000c13d000000000300041200000515033001970000000004000410000000000343004b000010340000c13d000000a403200039000000000331034f0000006402200039000000000121034f000000000101043b000000000203043b000000000302004b000001f00000c13d00000000040004150000000b0440008a00000020044000c90000000001000414000b00000000001d000900000004001d0000050b020000410000050b0310009c0000000001028019000000c0011002100000800102000039142714130000040f0000000903000029000300000001035500000060011002700001050b0010019d000000050130027000000001012001950000000101200190000010340000c13d000000400100043d000000640210003900000517030000410000000000320435000000440210003900000518030000410000000000320435000000240210003900000025030000390000000000320435000005190200004100000000002104350000000402100039000000200300003900000000003204350000050b020000410000050b0310009c000000000102801900000040011002100000051a011001c70000142900010430000000040260008a000000600220008c000001290000413d0000004402100370000000000202043b000900000002001d000005130220009c000001290000213d0000000902000029000800040020003d000000080260006a0000051403000041000002600420008c000000000400001900000000040340190000051402200197000000000502004b000000000300a019000005140220009c000000000304c019000000000203004b0000012b0000613d000000000100001900001429000104300000002402100370000000000202043b000700000002001d0000000002000411000080010220008c000010340000c13d000000000200041200000515022001970000000003000410000600000003001d000000000232004b000010340000c13d00000000020004140000053f03000041000000a00030043f0000000903000029000501040030003d0000000501100360000000000101043b000000a40010043f0000002401000039000000800010043f000000e001000039000000400010043f000000c001200210000005220110019700000540011001c700008003020000390000000003000019000000000400001900000000050000190000000006000019142714130000040f0003000000010355000000000301001900000060033002700001050b0030019d0000050b083001970000003f038000390000054104300197000000400600043d0000000003640019000000000443004b00000000040000190000000104004039000005130530009c000013490000213d0000000104400190000013490000c13d000000400030043f000000000786043600000002030003670000000004000031000000000543034f0000001f0980003900000005099002720000016d0000613d000000000a000019000000050ba00210000000000cb70019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000001650000413d000000000900004b0000016f0000613d0000001f0980018f00000005088002720000017b0000613d000000000a000019000000050ba00210000000000cb70019000000000bb1034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b000001730000413d000000000a09004b0000018a0000613d0000000508800210000000000181034f00000000088700190000000309900210000000000a080433000000000a9a01cf000000000a9a022f000000000101043b0000010009900089000000000191022f00000000019101cf0000000001a1019f00000000001804350000000101200190000002420000613d000000070100006b0000120f0000c13d0000000501000029000001000110008a000000000113034f000000000101043b000000010210008c0000025f0000213d000000000201004b000002ae0000613d000000010110008c0000029c0000c13d000005420100004100000000001004390000050b0100004100000000020004140000050b0320009c0000000002018019000000c00120021000000543011001c70000800b02000039142714180000040f00000001022001900000124f0000613d000000400300043d000000000401043b000000800140008c000004490000413d0000008001400270000005460240009c000000000104a019000005460240009c0000000002000019000000100200203900000008052001bf000005130610009c000000000502a0190000004002100270000005130610009c000000000201a01900000004015001bf0000050b0620009c000000000105a01900000020062002700000050b0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000005130610009c000013490000213d0000000102200190000013490000c13d000000400010043f000000020150003900000000061304360000000201000367000000000200003100000021075000390000000507700272000001de0000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000001d60000413d000000000700004b000001e00000613d0000000007030433000000000707004b000009cb0000613d00000000070604330000054507700197000000f808500210000000000778019f000005470770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c000000000400201900000021053000390000045c0000013d00000000431200a900000000422300d9000000000112004b0000122b0000c13d00000000040004150000000a0440008a00000020044000c90000000001000414000a00000000001d000000000203004b000000ef0000613d0000050b020000410000050b0410009c0000000001028019000000c00110021000000516011001c7000080090200003900008001040000390000000005000019142714130000040f00000000030004150000000a0330008a00000020033000c9000000f70000013d000000a008800039000000000881034f000000000808043b0000001f0550008a0000051409000041000000000a58004b000000000a000019000000000a0980190000051405500197000005140b800197000000000c5b004b000000000900801900000000055b013f000005140550009c00000000090ac019000000000509004b000001290000c13d0000000002280019000000000521034f000000000805043b000005130580009c000001290000213d000000000586004900000020092000390000051402000041000000000a59004b000000000a000019000000000a0220190000051405500197000005140b900197000000000c5b004b000000000200801900000000055b013f000005140550009c00000000020ac019000000000202004b000001290000c13d00000000020004140000050b0520009c000000bd0000213d000080060540008c0000000005000019000003de0000c13d000000040580008c0000000005000019000003de0000413d000000000a91034f0000000105000039000000000a0a043b0000051c0aa001970000051d0ba0009c000003da0000213d000005200ba0009c000003de0000613d000005210aa0009c000003de0000613d0000000005000019000003de0000013d00000000010604330000050b020000410000050b0310009c00000000010280190000050b0370009c000000000702801900000040027002100000006001100210000000000121019f0000142900010430000000000751034f000000000707043b0000051c07700197000005280870009c000010340000613d000005290770009c000003540000c13d000000430440008c000003bb0000213d0000051901000041000000800010043f0000002001000039000000840010043f0000004001000039000000a40010043f0000053901000041000000c40010043f0000053a01000041000000950000013d000000020210008c000002fc0000613d000000710110008c0000029c0000c13d0000000902000029000001c401200039000000000113034f0000000002240049000000230220008a000000000101043b0000051405000041000000000621004b0000000006000019000000000605801900000514022001970000051407100197000000000827004b0000000005008019000000000227013f000005140220009c000000000506c019000000000205004b000001290000c13d0000000801100029000000000213034f000000000202043b000005130520009c000001290000213d000000000524004900000020011000390000051406000041000000000751004b0000000007000019000000000706201900000514055001970000051408100197000000000958004b0000000006008019000000000558013f000005140550009c000000000607c019000000000506004b000001290000c13d00000000050004140000000006120019000000000226004b0000000002000019000000010200403900000001022001900000122b0000c13d000000000264004b0000122b0000413d0000054d0250009c000006970000413d000000400100043d00000044021000390000052603000041000000000032043500000024021000390000000803000039000002a20000013d000000400100043d000000440210003900000564030000410000000000320435000000240210003900000017030000390000000000320435000005190200004100000000002104350000000402100039000000200300003900000000003204350000050b020000410000050b0310009c0000000001028019000000400110021000000538011001c700001429000104300000000501300360000000400200043d000700000002001d000000000101043b000000800210008c0000035c0000413d0000008002100270000005460610009c000000000201a019000005460610009c0000000006000019000000100600203900000008076001bf000005130820009c000000000706a0190000004006200270000005130820009c000000000602a01900000004087001bf0000050b0260009c000000000807a01900000020076002700000050b0260009c000000000706a01900000002028001bf0000ffff0670008c000000000208a0190000001006700270000000000607a019000000ff0660008c0000000102202039000000200600008a0000004107200039000000000667016f0000000706600029000000070760006c00000000070000190000000107004039000005130860009c000013490000213d0000000107700190000013490000c13d000000400060043f00000002062000390000000707000029000000000667043600000021072000390000000507700272000002e80000613d00000000080000190000000509800210000000000a960019000000000995034f000000000909043b00000000009a04350000000108800039000000000978004b000002e00000413d000000000700004b000002ea0000613d00000007070000290000000007070433000000000707004b000009cb0000613d00000000070604330000054507700197000000f808200210000000000778019f000005470770004100000000007604350000000302200210000000f80220008900000000012101cf000000ff0220008c0000000001002019000000070200002900000021022000390000036e0000013d000005420100004100000000001004390000050b0100004100000000020004140000050b0320009c0000000002018019000000c00120021000000543011001c70000800b02000039142714180000040f00000001022001900000124f0000613d000000400300043d000000000401043b000000800140008c000004a80000413d0000008001400270000005460240009c000000000104a019000005460240009c0000000002000019000000100200203900000008052001bf000005130610009c000000000502a0190000004002100270000005130610009c000000000201a01900000004015001bf0000050b0620009c000000000105a01900000020062002700000050b0520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000005130610009c000013490000213d0000000102200190000013490000c13d000000400010043f000000020150003900000000061304360000000201000367000000000200003100000021075000390000000507700272000003420000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b0000033a0000413d000000000700004b000003440000613d0000000007030433000000000707004b000009cb0000613d00000000070604330000054507700197000000f808500210000000000778019f000005470770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c00000000040020190000002105300039000004bb0000013d0000051901000041000000800010043f0000002001000039000000840010043f0000001a01000039000000a40010043f0000053c01000041000000c40000013d0000000702000029000005440220009c000013490000213d00000007060000290000004002600039000000400020043f000000010200003a00000000022604360000000006500350000000000606043b0000000000620435000009cb0000613d000000f8071002100000051408000041000000000101004b000000000807c0190000054501600197000000000181019f0000000000120435000000400100043d0000000502000029000000600220008a000000000623034f000000000606043b000000800760008c000005070000413d0000008007600270000005460860009c000000000706a019000005460860009c0000000008000019000000100800203900000008098001bf000005130a70009c000000000908a0190000004008700270000005130a70009c000000000807a019000000040a9001bf0000050b0780009c000000000a09a01900000020098002700000050b0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008810019000000000918004b00000000090000190000000109004039000005130a80009c000013490000213d0000000109900190000013490000c13d000000400080043f0000000208700039000000000881043600000021097000390000000509900272000003a90000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000003a10000413d000000000900004b000003ab0000613d0000000009010433000000000909004b000009cb0000613d00000000090804330000054509900197000000f80a70021000000000099a019f000005470990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c00000000060020190000002107100039000005170000013d0000000404500039000000000541034f000000000505043b000800000005001d000005150550009c000001290000213d000001400330008a000000000331034f0000002004400039000000000441034f000000000404043b000700000004001d000000000303043b0000052a04000041000000800040043f0000051502200197000500000002001d000000840020043f0000051502300197000600000002001d000000a40020043f00000000020004140000000803000029000000040330008c000005630000c13d000000000161034f0000000103000031000000200230008c000000000403001900000020040080390000058f0000013d0000051e0ba0009c000003de0000613d0000051f0aa0009c000000000500c019000000000a9800190000000006a6004b0000000006000019000000010600403900000000088a004b00000001066041bf0000050b08900197000000000181034f000000000803004b000003f70000c13d00000001036001900000122b0000c13d00000523030000410000052406000041000000000505004b000000000603c019000000c0022002100000052202200197000000000226019f0000000003a700490000050b0330019700000000013103df00000000012103af0000000002040019000004020000013d00000001066001900000122b0000c13d0000000006a700490000050b0660019700000000016103df000000c002200210000005220220019700000523022001c700000000012103af000080090200003900000000060000191427141d0000040f0003000000010355000000000301001900000060033002700001050b0030019d0000050b0330019700000001022001900000042e0000613d000000400200043d000005250120009c000013490000213d0000002001200039000000400010043f00000000000204350000002003000039000000400100043d0000000004310436000000000302043300000000003404350000004004100039000000000503004b000004200000613d000000000500001900000000064500190000002005500039000000000725001900000000070704330000000000760435000000000635004b000004190000413d000000000243001900000000000204350000005f02300039000000200300008a000000000232016f0000050b030000410000050b0420009c00000000020380190000050b0410009c000000000103801900000040011002100000006002200210000000000112019f000014280001042e0000001f0430018f0000000502300272000004390000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000004320000413d000000000504004b000004470000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000142900010430000005440130009c000013490000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000201000367000000000621034f0000000006600350000000000606043b0000000000650435000009cb0000613d000000f8074002100000051408000041000000000404004b000000000807c0190000054504600197000000000484019f00000000004504350000000505100360000000400400043d000000000505043b000000800650008c000005b60000413d0000008006500270000005460750009c000000000605a019000005460750009c0000000007000019000000100700203900000008087001bf000005130960009c000000000807a0190000004007600270000005130960009c000000000706a01900000004098001bf0000050b0670009c000000000908a01900000020087002700000050b0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007740019000000000847004b00000000080000190000000108004039000005130970009c000013490000213d0000000108800190000013490000c13d000000400070043f0000000207600039000000000774043600000021086000390000000508800272000004960000613d000000000921034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b0000048e0000413d000000000800004b000004980000613d0000000008040433000000000808004b000009cb0000613d00000000080704330000054508800197000000f809600210000000000889019f000005470880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106400039000005c70000013d000005440130009c000013490000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000201000367000000000621034f0000000006600350000000000606043b0000000000650435000009cb0000613d000000f8074002100000051408000041000000000404004b000000000807c0190000054504600197000000000484019f00000000004504350000000505100360000000400400043d000000000505043b000000800650008c000006150000413d0000008006500270000005460750009c000000000605a019000005460750009c0000000007000019000000100700203900000008087001bf000005130960009c000000000807a0190000004007600270000005130960009c000000000706a01900000004098001bf0000050b0670009c000000000908a01900000020087002700000050b0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007740019000000000847004b00000000080000190000000108004039000005130970009c000013490000213d0000000108800190000013490000c13d000000400070043f0000000207600039000000000774043600000021086000390000000508800272000004f50000613d000000000921034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b000004ed0000413d000000000800004b000004f70000613d0000000008040433000000000808004b000009cb0000613d00000000080704330000054508800197000000f809600210000000000889019f000005470880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106400039000006260000013d000005440710009c000013490000213d0000004007100039000000400070043f000000010700003a00000000077104360000000008500350000000000808043b0000000000870435000009cb0000613d000000f809600210000005140a000041000000000606004b000000000a09c01900000545068001970000000006a6019f0000000000670435000000400220008a000000000623034f000000400200043d000000000606043b000000800760008c0000086e0000413d0000008007600270000005460860009c000000000706a019000005460860009c0000000008000019000000100800203900000008098001bf000005130a70009c000000000908a0190000004008700270000005130a70009c000000000807a019000000040a9001bf0000050b0780009c000000000a09a01900000020098002700000050b0780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008820019000000000928004b00000000090000190000000109004039000005130a80009c000013490000213d0000000109900190000013490000c13d000000400080043f0000000208700039000000000882043600000021097000390000000509900272000005510000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000005490000413d000000000900004b000005530000613d0000000009020433000000000909004b000009cb0000613d00000000090804330000054509900197000000f80a70021000000000099a019f000005470990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c000000000600201900000021072000390000087e0000013d0000050b010000410000050b0320009c0000000002018019000000c0012002100000052b011001c70000000802000029142714180000040f000000000301001900000060033002700000050b03300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000057c0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000005740000413d000000000705004b0000058b0000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f00030000000103550000000102200190000006740000613d0000001f02400039000000600520018f00000080025001bf000000400020043f000000200430008c000001290000413d000000800400043d000000070440006c000010340000813d000000a0045000390000052c060000410000000000640435000000a40650003900000006070000290000000000760435000000c40650003900000000000604350000004406000039000100000006001d00000000006204350000014006500039000000400060043f00000120065000390000052d07000041000000000076043500000100065001bf0000002005000039000300000005001d000200000006001d0000000000560435000000000502043300000000020004140000000806000029000000040660008c0000090c0000c13d0000000102000039000005130430009c000013490000213d000009200000013d000005440640009c000013490000213d0000004006400039000000400060043f000000000721034f000000010600003a00000000066404360000000007700350000000000707043b0000000000760435000009cb0000613d000000f8085002100000051409000041000000000505004b000000000908c0190000054505700197000000000595019f0000000000560435000000400500043d0000000506000029000000600660008a000000000761034f000000000707043b000000800870008c000009620000413d0000008008700270000005460970009c000000000807a019000005460970009c00000000090000190000001009002039000000080a9001bf000005130b80009c000000000a09a0190000004009800270000005130b80009c000000000908a019000000040ba001bf0000050b0890009c000000000b0aa019000000200a9002700000050b0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000005130b90009c000013490000213d000000010aa00190000013490000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa00272000006030000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000005fb0000413d000000000a00004b000006050000613d000000000a050433000000000a0a004b000009cb0000613d000000000a090433000005450aa00197000000f80b800210000000000aab019f000005470aa000410000000000a904350000000308800210000000f80880008900000000078701cf000000ff0880008c00000000070020190000002108500039000009730000013d000005440640009c000013490000213d0000004006400039000000400060043f000000000721034f000000010600003a00000000066404360000000007700350000000000707043b0000000000760435000009cb0000613d000000f8085002100000051409000041000000000505004b000000000908c0190000054505700197000000000595019f0000000000560435000000400500043d0000000506000029000000400760008a000000000671034f000000000606043b000000800860008c000009c00000413d0000008008600270000005460960009c000000000806a019000005460960009c00000000090000190000001009002039000000080a9001bf000005130b80009c000000000a09a0190000004009800270000005130b80009c000000000908a019000000040ba001bf0000050b0890009c000000000b0aa019000000200a9002700000050b0890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000005130b90009c000013490000213d000000010aa00190000013490000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa00272000006620000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b0000065a0000413d000000000a00004b000006640000613d000000000a050433000000000a0a004b000009cb0000613d000000000a090433000005450aa00197000000f80b800210000000000aab019f000005470aa000410000000000a904350000000308800210000000f80880008900000000068601cf000000ff0880008c0000000006002019000000210850003900000a8f0000013d000000400200043d0000001f0430018f0000000505300272000006810000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000006790000413d000000000604004b000006900000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f00000000001504350000050b010000410000050b0420009c000000000201801900000040012002100000006002300210000000000121019f00001429000104300000050b01100197000000000113034f00000000026400490000050b0220019700000000012103df000000c002500210000005220220019700000524022001c700000000012103af0000801002000039142714220000040f000000000301001900000060033002700001050b0030019d0000050b0530019700030000000103550000000102200190000009cf0000613d0000003f025000390000054102200197000000400600043d0000000002260019000000000362004b00000000030000190000000103004039000005130420009c000013490000213d0000000103300190000013490000c13d000000400020043f0000000004560436000000020200036700000000030000310000001f075000390000000507700272000006c50000613d000000000832034f0000000009000019000000050a900210000000000ba40019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000006bd0000413d000000000700004b000006c70000613d0000001f0750018f0000000505500272000006d30000613d00000000080000190000000509800210000000000a940019000000000991034f000000000909043b00000000009a04350000000108800039000000000958004b000006cb0000413d000000000807004b000006e20000613d0000000505500210000000000151034f00000000055400190000000307700210000000000805043300000000087801cf000000000878022f000000000101043b0000010007700089000000000171022f00000000017101cf000000000181019f00000000001504350000000001060433000000200110008c00000a110000c13d00000009060000290000000001630049000000230510008a000702040060003d0000000701200360000000000101043b0000051406000041000000000751004b0000000007000019000000000706801900000514055001970000051408100197000000000958004b0000000006008019000000000558013f000005140550009c000000000607c019000000000506004b000001290000c13d0000000004040433000400000004001d0000000801100029000000000412034f000000000504043b000005130450009c000001290000213d0000000504500210000000000343004900000020061000390000051401000041000000000736004b0000000007000019000000000701201900000514033001970000051408600197000000000938004b0000000001008019000000000338013f000005140330009c000000000107c019000000000101004b000001290000c13d000000400100043d00000020031000390000054e055001980000071d0000613d000000000262034f000000000600001900000005076002100000000008730019000000000772034f000000000707043b00000000007804350000000106600039000000000756004b000007150000413d000000000200004b0000071f0000613d00000000004104350000003f02400039000000200400008a000000000242016f0000000002210019000000000412004b00000000040000190000000104004039000005130520009c000013490000213d0000000104400190000013490000c13d000000400020043f0000050b020000410000050b0430009c0000000003028019000000400330021000000000010104330000050b0410009c00000000010280190000006001100210000000000131019f00000000030004140000050b0430009c0000000003028019000000c002300210000000000112019f00000516011001c70000801002000039142714180000040f0000000102200190000001290000613d0000000002000031000000090320006a000000230530008a000000070300002900000020043000390000000203000367000000000443034f000000000404043b0000051406000041000000000754004b0000000007000019000000000706801900000514055001970000051408400197000000000958004b0000000006008019000000000558013f000005140550009c000000000607c019000000000101043b000700000001001d000000000106004b000001290000c13d0000000801400029000000000413034f000000000404043b000005130540009c000001290000213d000000000542004900000020011000390000051406000041000000000751004b0000000007000019000000000706201900000514055001970000051408100197000000000958004b0000000006008019000000000558013f000005140550009c000000000607c019000000000506004b000001290000c13d00000000050004140000000006140019000000000446004b0000000004000019000000010400403900000001044001900000122b0000c13d000000000462004b0000122b0000413d0000050b0450009c000002950000213d0000050b01100197000000000113034f00000000026200490000050b0220019700000000012103df000000c002500210000005220220019700000524022001c700000000012103af0000801002000039142714220000040f000000000301001900000060033002700001050b0030019d0000050b03300197000300000001035500000001022001900000113c0000613d0000003f023000390000054102200197000000400500043d0000000002250019000000000452004b00000000040000190000000104004039000005130620009c000013490000213d0000000104400190000013490000c13d000000400020043f000000000235043600000002040003670000001f063000390000000506600272000007a20000613d000000000740036800000000080000190000000509800210000000000a920019000000000997034f000000000909043b00000000009a04350000000108800039000000000968004b0000079a0000413d000000000600004b000007a40000613d0000001f0630018f0000000503300272000007b00000613d000000000700001900000005087002100000000009820019000000000881034f000000000808043b00000000008904350000000107700039000000000837004b000007a80000413d000000000706004b000007bf0000613d0000000503300210000000000131034f00000000033200190000000306600210000000000703043300000000076701cf000000000767022f000000000101043b0000010006600089000000000161022f00000000016101cf000000000171019f00000000001304350000000001050433000000200110008c00000a110000c13d000000090c0000290000006401c00039000000000114034f0000004403c00039000000000534034f0000002403c00039000000000634034f0000012403c00039000000000734034f0000000508400360000000e403c00039000000000934034f000000c403c00039000000000a34034f000000a403c00039000000000b34034f0000008403c00039000000000c34034f0000000803400360000000000303043b000000000406043b000000000505043b000000000601043b000000000c0c043b000000000b0b043b000000000a0a043b000000000909043b000000000808043b000000000707043b0000000002020433000000400100043d000001c00d10003900000000002d0435000001a002100039000000070d0000290000000000d204350000018002100039000000040d0000290000000000d2043500000160021000390000000000720435000001400210003900000000008204350000012002100039000000000092043500000100021000390000000000a20435000000e0021000390000000000b20435000000c0021000390000000000c20435000000a0021000390000000000620435000000800210003900000000005204350000006002100039000000000042043500000040021000390000000000320435000000200210003900000550030000410000000000320435000001c0030000390000000000310435000005510310009c000013490000213d000001e003100039000000400030043f0000050b040000410000050b0320009c0000000002048019000000400220021000000000010104330000050b0310009c00000000010480190000006001100210000000000121019f00000000020004140000050b0320009c0000000002048019000000c002200210000000000112019f00000516011001c70000801002000039142714180000040f0000000102200190000001290000613d000000000101043b000500000001001d000000400100043d000700000001001d0000054201000041000000000010043900000000010004140000050b0210009c0000050b01008041000000c00110021000000543011001c70000800b02000039142714180000040f00000001022001900000124f0000613d00000007040000290000002002400039000000000101043b000005520300004100000000003204350000008003400039000000000013043500000060014000390000055303000041000000000031043500000040014000390000055403000041000000000031043500000080010000390000000000140435000005550140009c000013490000213d0000000704000029000000a001400039000000400010043f0000050b010000410000050b0320009c0000000002018019000000400220021000000000030404330000050b0430009c00000000030180190000006003300210000000000223019f00000000030004140000050b0430009c0000000003018019000000c001300210000000000121019f00000516011001c70000801002000039142714180000040f0000000102200190000001290000613d000000000301043b000000400100043d0000004202100039000000050400002900000000004204350000002002100039000005560400004100000000004204350000002204100039000000000034043500000042030000390000000000310435000005330310009c000013490000213d0000008003100039000000400030043f0000050b030000410000050b0420009c0000000002038019000000400220021000000000010104330000050b0410009c00000000010380190000006001100210000000000121019f00000000020004140000050b0420009c0000000002038019000000c002200210000000000112019f000012070000013d000005440720009c000013490000213d0000004007200039000000400070043f000000010700003a00000000077204360000000008500350000000000808043b0000000000870435000009cb0000613d000000f809600210000005140a000041000000000606004b000000000a09c01900000545068001970000000006a6019f0000000000670435000000400600043d000500000006001d00000020076000390000000006010433000000000806004b0000088d0000613d000000000800001900000000097800190000002008800039000000000a180019000000000a0a04330000000000a90435000000000968004b000008860000413d000000000176001900000000000104350000000007020433000000000807004b0000089a0000613d000000000800001900000000091800190000002008800039000000000a280019000000000a0a04330000000000a90435000000000978004b000008930000413d000000000117001900000000000104350000000001670019000000050600002900000000001604350000003f011000390001002000000092000000010110017f0000000002610019000000000112004b00000000010000190000000101004039000400000002001d000005130220009c000013490000213d0000000101100190000013490000c13d0000000401000029000000400010043f000005440110009c000013490000213d00000009070000290000004401700039000000000113034f000000000101043b00000004080000290000004002800039000000400020043f000000200280003900000548060000410000000000620435000000150200003900000000002804350000006001100210000000210280003900000000001204350000012401700039000000000213034f000000400600043d000300000006001d000000000202043b000000800620008c00000b3b0000413d0000008006200270000005460720009c000000000602a019000005460720009c0000000007000019000000100700203900000008087001bf000005130960009c000000000807a0190000004007600270000005130960009c000000000706a01900000004098001bf0000050b0670009c000000000908a01900000020087002700000050b0670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c00000001066020390000004107600039000000010770017f0000000307700029000000030870006c00000000080000190000000108004039000005130970009c000013490000213d0000000108800190000013490000c13d000000400070043f00000002076000390000000308000029000000000778043600000021086000390000000508800272000008f80000613d0000000009000019000000050a900210000000000ba70019000000000aa5034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b000008f00000413d000000000800004b000008fa0000613d00000003080000290000000008080433000000000808004b000009cb0000613d00000000080704330000054508800197000000f809600210000000000889019f000005470880004100000000008704350000000306600210000000f80660008900000000026201cf000000ff0660008c00000000020020190000000306000029000000210660003900000b4d0000013d0000050b010000410000050b0350009c000000000501801900000060035002100000004004400210000000000343019f0000050b0420009c0000000002018019000000c001200210000000000113019f0000000802000029142714130000040f000400600000003d000000010220018f0003000000010355000000000301001900000060033002700001050b0030019d0000050b033001980000094c0000613d0000003f04300039000000200500008a000000000454016f000000400500043d0000000004450019000400000005001d000000000554004b00000000050000190000000105004039000005130640009c000013490000213d0000000105500190000013490000c13d000000400040043f0000001f0430018f0000000405000029000000000835043600000005033002720000093c0000613d000000000500001900000005065002100000000007680019000000000661034f000000000606043b00000000006704350000000105500039000000000635004b000009340000413d000900000008001d000000000504004b0000094c0000613d0000000503300210000000000131034f00000009033000290000000304400210000000000503043300000000054501cf000000000545022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000013043500000004010000290000000001010433000000000202004b000009ea0000c13d000000000201004b00000a090000c13d000000400300043d000900000003001d0000051901000041000000000013043500000004013000390000000302000029000000000021043500000024023000390000000201000029142713ff0000040f000000090400002900000000014100490000050b020000410000050b0310009c000000000102801900000a0d0000013d000005440850009c000013490000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b0000000000980435000009cb0000613d000000f80a700210000005140b000041000000000707004b000000000b0ac01900000545079001970000000007b7019f0000000000780435000000400700043d000000400660008a000000000861034f000000000808043b000000800980008c00000a180000413d0000008009800270000005460a80009c000000000908a019000005460a80009c000000000a000019000000100a002039000000080ba001bf000005130c90009c000000000b0aa019000000400a900270000005130c90009c000000000a09a019000000040cb001bf0000050b09a0009c000000000c0ba019000000200ba002700000050b09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa70019000000000b7a004b000000000b000019000000010b004039000005130ca0009c000013490000213d000000010bb00190000013490000c13d0000004000a0043f000000020a900039000000000aa70436000000210b900039000000050bb00272000009ae0000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b000009a60000413d000000000b00004b000009b00000613d000000000b070433000000000b0b004b000009cb0000613d000000000b0a0433000005450bb00197000000f80c900210000000000bbc019f000005470bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c0000000008002019000000210970003900000a290000013d000005440850009c000013490000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b000000000098043500000a890000c13d000005620100004100000000001004350000003201000039000000410000013d0000001f0350018f0000000502500272000009da0000613d00000000040000190000000506400210000000000761034f000000000707043b00000000007604350000000104400039000000000624004b000009d30000413d000000000403004b000009e80000613d00000003033002100000000502200210000000000402043300000000043401cf000000000434022f000000000121034f000000000101043b0000010003300089000000000131022f00000000013101cf000000000141019f000000000012043500000060015002100000142900010430000000000201004b00000b970000c13d0000052e010000410000000000100439000000080100002900000004001004430000050b0100004100000000020004140000050b0320009c0000000002018019000000c0012002100000052f011001c70000800202000039142714180000040f00000001022001900000124f0000613d000000000101043b000000000101004b00000b930000c13d000000400100043d00000044021000390000053703000041000000000032043500000024021000390000001d0300003900000000003204350000051902000041000000000021043500000004021000390000000303000029000002a70000013d0000050b020000410000050b0310009c000000000102801900000009040000290000050b0340009c00000000040280190000004002400210000002490000013d000000400100043d00000044021000390000054f03000041000000000032043500000024021000390000001f03000039000002a20000013d000005440970009c000013490000213d0000004009700039000000400090043f000000000a21034f000000010900003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000009cb0000613d000000f80b800210000005140c000041000000000808004b000000000c0bc0190000054508a001970000000008c8019f0000000000890435000000400900043d000005440890009c000013490000213d000000200860008a000000000881034f000000000808043b000000400a9000390000004000a0043f000000200a900039000005480b0000410000000000ba0435000000150a0000390000000000a904350000006008800210000000210a90003900000000008a0435000000c006600039000000000661034f000000400800043d000000000606043b000700000006001d000000800a60008c00000ca80000413d0000000706000029000000800a600270000005460b60009c000000000a06a019000005460b60009c000000000b000019000000100b002039000000080cb001bf000005130da0009c000000000c0ba019000000400ba00270000005130da0009c000000000b0aa019000000040dc001bf0000050b0ab0009c000000000d0ca019000000200cb002700000050b0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000005130db0009c000013490000213d000000010cc00190000013490000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc0027200000a760000613d000000000d21034f000000000e000019000000050fe002100000000006fb0019000000000ffd034f000000000f0f043b0000000000f60435000000010ee000390000000006ce004b00000a6e0000413d000000000600004b00000a780000613d0000000006080433000000000606004b000009cb0000613d00000000060b04330000054506600197000000f80ca0021000000000066c019f000005470660004100000000006b04350000000306a00210000000f806600089000000070a6001ef000000ff0660008c000000000a00201900000021068000390000000000a6043500000cbb0000013d000000f80a600210000005140b000041000000000606004b000000000b0ac01900000545069001970000000006b6019f0000000000680435000000400600043d000000200770008a000000000871034f000000000808043b000000800980008c00000adc0000413d0000008009800270000005460a80009c000000000908a019000005460a80009c000000000a000019000000100a002039000000080ba001bf000005130c90009c000000000b0aa019000000400a900270000005130c90009c000000000a09a019000000040cb001bf0000050b09a0009c000000000c0ba019000000200ba002700000050b09a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa60019000000000b6a004b000000000b000019000000010b004039000005130ca0009c000013490000213d000000010bb00190000013490000c13d0000004000a0043f000000020a900039000000000aa60436000000210b900039000000050bb0027200000aca0000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b00000ac20000413d000000000b00004b00000acc0000613d000000000b060433000000000b0b004b000009cb0000613d000000000b0a0433000005450bb00197000000f80c900210000000000bbc019f000005470bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c0000000008002019000000210960003900000aed0000013d000005440960009c000013490000213d0000004009600039000000400090043f000000000a21034f000000010900003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000009cb0000613d000000f80b800210000005140c000041000000000808004b000000000c0bc0190000054508a001970000000008c8019f0000000000890435000000400800043d00070040007000920000000709100360000000000909043b000000800a90008c00000bcd0000413d000000800a900270000005460b90009c000000000a09a019000005460b90009c000000000b000019000000100b002039000000080cb001bf000005130da0009c000000000c0ba019000000400ba00270000005130da0009c000000000b0aa019000000040dc001bf0000050b0ab0009c000000000d0ca019000000200cb002700000050b0ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000005130db0009c000013490000213d000000010cc00190000013490000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc0027200000b280000613d000000000d21034f000000000e000019000000050fe002100000000007fb0019000000000ffd034f000000000f0f043b0000000000f70435000000010ee000390000000007ce004b00000b200000413d000000000700004b00000b2a0000613d0000000007080433000000000707004b000009cb0000613d00000000070b04330000054507700197000000f80ca0021000000000077c019f000005470770004100000000007b04350000000307a00210000000f80770008900000000097901cf000000ff0770008c00000000090020190000002107800039000000000097043500000bdf0000013d0000000306000029000005440660009c000013490000213d00000003070000290000004006700039000000400060043f000000010600003a00000000066704360000000007500350000000000707043b0000000000760435000009cb0000613d000000f8082002100000051409000041000000000202004b000000000908c0190000054502700197000000000292019f0000000000260435000000080640006a000000a001100039000000000213034f000000000202043b0000001f0660008a000005140760019700000514082001970000051409000041000000000a78004b000000000a000019000000000a094019000000000778013f000000000862004b0000000009004019000005140770009c000000000a09c01900000000070a004b000001290000c13d0000000808200029000000000783034f000000000707043b000005130970009c000001290000213d00000000097400490000002008800039000005140a000041000000000b98004b000000000b000019000000000b0a20190000051409900197000005140c800197000000000d9c004b000000000a00801900000000099c013f000005140990009c000000000a0bc01900000000090a004b000001290000c13d000000010970008c00000e600000c13d000000000583034f000000000505043b000000010700008a0000051408000041000000000775004b000000000700001900000000070820190000051405500197000005140950009c00000000080080190000051405500167000005140550009c000000000807c019000200600000003d000000000508004b00000e9c0000c13d000000400500043d000200000005001d000005440550009c000013490000213d00000002080000290000004005800039000000400050043f0000002005800039000005470700004100000000007504350000000105000039000000000058043500000e9c0000013d00000004010000290000000001010433000000000201004b00000bba0000613d0000051402000041000000200310008c000000000300001900000000030240190000051401100197000000000401004b000000000200a019000005140110009c000000000203c019000000000102004b000001290000c13d00000009010000290000000001010433000000000201004b0000000002000019000000010200c039000000000221004b000001290000c13d000000000101004b00000bba0000c13d000000400100043d00000064021000390000053503000041000000000032043500000044021000390000053603000041000000000032043500000024021000390000002a03000039000000000032043500000519020000410000000000210435000000040210003900000003030000290000010c0000013d000000400300043d0000002401300039000000060200002900000000002104350000052a010000410000000000130435000900000003001d00000004013000390000000502000029000000000021043500000000010004140000000802000029000000040220008c00000c420000c13d0000000103000031000000200130008c0000000004030019000000200400803900000c740000013d000005440780009c000013490000213d0000004007800039000000400070043f000000000721034f000000010a00003a000000000aa804360000000007700350000000000b07043b0000000000ba0435000009cb0000613d000000f807900210000005140c000041000000000909004b000000000c07c0190000054507b001970000000007c7019f00000000007a0435000000400a00043d0000054407a0009c000013490000213d000000070c0000290000002007c0008a000000000771034f000000000707043b0000004009a00039000000400090043f0000002009a00039000005480b0000410000000000b90435000000150900003900000000009a043500000060077002100000002109a000390000000000790435000000c007c00039000000000771034f000000400900043d000000000707043b000700000007001d000000800b70008c00000d850000413d0000000707000029000000800b700270000005460c70009c000000000b07a019000005460c70009c000000000c000019000000100c002039000000080dc001bf000005130eb0009c000000000d0ca019000000400cb00270000005130eb0009c000000000c0ba019000000040ed001bf0000050b0bc0009c000000000e0da019000000200dc002700000050b0bc0009c000000000d0ca0190000000207e001bf0000ffff0cd0008c00000000070ea019000000100cd00270000000000c0da019000000ff0cc0008c0000000107702039000000200c00008a000500000007001d000000410d700039000000000ccd016f000000000cc90019000000000d9c004b000000000d000019000000010d004039000005130ec0009c000013490000213d000000010dd00190000013490000c13d0000004000c0043f0000000507000029000000020c700039000000000cc90436000000210d700039000000050dd0027200000c2e0000613d000000000e21034f000000000f0000190000000507f00210000000000b7c001900000000077e034f000000000707043b00000000007b0435000000010ff000390000000007df004b00000c260000413d000000000700004b00000c300000613d0000000007090433000000000707004b000009cb0000613d00000000070c04330000054507700197000000050d000029000000f80bd0021000000000077b019f000005470770004100000000007c04350000000307d00210000000f807700089000000070b7001ef000000ff0770008c000000000b00201900000021079000390000000000b7043500000d980000013d0000050b020000410000050b0310009c000000000102801900000009040000290000050b0340009c00000000020440190000004002200210000000c001100210000000000121019f00000530011001c70000000802000029142714180000040f000000090a000029000000000301001900000060033002700000050b03300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000c610000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000c590000413d000000000705004b00000c700000613d0000000506600210000000000761034f00000009066000290000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f0003000000010355000000010220019000000d680000613d0000001f01400039000000600210018f0000000901200029000000000221004b00000000020000190000000102004039000005130410009c000013490000213d0000000102200190000013490000c13d000000400010043f000000200230008c000001290000413d0000004404100039000000240510003900000009020000290000000002020433000000000202004b00000e540000c13d00000020021000390000052c060000410000000000620435000000060600002900000000006504350000000705000029000000000054043500000001040000290000000000410435000005330410009c000013490000213d0000008004100039000900000004001d000000400040043f000005340410009c000013490000213d000000c004100039000000400040043f000000030400002900000009050000290000000000450435000000a0041000390000052d050000410000000000540435000000000401043300000000010004140000000805000029000000040550008c00000f540000c13d0000000102000039000005130130009c000013490000213d00000f6a0000013d000005440680009c000013490000213d0000004006800039000000400060043f000000000621034f000000010a00003a000000000aa804360000000006600350000000000b06043b0000000000ba0435000009cb0000613d000000070d000029000000f806d00210000005140c000041000000000d0d004b000000000c06c0190000054506b001970000000006c6019f00000000006a0435000000400600043d000000200b600039000000000a030433000000000c0a004b00000cc80000613d000000000c000019000000000dbc0019000000200cc00039000000000e3c0019000000000e0e04330000000000ed0435000000000dac004b00000cc10000413d0000000003ba0019000000000003043500000000036a0019000000200b300039000000000a040433000000000c0a004b00000cd70000613d000000000c000019000000000dbc0019000000200cc00039000000000e4c0019000000000e0e04330000000000ed0435000000000dac004b00000cd00000413d0000000004ba0019000000000004043500000000033a0019000000200a3000390000000004050433000000000b04004b00000ce60000613d000000000b000019000000000cab0019000000200bb00039000000000d5b0019000000000d0d04330000000000dc0435000000000c4b004b00000cdf0000413d0000000005a400190000000000050435000000000334001900000020053000390000000004070433000000000a04004b00000cf50000613d000000000a000019000000000b5a0019000000200aa00039000000000c7a0019000000000c0c04330000000000cb0435000000000b4a004b00000cee0000413d00000000055400190000000000050435000000000334001900000020053000390000000004090433000000000704004b00000d040000613d0000000007000019000000000a5700190000002007700039000000000b970019000000000b0b04330000000000ba0435000000000a47004b00000cfd0000413d00000000055400190000000000050435000000000334001900000020053000390000000004080433000000000704004b00000d130000613d000000000700001900000000095700190000002007700039000000000a870019000000000a0a04330000000000a90435000000000947004b00000d0c0000413d000000000554001900000000000504350000000003630049000000000334001900000000003604350000003f04300039000000200300008a000000000434016f0000000007640019000000000447004b00000000040000190000000104004039000005130570009c000013490000213d0000000104400190000013490000c13d000000400070043f0000000905000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b0000051408000041000000000954004b000000000900001900000000090880190000051405500197000005140a400197000000000b5a004b000000000800801900000000055a013f000005140550009c000000000809c019000000000508004b000001290000c13d0000000805400029000000000451034f000000000404043b000005130840009c000001290000213d000000000842004900000020055000390000051409000041000000000a85004b000000000a000019000000000a0920190000051408800197000005140b500197000000000c8b004b000000000900801900000000088b013f000005140880009c00000000090ac019000000000809004b000001290000c13d000000010840008c00000fa90000c13d000000000851034f000000000808043b000000010900008a000005140a000041000000000998004b000000000900001900000000090a20190000051408800197000005140b80009c000000000a0080190000051408800167000005140880009c000000000a09c019000000600800003900000000090a004b000010470000c13d000005440870009c000013490000213d0000004008700039000000400080043f000000200870003900000547090000410000000000980435000000010800003900000000008704350000000008070019000010470000013d000000400200043d0000001f0430018f000000050530027200000d750000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000d6d0000413d000000000604004b00000d840000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000006900000013d000005440790009c000013490000213d0000004007900039000000400070043f000000000721034f000000010b00003a000000000bb904360000000007700350000000000c07043b0000000000cb0435000009cb0000613d000000070e000029000000f807e00210000005140d000041000000000e0e004b000000000d07c0190000054507c001970000000007d7019f00000000007b0435000000400700043d000000200c700039000000000b030433000000000d0b004b00000da50000613d000000000d000019000000000ecd0019000000200dd00039000000000f3d0019000000000f0f04330000000000fe0435000000000ebd004b00000d9e0000413d0000000003cb0019000000000003043500000000037b0019000000200c300039000000000b040433000000000d0b004b00000db40000613d000000000d000019000000000ecd0019000000200dd00039000000000f4d0019000000000f0f04330000000000fe0435000000000ebd004b00000dad0000413d0000000004cb0019000000000004043500000000033b0019000000200b3000390000000004050433000000000c04004b00000dc30000613d000000000c000019000000000dbc0019000000200cc00039000000000e5c0019000000000e0e04330000000000ed0435000000000d4c004b00000dbc0000413d0000000005b400190000000000050435000000000334001900000020053000390000000004060433000000000b04004b00000dd20000613d000000000b000019000000000c5b0019000000200bb00039000000000d6b0019000000000d0d04330000000000dc0435000000000c4b004b00000dcb0000413d00000000055400190000000000050435000000000334001900000020053000390000000004080433000000000604004b00000de10000613d0000000006000019000000000b5600190000002006600039000000000c860019000000000c0c04330000000000cb0435000000000b46004b00000dda0000413d000000000554001900000000000504350000000003340019000000200530003900000000040a0433000000000604004b00000df00000613d000000000600001900000000085600190000002006600039000000000ba60019000000000b0b04330000000000b80435000000000846004b00000de90000413d00000000055400190000000000050435000000000334001900000020053000390000000004090433000000000604004b00000dff0000613d000000000600001900000000085600190000002006600039000000000a960019000000000a0a04330000000000a80435000000000846004b00000df80000413d000000000554001900000000000504350000000003730049000000000334001900000000003704350000003f04300039000000200300008a000000000434016f0000000006740019000000000446004b00000000040000190000000104004039000005130560009c000013490000213d0000000104400190000013490000c13d000000400060043f0000000905000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b0000051408000041000000000954004b000000000900001900000000090880190000051405500197000005140a400197000000000b5a004b000000000800801900000000055a013f000005140550009c000000000809c019000000000508004b000001290000c13d0000000805400029000000000451034f000000000404043b000005130840009c000001290000213d000000000842004900000020055000390000051409000041000000000a85004b000000000a000019000000000a0920190000051408800197000005140b500197000000000c8b004b000000000900801900000000088b013f000005140880009c00000000090ac019000000000809004b000001290000c13d000000010840008c000011570000c13d000000000851034f000000000808043b000000010900008a000005140a000041000000000998004b000000000900001900000000090a20190000051408800197000005140b80009c000000000a0080190000051408800167000005140880009c000000000a09c019000000600800003900000000090a004b000013460000c13d000005440860009c000013490000213d0000004008600039000000400080043f000000200860003900000547090000410000000000980435000000010800003900000000008604350000000008060019000013460000013d000005190200004100000000002104350000000402100039000000030300002900000000003204350000003602000039000000000025043500000531020000410000000000240435000000640210003900000532030000410000010c0000013d000000400800043d000200000008001d000000380870008c00000e8b0000413d00000020097002700000050b0870009c000000000907a0190000050b0870009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000000020a000029000005440aa0009c000013490000213d000000000898019f000000020a0000290000004009a00039000000400090043f000000020980003a00000000099a04360000000005500350000000000505043b0000000000590435000009cb0000613d0000054505500197000000f80a80021000000000055a019f00000549055001c700000000005904350000000305800210000000f80550015f00000000055701cf00000002070000290000002107700039000000000057043500000e9c0000013d0000000208000029000005440880009c000013490000213d00000002090000290000004008900039000000400080043f000000010800003a00000000088904360000000005500350000000000505043b0000000000580435000009cb0000613d000000f8077002100000054505500197000000000575019f00000514055001670000000000580435000000800110008a000000000513034f0000006001000039000000000505043b000000000505004b00000efd0000c13d0000051405000041000000000762004b0000000007000019000000000705801900000514066001970000051408200197000000000968004b0000000005008019000000000668013f000005140660009c000000000507c019000000000505004b000001290000c13d000000070500002900000000060504330000000505000029000000000705043300000004050000290000000008050433000000030500002900000000090504330000000205000029000000000a0504330000000805200029000000000253034f000000000202043b000005130b20009c000001290000213d000000000b2400490000002005500039000005140c000041000000000db5004b000000000d000019000000000d0c2019000005140bb00197000005140e500197000000000fbe004b000000000c008019000000000bbe013f000005140bb0009c000000000c0dc019000000000b0c004b000001290000c13d0000000006670019000000000686001900000000069600190000000006a60019000000000626001900000000070104330000000006760019000000400700043d0000051306600197000000380860008c000010870000413d00000020096002700000050b0860009c000000000906a0190000050b0860009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000005440a70009c000013490000213d000000000898019f0000004009700039000000400090043f000000000943034f000000020480003a00000000044704360000000009900350000000000909043b0000000000940435000009cb0000613d0000054509900197000000f80a80021000000000099a019f0000054b099001c700000000009404350000000304800210000000f80440015f00000000044601cf00000021067000390000000000460435000010970000013d000005420100004100000000001004390000050b0100004100000000020004140000050b0320009c0000000002018019000000c00120021000000543011001c70000800b02000039142714180000040f00000001022001900000124f0000613d000000400200043d000000000101043b000000800310008c00000fd10000413d0000008003100270000005460410009c000000000301a019000005460410009c0000000004000019000000100400203900000008054001bf000005130630009c000000000504a0190000004004300270000005130630009c000000000403a01900000004035001bf0000050b0640009c000000000305a01900000020064002700000050b0540009c000000000604a01900000002053001bf0000ffff0460008c000000000503a0190000001003600270000000000306a019000000ff0330008c00000001055020390000004103500039000000010330017f0000000003320019000000000423004b00000000040000190000000104004039000005130630009c000013490000213d0000000104400190000013490000c13d000000400030043f00000002035000390000000006320436000000020300036700000000040000310000002107500039000000050770027200000f420000613d000000000843034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000f3a0000413d000000000700004b00000f440000613d0000000007020433000000000707004b000009cb0000613d00000000070604330000054507700197000000f808500210000000000778019f000005470770004100000000007604350000000305500210000000f80550008900000000015101cf000000ff0550008c0000000001002019000000210520003900000fe40000013d0000050b030000410000050b0520009c000000000203801900000040022002100000050b0540009c00000000040380190000006004400210000000000224019f0000050b0410009c0000000001038019000000c001100210000000000112019f0000000802000029142714130000040f000700600000003d000600800000003d000000010220018f000300000001035500000060011002700001050b0010019d0000050b0310019800000f970000613d0000003f01300039000000200400008a000000000141016f000000400400043d0000000001140019000700000004001d000000000441004b00000000040000190000000104004039000005130510009c000013490000213d0000000104400190000013490000c13d000000400010043f0000001f0130018f000000070400002900000000083404360000000304000367000000050330027200000f870000613d000000000500001900000005065002100000000007680019000000000664034f000000000606043b00000000006704350000000105500039000000000635004b00000f7f0000413d000600000008001d000000000501004b00000f970000613d0000000503300210000000000434034f00000006033000290000000301100210000000000503043300000000051501cf000000000515022f000000000404043b0000010001100089000000000414022f00000000011401cf000000000151019f000000000013043500000007010000290000000001010433000000000202004b000010090000c13d000000000201004b000010820000c13d000000400300043d000800000003001d0000051901000041000000000013043500000004013000390000000302000029000000000021043500000024023000390000000901000029142713ff0000040f00000008040000290000095d0000013d000000380840008c000010360000413d00000020094002700000050b0840009c000000000904a0190000050b0840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000005440a70009c000013490000213d000000000898019f0000004009700039000000400090043f000000000a21034f000000020980003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000009cb0000613d000005450aa00197000000f80b800210000000000aab019f000005490aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf000000210970003900000000008904350000000008070019000010470000013d000005440320009c000013490000213d0000004003200039000000400030043f000000010300003a000000000532043600000000040000310000000203000367000000000643034f0000000006600350000000000606043b0000000000650435000009cb0000613d000000f8071002100000051408000041000000000101004b000000000807c0190000054501600197000000000181019f0000000000150435000000400100043d00000020061000390000000005020433000000000705004b00000ff20000613d000000000700001900000000086700190000002007700039000000000927001900000000090904330000000000980435000000000857004b00000feb0000413d000000000265001900000557060000410000000000620435000000020250003900000000002104350000004102500039000000010520017f0000000002150019000000000552004b00000000050000190000000105004039000005130620009c000013490000213d0000000105500190000013490000c13d0000000906000029000001c405600039000000400020043f000000000253034f0000000005640049000000230650008a000000000202043b00000ea20000013d000000000201004b000010200000c13d0000052e010000410000000000100439000000080100002900000004001004430000050b0100004100000000020004140000050b0320009c0000000002018019000000c0012002100000052f011001c70000800202000039142714180000040f00000001022001900000124f0000613d000000000101043b000000000101004b000009fd0000613d00000007010000290000000001010433000000000201004b000010340000613d0000051402000041000000200310008c000000000300001900000000030240190000051401100197000000000401004b000000000200a019000005140110009c000000000203c019000000000102004b000001290000c13d00000006010000290000000001010433000000000201004b0000000002000019000000010200c039000000000221004b000001290000c13d000000000101004b00000bab0000613d0000000001000019000014280001042e000005440870009c000013490000213d0000004008700039000000400080043f000000000921034f000000010800003a00000000088704360000000009900350000000000909043b0000000000980435000009cb0000613d000000f80a40021000000545099001970000000009a9019f000005140990016700000000009804350000000008070019000000400700043d000005440970009c000013490000213d0000004009700039000000400090043f000000000221034f000000010c00003a0000000009c704360000000002200350000000000b02043b0000000000b90435000009cb0000613d0000054502b001970000054a0a2001c70000000000a9043500000000090604330000000009490019000000000a0804330000000009a90019000000000a0704330000000009a90019000000400a00043d0000051309900197000000380d90008c0000117f0000413d000000200d9002700000050b0c90009c000000000d09a0190000050b0c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d002039000005440ea0009c000013490000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000009cb0000613d000000f80bc0021000000000022b019f0000054b022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a0003900000000002904350000118c0000013d0000050b020000410000050b0310009c0000000001028019000000060400002900000a0d0000013d000005440870009c000013490000213d0000004008700039000000400080043f000000000843034f000000010400003a00000000044704360000000008800350000000000808043b0000000000840435000009cb0000613d0000054508800197000000f806600210000000000686019f0000054a066000410000000000640435000000400400043d00000020064000390000000008070433000000000908004b000010a40000613d0000000009000019000000000a6900190000002009900039000000000b790019000000000b0b04330000000000ba0435000000000a89004b0000109d0000413d000000000768001900000000000704350000000007480019000000200970003900000007080000290000000008080433000000000a08004b000010b40000613d000000000a000019000000000b9a0019000000200aa00039000000070ca00029000000000c0c04330000000000cb0435000000000b8a004b000010ad0000413d000000000998001900000000000904350000000007780019000000200970003900000005080000290000000008080433000000000a08004b000010c40000613d000000000a000019000000000b9a0019000000200aa00039000000050ca00029000000000c0c04330000000000cb0435000000000b8a004b000010bd0000413d000000000998001900000000000904350000000007780019000000200970003900000004080000290000000008080433000000000a08004b000010d40000613d000000000a000019000000000b9a0019000000200aa00039000000040ca00029000000000c0c04330000000000cb0435000000000b8a004b000010cd0000413d000000000998001900000000000904350000000007780019000000200970003900000003080000290000000008080433000000000a08004b000010e40000613d000000000a000019000000000b9a0019000000200aa00039000000030ca00029000000000c0c04330000000000cb0435000000000b8a004b000010dd0000413d000000000998001900000000000904350000000007780019000000200970003900000002080000290000000008080433000000000a08004b000010f40000613d000000000a000019000000000b9a0019000000200aa00039000000020ca00029000000000c0c04330000000000cb0435000000000b8a004b000010ed0000413d00000000099800190000000000090435000000000553034f00000000037800190000001f0720018f00000020083000390000000509200272000011050000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000010fd0000413d000000000a07004b000011140000613d0000000509900210000000000595034f00000000089800190000000307700210000000000908043300000000097901cf000000000979022f000000000505043b0000010007700089000000000575022f00000000057501cf000000000595019f00000000005804350000000002230019000000200520003900000000000504350000000003010433000000000703004b000011220000613d000000000700001900000000085700190000002007700039000000000917001900000000090904330000000000980435000000000837004b0000111b0000413d000000000153001900000000000104350000000001420049000000000113001900000000001404350000003f01100039000000010210017f0000000001420019000000000221004b00000000020000190000000102004039000005130310009c000013490000213d0000000102200190000013490000c13d000000400010043f0000050b010000410000050b0260009c0000000006018019000000400260021000000000030404330000050b0430009c00000000030180190000006003300210000000000223019f000012020000013d0000001f0430018f0000000502300272000011470000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000011400000413d000000000504004b000011550000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000142900010430000000380840008c000013350000413d00000020094002700000050b0840009c000000000904a0190000050b0840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000005440a60009c000013490000213d000000000898019f0000004009600039000000400090043f000000000a21034f000000020980003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000009cb0000613d000005450aa00197000000f80b800210000000000aab019f000005490aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf000000210960003900000000008904350000000008060019000013460000013d000005440da0009c000013490000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000009cb0000613d000000f809900210000000000229019f0000054a0220004100000000002d0435000000400200043d00000020092000390000054c0b0000410000000000b90435000000210c200039000000000b0a0433000000000d0b004b0000119c0000613d000000000d000019000000000ecd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ebd004b000011950000413d000000000acb001900000000000a0435000000000a2b0019000000210ca00039000000000b060433000000000d0b004b000011ab0000613d000000000d000019000000000ecd0019000000200dd00039000000000f6d0019000000000f0f04330000000000fe0435000000000ebd004b000011a40000413d0000000006cb001900000000000604350000000006ab0019000000210b600039000000000a080433000000000c0a004b000011ba0000613d000000000c000019000000000dbc0019000000200cc00039000000000e8c0019000000000e0e04330000000000ed0435000000000dac004b000011b30000413d0000000008ba00190000000000080435000000000551034f00000000016a00190000001f0640018f0000002108100039000000050a400272000011cb0000613d000000000b000019000000050cb00210000000000dc80019000000000cc5034f000000000c0c043b0000000000cd0435000000010bb00039000000000cab004b000011c30000413d000000000b06004b000011da0000613d000000050aa002100000000005a5034f0000000008a800190000000306600210000000000a080433000000000a6a01cf000000000a6a022f000000000505043b0000010006600089000000000565022f00000000056501cf0000000005a5019f00000000005804350000000001410019000000210510003900000000000504350000000004070433000000000604004b000011e80000613d000000000600001900000000085600190000002006600039000000000a760019000000000a0a04330000000000a80435000000000846004b000011e10000413d0000000005540019000000000005043500000000012100490000000001140019000000010410003900000000004204350000004001100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000005130410009c000013490000213d0000000103300190000013490000c13d000000400010043f0000050b010000410000050b0390009c0000000009018019000000400390021000000000020204330000050b0420009c00000000020180190000006002200210000000000232019f00000000030004140000050b0430009c0000000003018019000000c001300210000000000121019f00000516011001c70000801002000039142714180000040f0000000102200190000001290000613d0000000203000367000000000101043b000700000001001d0000000901000029000000e404100039000000000143034f000000000101043b0000051501100198000400000004001d0000122f0000c13d000000800140008a000000000213034f000000400140008a000000000513034f000000000402043b000000000505043b00000000624500a9000000000605004b000012220000613d00000000655200d9000000000445004b0000122b0000c13d0000008001100039000000000113034f000000000101043b000500000021001d000000050110006b000000000100001900000001010040390000000101100190000012340000613d000005620100004100000000001004350000001101000039000000410000013d00000009010000290000012401100039000000000113034f000000000101043b000500000001001d00000558010000410000000000100439000000060100002900000004001004430000050b0100004100000000020004140000050b0320009c0000000002018019000000c0012002100000052f011001c70000800a02000039142714180000040f00000001022001900000124f0000613d000000000101043b000000050110006b000012500000a13d000000400100043d00000064021000390000056003000041000000000032043500000044021000390000056103000041000000000032043500000024021000390000002203000039000001070000013d000000000001042f0000000004000031000000090140006a000000230210008a000000040100002900000100011000390000000203000367000000000113034f000000000101043b0000051405000041000000000621004b0000000006000019000000000605801900000514022001970000051407100197000000000827004b0000000005008019000000000227013f000005140220009c000000000506c019000000000205004b000001290000c13d0000000802100029000000000123034f000000000101043b000005130510009c000001290000213d000000000514004900000020062000390000051402000041000000000756004b0000000007000019000000000702201900000514055001970000051408600197000000000958004b0000000002008019000000000558013f000005140550009c000000000207c019000000000202004b000001290000c13d0000003f02100039000000200500008a000000000552016f000000400200043d0000000005520019000000000725004b00000000070000190000000107004039000005130850009c000013490000213d0000000107700190000013490000c13d000000400050043f00000000051204360000000007610019000000000447004b000001290000213d000000000463034f0000001f0310018f0000000506100272000012970000613d000000000700001900000005087002100000000009850019000000000884034f000000000808043b00000000008904350000000107700039000000000867004b0000128f0000413d000000000703004b000012a60000613d0000000506600210000000000464034f00000000066500190000000303300210000000000706043300000000073701cf000000000737022f000000000404043b0000010003300089000000000434022f00000000033401cf000000000373019f000000000036043500000000011500190000000000010435000000400100043d0000000003020433000000410330008c000012b90000c13d00000041032000390000000003030433000000ff0330018f0000001d0430008a000000030600008a000000000464004b000012bf0000213d00000044021000390000055f03000041000000000032043500000024021000390000001603000039000002a20000013d00000044021000390000055903000041000000000032043500000024021000390000001d03000039000002a20000013d0000000004050433000000400220003900000000020204330000055a0520009c000012ca0000413d00000044021000390000055e03000041000000000032043500000024021000390000000903000039000002a20000013d0000006005100039000000000025043500000040021000390000000000420435000000200210003900000000003204350000000702000029000000000021043500000000000004350000050b0200004100000000030004140000050b0430009c00000000030280190000050b0410009c00000000010280190000004001100210000000c002300210000000000112019f0000055b011001c70000000102000039142714180000040f000000000301001900000060033002700000050b03300197000000200430008c000000000403001900000020040080390000001f0540018f0000000504400272000012f00000613d00000000060000190000000507600210000000000871034f000000000808043b00000000008704350000000106600039000000000746004b000012e90000413d000000000605004b000012fe0000613d00000003055002100000000504400210000000000604043300000000065601cf000000000656022f000000000741034f000000000707043b0000010005500089000000000757022f00000000055701cf000000000565019f0000000000540435000100000003001f0003000000010355000000400400043d0000000102200190000013150000613d00000000010004330000051501100197000000060210006c0000000002000019000000010200c039000000000101004b0000000001000019000000010100603900000000011201a00000055c01000041000000000100c01900000000001404350000050b010000410000050b0240009c000000000401801900000040014002100000055d011001c7000014280001042e0000001f0230018f0000000505300272000013210000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000013190000413d000000000602004b000013300000613d0000000505500210000000000151034f00000000055400190000000302200210000000000605043300000000062601cf000000000626022f000000000101043b0000010002200089000000000121022f00000000012101cf000000000161019f00000000001504350000050b010000410000050b0240009c00000000040180190000004001400210000006940000013d000005440860009c000013490000213d0000004008600039000000400080043f000000000921034f000000010800003a00000000088604360000000009900350000000000909043b0000000000980435000009cb0000613d000000f80a40021000000545099001970000000009a9019f000005140990016700000000009804350000000008060019000000400600043d000005440960009c0000134d0000a13d000005620100004100000000001004350000004101000039000000410000013d0000004009600039000000400090043f000000000221034f000000010c00003a0000000009c604360000000002200350000000000b02043b0000000000b90435000009cb0000613d0000054502b001970000054a0a2001c70000000000a9043500000000090704330000000009490019000000000a0804330000000009a90019000000000a0604330000000009a90019000000400a00043d0000051309900197000000380d90008c000013850000413d000000200d9002700000050b0c90009c000000000d09a0190000050b0c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d002039000005440ea0009c000013490000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000009cb0000613d000000f80bc0021000000000022b019f0000054b022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a000390000000000290435000013920000013d000005440da0009c000013490000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000009cb0000613d000000f809900210000000000229019f0000054a0220004100000000002d0435000000400200043d0000002009200039000005160b0000410000000000b90435000000210c200039000000000b0a0433000000000d0b004b000013a20000613d000000000d000019000000000ecd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ebd004b0000139b0000413d000000000acb001900000000000a0435000000000a2b0019000000210ca00039000000000b070433000000000d0b004b000013b10000613d000000000d000019000000000ecd0019000000200dd00039000000000f7d0019000000000f0f04330000000000fe0435000000000ebd004b000013aa0000413d0000000007cb001900000000000704350000000007ab0019000000210b700039000000000a080433000000000c0a004b000013c00000613d000000000c000019000000000dbc0019000000200cc00039000000000e8c0019000000000e0e04330000000000ed0435000000000dac004b000013b90000413d0000000008ba00190000000000080435000000000551034f00000000017a00190000001f0740018f0000002108100039000000050a400272000013d10000613d000000000b000019000000050cb00210000000000dc80019000000000cc5034f000000000c0c043b0000000000cd0435000000010bb00039000000000cab004b000013c90000413d000000000b07004b000013e00000613d000000050aa002100000000005a5034f0000000008a800190000000307700210000000000a080433000000000a7a01cf000000000a7a022f000000000505043b0000010007700089000000000575022f00000000057501cf0000000005a5019f00000000005804350000000001410019000000210510003900000000000504350000000004060433000000000704004b000013ee0000613d000000000700001900000000085700190000002007700039000000000a670019000000000a0a04330000000000a80435000000000847004b000013e70000413d0000000005540019000000000005043500000000012100490000000001140019000000010410003900000000004204350000004001100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000005130410009c000013490000213d0000000103300190000013490000c13d000011f80000013d00000000030104330000000002320436000000000403004b0000140b0000613d000000000400001900000000052400190000002004400039000000000614001900000000060604330000000000650435000000000534004b000014040000413d000000000123001900000000000104350000001f01300039000000200300008a000000000131016f0000000001120019000000000001042d000000000001042f00001416002104210000000102000039000000000001042d0000000002000019000000000001042d0000141b002104230000000102000039000000000001042d0000000002000019000000000001042d00001420002104210000000102000039000000000001042d0000000002000019000000000001042d00001425002104230000000102000039000000000001042d0000000002000019000000000001042d0000142700000432000014280001042e00001429000104300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000df9c158800000000000000000000000000000000000000000000000000000000df9c158900000000000000000000000000000000000000000000000000000000e2f318e300000000000000000000000000000000000000000000000000000000eeb8cb0900000000000000000000000000000000000000000000000000000000202bcce700000000000000000000000000000000000000000000000000000000a28c1aee000000000000000000000000000000000000000000000000ffffffffffffffff8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff02000000000000000000000000000000000000000000000000000000000000007261746f720000000000000000000000000000000000000000000000000000004661696c656420746f20706179207468652066656520746f20746865206f706508c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000840000000000000000000000000000000000000000000000000000000100000000000000000000000000000000ffffffff000000000000000000000000000000000000000000000000000000009c4d535affffffffffffffffffffffffffffffffffffffffffffffffffffffff9c4d535b00000000000000000000000000000000000000000000000000000000ecf95b8a000000000000000000000000000000000000000000000000000000003cda3351000000000000000000000000000000000000000000000000000000005d3827000000000000000000000000000000000000000000000000000000000000000000ffffffff00000000000000000000000000000000000000000000000001000001000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffdf4f766572666c6f7700000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000008000000000000000008c5a344500000000000000000000000000000000000000000000000000000000949431dc00000000000000000000000000000000000000000000000000000000dd62ed3e000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000044000000800000000000000000095ea7b3000000000000000000000000000000000000000000000000000000005361666545524332303a206c6f772d6c6576656c2063616c6c206661696c65641806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b83020000020000000000000000000000000000002400000000000000000000000000000000000000000000000000000000000000440000000000000000000000005361666545524332303a20617070726f76652066726f6d206e6f6e2d7a65726f20746f206e6f6e2d7a65726f20616c6c6f77616e636500000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff7f000000000000000000000000000000000000000000000000ffffffffffffff3f6f742073756363656564000000000000000000000000000000000000000000005361666545524332303a204552433230206f7065726174696f6e20646964206e416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000000000000000000000000000000000000000006400000000000000000000000054686520617070726f76616c4261736564207061796d617374657220696e707574206d757374206265206174206c65617374203638206279746573206c6f6e670000000000000000000000000000000000000084000000800000000000000000556e737570706f72746564207061796d617374657220666c6f77000000000000546865207374616e64617264207061796d617374657220696e707574206d757374206265206174206c656173742034206279746573206c6f6e67000000000000e1239cd8000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000024000000a0000000000000000000000000000000000000000000000000000000000000000000000001ffffffe09a8a0592ac89c5ad3bc6df8224c17b485976f597df104ee20d0df415241f670b0200000200000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffbf00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00000000000000000000000000000000ffffffffffffffffffffffffffffffff81000000000000000000000000000000000000000000000000000000000000009400000000000000000000000000000000000000000000000000000000000000b800000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000000f8000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000007ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff6b656363616b3235362072657475726e656420696e76616c6964206461746100848e1bfa1ac4e3576b728bda6721b215c70a7799a5b4866282a71bab954baac8000000000000000000000000000000000000000000000000fffffffffffffe1fc2f8787176b8ac6bf7215b4adcc1e069bf4ab82d9ab1df05a57a91d425935b6ead7c5bef027816a800da1736444fb58a807ef4c9603b7848673f7e3a68eb14a519b453ce45aaaaf3a300f5a9ec95869b4f28ab10430b572ee218c3a6a5e07d6f000000000000000000000000000000000000000000000000ffffffffffffff5f190100000000000000000000000000000000000000000000000000000000000080800000000000000000000000000000000000000000000000000000000000009cc7f708afc65944829bd487b90b72536b1951864fbfc14e125fc972a6507f395369676e6174757265206c656e67746820697320696e636f72726563740000007fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a10000000000000000000000000000000000000080000000000000000000000000202bcce7000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000496e76616c69642073000000000000000000000000000000000000000000000076206973206e656974686572203237206e6f722032380000000000000000000075650000000000000000000000000000000000000000000000000000000000004e6f7420656e6f7567682062616c616e636520666f7220666565202b2076616c4e487b71000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000456e636f64696e6720756e737570706f7274656420747800000000000000000000000000000000000000000000000000000000000000000000000000000000009ca42e6981d147c944c67468396472d007d7f04ef9344c9f6cf97a796a6536cd", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/DefaultAccountNoSecurity.json b/.test-node-subtree/src/deps/contracts/DefaultAccountNoSecurity.json new file mode 100644 index 00000000..18267058 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/DefaultAccountNoSecurity.json @@ -0,0 +1,547 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "DefaultAccountNoSecurity", + "sourceName": "cache-zk/solpp-generated-contracts/DefaultAccountNoSecurity.sol", + "abi": [ + { + "stateMutability": "payable", + "type": "fallback" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "executeTransaction", + "outputs": [ + { + "internalType": "bytes", + "name": "returnData", + "type": "bytes" + } + ], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "executeTransactionFromOutside", + "outputs": [], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "payForTransaction", + "outputs": [], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "prepareForPaymaster", + "outputs": [], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "_suggestedSignedHash", + "type": "bytes32" + }, + { + "components": [ + { + "internalType": "uint256", + "name": "txType", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "from", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "to", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "gasPerPubdataByteLimit", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "maxPriorityFeePerGas", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "paymaster", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + }, + { + "internalType": "uint256[4]", + "name": "reserved", + "type": "uint256[4]" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "signature", + "type": "bytes" + }, + { + "internalType": "bytes32[]", + "name": "factoryDeps", + "type": "bytes32[]" + }, + { + "internalType": "bytes", + "name": "paymasterInput", + "type": "bytes" + }, + { + "internalType": "bytes", + "name": "reservedDynamic", + "type": "bytes" + } + ], + "internalType": "struct Transaction", + "name": "_transaction", + "type": "tuple" + } + ], + "name": "validateTransaction", + "outputs": [ + { + "internalType": "bytes4", + "name": "magic", + "type": "bytes4" + } + ], + "stateMutability": "payable", + "type": "function" + }, + { + "stateMutability": "payable", + "type": "receive" + } + ], + "bytecode": "0x0004000000000002000b00000000000200000000030100190000006007300270000004f50670019700030000006103550002000000010355000004f50070019d0000008004000039000000400040043f00000001022001900000002c0000c13d000000040260008c000000340000413d000000000201043b000000e002200270000004f70320009c0000003f0000a13d000004f80320009c000000930000613d000004f90320009c000000c20000613d000004fa0220009c000000360000c13d000000040260008a000000200320008c000001240000413d0000000401100370000000000101043b000004fd0310009c000001240000213d0000000001120049000004fe02000041000002600310008c00000000030000190000000003024019000004fe01100197000000000401004b000000000200a019000004fe0110009c000000000203c019000000000102004b000010610000613d000001240000013d0000000001000416000000000101004b000001240000c13d000000200100003900000100001004430000012000000443000004f601000041000013cf0001042e000000000106004b000010610000613d0000000001000411000080010110008c000010610000c13d000005460100004100000000001004350000000101000039000000040010043f0000054701000041000013d000010430000004fb0320009c0000010e0000613d000900000004001d000004fc0220009c000000360000c13d000000040260008a000000600220008c000001240000413d0000004402100370000000000302043b000004fd0230009c000001240000213d00000004043000390000000005460049000004fe02000041000002600750008c00000000070000190000000007024019000004fe08500197000000000908004b000000000200a019000004fe0880009c000000000207c019000000000202004b000001240000c13d0000000002000411000080010220008c000010610000c13d0000000002000412000004ff072001970000000002000410000000000727004b000010610000c13d0000022403300039000000000731034f000000000707043b0000001f0550008a000004fe08000041000000000957004b00000000090000190000000009088019000004fe05500197000004fe0a700197000000000b5a004b000000000800801900000000055a013f000004fe0550009c000000000809c019000000000508004b000001240000c13d0000000005470019000000000451034f000000000404043b000004fd0740009c000001240000213d00000000074600490000002005500039000004fe08000041000000000975004b00000000090000190000000009082019000004fe07700197000004fe0a500197000000000b7a004b000000000800801900000000077a013f000004fe0770009c000000000809c019000000000708004b000001240000c13d000000030740008c000002470000213d0000050301000041000000800010043f0000002001000039000000840010043f0000003a01000039000000a40010043f0000052701000041000000c40010043f0000052801000041000000e40010043f0000052501000041000013d000010430000000040260008a000000600220008c000001240000413d0000004402100370000000000302043b000004fd0230009c000001240000213d00000004023000390000000005260049000004fe04000041000002600850008c00000000080000190000000008044019000004fe09500197000000000a09004b000000000400a019000004fe0990009c000000000408c019000000000404004b000001240000c13d0000000004000411000080010440008c000010610000c13d0000000004000412000004ff044001970000000008000410000000000484004b000010610000c13d0000004404300039000000000441034f0000012408300039000000000381034f000000000404043b000004ff04400197000000000303043b000005050930009c000002030000413d0000050301000041000000800010043f0000002001000039000000840010043f0000000801000039000000a40010043f0000051001000041000000c40010043f0000051101000041000013d000010430000000040360008a000000600230008c000001240000413d0000004402100370000000000202043b000004fd0420009c000001240000213d0000000003230049000004fe04000041000002600530008c00000000050000190000000005044019000004fe03300197000000000603004b000000000400a019000004fe0330009c000000000405c019000000000304004b000001240000c13d0000000003000411000080010330008c000010610000c13d0000000003000412000004ff033001970000000004000410000000000343004b000010610000c13d000000a403200039000000000331034f0000006402200039000000000121034f000000000101043b000000000203043b000000000302004b000001eb0000c13d00000000040004150000000b0440008a00000020044000c90000000001000414000b00000000001d000900000004001d000004f502000041000004f50310009c0000000001028019000000c001100210000080010200003913ce13ba0000040f000000090300002900030000000103550000006001100270000104f50010019d000000050130027000000001012001950000000101200190000010610000c13d000000400100043d00000064021000390000050103000041000000000032043500000044021000390000050203000041000000000032043500000024021000390000002503000039000000000032043500000503020000410000000000210435000000040210003900000020030000390000000000320435000004f502000041000004f50310009c0000000001028019000000400110021000000504011001c7000013d000010430000000040260008a000000600220008c000001240000413d0000004402100370000000000202043b000900000002001d000004fd0220009c000001240000213d0000000902000029000800040020003d000000080260006a000004fe03000041000002600420008c00000000040000190000000004034019000004fe02200197000000000502004b000000000300a019000004fe0220009c000000000304c019000000000203004b000001260000613d0000000001000019000013d0000104300000002402100370000000000202043b000700000002001d0000000002000411000080010220008c000010610000c13d0000000002000412000004ff022001970000000003000410000600000003001d000000000232004b000010610000c13d00000000020004140000052903000041000000a00030043f0000000903000029000501040030003d0000000501100360000000000101043b000000a40010043f0000002401000039000000800010043f000000e001000039000000400010043f000000c0012002100000050c011001970000052a011001c70000800302000039000000000300001900000000040000190000000005000019000000000600001913ce13ba0000040f000300000001035500000000030100190000006003300270000104f50030019d000004f5083001970000003f038000390000050f04300197000000400600043d0000000003640019000000000443004b00000000040000190000000104004039000004fd0530009c000012f00000213d0000000104400190000012f00000c13d000000400030043f000000000786043600000002030003670000000004000031000000000543034f0000001f098000390000000509900272000001680000613d000000000a000019000000050ba00210000000000cb70019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000001600000413d000000000900004b0000016a0000613d0000001f0980018f0000000508800272000001760000613d000000000a000019000000050ba00210000000000cb70019000000000bb1034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b0000016e0000413d000000000a09004b000001850000613d0000000508800210000000000181034f00000000088700190000000309900210000000000a080433000000000a9a01cf000000000a9a022f000000000101043b0000010009900089000000000191022f00000000019101cf0000000001a1019f000000000018043500000001012001900000023d0000613d000000070100006b000012390000c13d0000000501000029000001000110008a000000000113034f000000000101043b000000010210008c0000025a0000213d000000000201004b000002a90000613d000000010110008c000002970000c13d0000052b010000410000000000100439000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000052c011001c70000800b0200003913ce13bf0000040f00000001022001900000127a0000613d000000400300043d000000000401043b000000800140008c000004760000413d00000080014002700000052f0240009c000000000104a0190000052f0240009c0000000002000019000000100200203900000008052001bf000004fd0610009c000000000502a0190000004002100270000004fd0610009c000000000201a01900000004015001bf000004f50620009c000000000105a0190000002006200270000004f50520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000004fd0610009c000012f00000213d0000000102200190000012f00000c13d000000400010043f000000020150003900000000061304360000000201000367000000000200003100000021075000390000000507700272000001d90000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000001d10000413d000000000700004b000001db0000613d0000000007030433000000000707004b000009f80000613d00000000070604330000052e07700197000000f808500210000000000778019f000005300770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c00000000040020190000002105300039000004890000013d00000000431200a900000000422300d9000000000112004b000012560000c13d00000000040004150000000a0440008a00000020044000c90000000001000414000a00000000001d000000000203004b000000ea0000613d000004f502000041000004f50410009c0000000001028019000000c00110021000000500011001c700008009020000390000800104000039000000000500001913ce13ba0000040f00000000030004150000000a0330008a00000020033000c9000000f20000013d000000a008800039000000000881034f000000000808043b0000001f0550008a000004fe09000041000000000a58004b000000000a000019000000000a098019000004fe05500197000004fe0b800197000000000c5b004b000000000900801900000000055b013f000004fe0550009c00000000090ac019000000000509004b000001240000c13d0000000002280019000000000521034f000000000805043b000004fd0580009c000001240000213d00000000058600490000002009200039000004fe02000041000000000a59004b000000000a000019000000000a022019000004fe05500197000004fe0b900197000000000c5b004b000000000200801900000000055b013f000004fe0550009c00000000020ac019000000000202004b000001240000c13d0000000002000414000004f50520009c000000b80000213d000080060540008c0000000005000019000003d90000c13d000000040580008c0000000005000019000003d90000413d000000000a91034f0000000105000039000000000a0a043b000005060aa00197000005070ba0009c000003d50000213d0000050a0ba0009c000003d90000613d0000050b0aa0009c000003d90000613d0000000005000019000003d90000013d0000000001060433000004f502000041000004f50310009c0000000001028019000004f50370009c000000000702801900000040027002100000006001100210000000000121019f000013d000010430000000000751034f000000000707043b0000050607700197000005120870009c000010610000613d000005130770009c0000034f0000c13d000000430440008c000003b60000213d0000050301000041000000800010043f0000002001000039000000840010043f0000004001000039000000a40010043f0000052301000041000000c40010043f0000052401000041000000900000013d000000020210008c000002f70000613d000000710110008c000002970000c13d0000000902000029000001c401200039000000000113034f0000000002240049000000230220008a000000000101043b000004fe05000041000000000621004b00000000060000190000000006058019000004fe02200197000004fe07100197000000000827004b0000000005008019000000000227013f000004fe0220009c000000000506c019000000000205004b000001240000c13d0000000801100029000000000213034f000000000202043b000004fd0520009c000001240000213d00000000052400490000002001100039000004fe06000041000000000751004b00000000070000190000000007062019000004fe05500197000004fe08100197000000000958004b0000000006008019000000000558013f000004fe0550009c000000000607c019000000000506004b000001240000c13d00000000050004140000000006120019000000000226004b000000000200001900000001020040390000000102200190000012560000c13d000000000264004b000012560000413d000005360250009c000006c40000413d000000400100043d000000440210003900000510030000410000000000320435000000240210003900000008030000390000029d0000013d000000400100043d00000044021000390000054803000041000000000032043500000024021000390000001703000039000000000032043500000503020000410000000000210435000000040210003900000020030000390000000000320435000004f502000041000004f50310009c0000000001028019000000400110021000000522011001c7000013d0000104300000000501300360000000400200043d000700000002001d000000000101043b000000800210008c000003570000413d00000080021002700000052f0610009c000000000201a0190000052f0610009c0000000006000019000000100600203900000008076001bf000004fd0820009c000000000706a0190000004006200270000004fd0820009c000000000602a01900000004087001bf000004f50260009c000000000807a0190000002007600270000004f50260009c000000000706a01900000002028001bf0000ffff0670008c000000000208a0190000001006700270000000000607a019000000ff0660008c0000000102202039000000200600008a0000004107200039000000000667016f0000000706600029000000070760006c00000000070000190000000107004039000004fd0860009c000012f00000213d0000000107700190000012f00000c13d000000400060043f00000002062000390000000707000029000000000667043600000021072000390000000507700272000002e30000613d00000000080000190000000509800210000000000a960019000000000995034f000000000909043b00000000009a04350000000108800039000000000978004b000002db0000413d000000000700004b000002e50000613d00000007070000290000000007070433000000000707004b000009f80000613d00000000070604330000052e07700197000000f808200210000000000778019f000005300770004100000000007604350000000302200210000000f80220008900000000012101cf000000ff0220008c000000000100201900000007020000290000002102200039000003690000013d0000052b010000410000000000100439000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000052c011001c70000800b0200003913ce13bf0000040f00000001022001900000127a0000613d000000400300043d000000000401043b000000800140008c000004d50000413d00000080014002700000052f0240009c000000000104a0190000052f0240009c0000000002000019000000100200203900000008052001bf000004fd0610009c000000000502a0190000004002100270000004fd0610009c000000000201a01900000004015001bf000004f50620009c000000000105a0190000002006200270000004f50520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000004fd0610009c000012f00000213d0000000102200190000012f00000c13d000000400010043f0000000201500039000000000613043600000002010003670000000002000031000000210750003900000005077002720000033d0000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000003350000413d000000000700004b0000033f0000613d0000000007030433000000000707004b000009f80000613d00000000070604330000052e07700197000000f808500210000000000778019f000005300770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c00000000040020190000002105300039000004e80000013d0000050301000041000000800010043f0000002001000039000000840010043f0000001a01000039000000a40010043f0000052601000041000000bf0000013d00000007020000290000052d0220009c000012f00000213d00000007060000290000004002600039000000400020043f000000010200003a00000000022604360000000006500350000000000606043b0000000000620435000009f80000613d000000f807100210000004fe08000041000000000101004b000000000807c0190000052e01600197000000000181019f0000000000120435000000400100043d0000000502000029000000600220008a000000000623034f000000000606043b000000800760008c000005340000413d00000080076002700000052f0860009c000000000706a0190000052f0860009c0000000008000019000000100800203900000008098001bf000004fd0a70009c000000000908a0190000004008700270000004fd0a70009c000000000807a019000000040a9001bf000004f50780009c000000000a09a0190000002009800270000004f50780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008810019000000000918004b00000000090000190000000109004039000004fd0a80009c000012f00000213d0000000109900190000012f00000c13d000000400080043f0000000208700039000000000881043600000021097000390000000509900272000003a40000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b0000039c0000413d000000000900004b000003a60000613d0000000009010433000000000909004b000009f80000613d00000000090804330000052e09900197000000f80a70021000000000099a019f000005300990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c00000000060020190000002107100039000005440000013d0000000404500039000000000541034f000000000505043b000800000005001d000004ff0550009c000001240000213d000001400330008a000000000331034f0000002004400039000000000441034f000000000404043b000700000004001d000000000303043b0000051404000041000000800040043f000004ff02200197000500000002001d000000840020043f000004ff02300197000600000002001d000000a40020043f00000000020004140000000803000029000000040330008c000005900000c13d000000000161034f0000000103000031000000200230008c00000000040300190000002004008039000005bc0000013d000005080ba0009c000003d90000613d000005090aa0009c000000000500c019000000000a9800190000000006a6004b0000000006000019000000010600403900000000088a004b00000001066041bf000004f508900197000000000181034f000000000803004b000003f20000c13d0000000103600190000012560000c13d0000050d030000410000050e06000041000000000505004b000000000603c019000000c0022002100000050c02200197000000000226019f0000000003a70049000004f50330019700000000013103df00000000012103af0000000002040019000003fd0000013d0000000106600190000012560000c13d0000000006a70049000004f50660019700000000016103df000000c0022002100000050c022001970000050d022001c700000000012103af0000800902000039000000000600001913ce13c40000040f000300000001035500000000030100190000006003300270000104f50030019d000004f50330019700000001022001900000045b0000613d0000003f023000390000050f04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000004fd0640009c000012f00000213d0000000105500190000012f00000c13d000000400040043f00000000043204360000001f053000390000000505500272000004200000613d00000000060000310000000206600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b000004180000413d000000000500004b000004220000613d0000001f0530018f00000005033002720000042e0000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b000004260000413d000000000605004b0000043d0000613d0000000503300210000000000131034f00000000033400190000000304500210000000000503043300000000054501cf000000000545022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f0000000000130435000000400100043d00000020030000390000000004310436000000000302043300000000003404350000004004100039000000000503004b0000044d0000613d000000000500001900000000064500190000002005500039000000000725001900000000070704330000000000760435000000000635004b000004460000413d000000000243001900000000000204350000005f02300039000000200300008a000000000232016f000004f503000041000004f50420009c0000000002038019000004f50410009c000000000103801900000040011002100000006002200210000000000112019f000013cf0001042e0000001f0430018f0000000502300272000004660000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b0000045f0000413d000000000504004b000004740000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013d0000104300000052d0130009c000012f00000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000201000367000000000621034f0000000006600350000000000606043b0000000000650435000009f80000613d000000f807400210000004fe08000041000000000404004b000000000807c0190000052e04600197000000000484019f00000000004504350000000505100360000000400400043d000000000505043b000000800650008c000005e30000413d00000080065002700000052f0750009c000000000605a0190000052f0750009c0000000007000019000000100700203900000008087001bf000004fd0960009c000000000807a0190000004007600270000004fd0960009c000000000706a01900000004098001bf000004f50670009c000000000908a0190000002008700270000004f50670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007740019000000000847004b00000000080000190000000108004039000004fd0970009c000012f00000213d0000000108800190000012f00000c13d000000400070043f0000000207600039000000000774043600000021086000390000000508800272000004c30000613d000000000921034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b000004bb0000413d000000000800004b000004c50000613d0000000008040433000000000808004b000009f80000613d00000000080704330000052e08800197000000f809600210000000000889019f000005300880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106400039000005f40000013d0000052d0130009c000012f00000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000201000367000000000621034f0000000006600350000000000606043b0000000000650435000009f80000613d000000f807400210000004fe08000041000000000404004b000000000807c0190000052e04600197000000000484019f00000000004504350000000505100360000000400400043d000000000505043b000000800650008c000006420000413d00000080065002700000052f0750009c000000000605a0190000052f0750009c0000000007000019000000100700203900000008087001bf000004fd0960009c000000000807a0190000004007600270000004fd0960009c000000000706a01900000004098001bf000004f50670009c000000000908a0190000002008700270000004f50670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007740019000000000847004b00000000080000190000000108004039000004fd0970009c000012f00000213d0000000108800190000012f00000c13d000000400070043f0000000207600039000000000774043600000021086000390000000508800272000005220000613d000000000921034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b0000051a0000413d000000000800004b000005240000613d0000000008040433000000000808004b000009f80000613d00000000080704330000052e08800197000000f809600210000000000889019f000005300880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106400039000006530000013d0000052d0710009c000012f00000213d0000004007100039000000400070043f000000010700003a00000000077104360000000008500350000000000808043b0000000000870435000009f80000613d000000f809600210000004fe0a000041000000000606004b000000000a09c0190000052e068001970000000006a6019f0000000000670435000000400220008a000000000623034f000000400200043d000000000606043b000000800760008c0000089b0000413d00000080076002700000052f0860009c000000000706a0190000052f0860009c0000000008000019000000100800203900000008098001bf000004fd0a70009c000000000908a0190000004008700270000004fd0a70009c000000000807a019000000040a9001bf000004f50780009c000000000a09a0190000002009800270000004f50780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008820019000000000928004b00000000090000190000000109004039000004fd0a80009c000012f00000213d0000000109900190000012f00000c13d000000400080043f00000002087000390000000008820436000000210970003900000005099002720000057e0000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000005760000413d000000000900004b000005800000613d0000000009020433000000000909004b000009f80000613d00000000090804330000052e09900197000000f80a70021000000000099a019f000005300990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c00000000060020190000002107200039000008ab0000013d000004f501000041000004f50320009c0000000002018019000000c00120021000000515011001c7000000080200002913ce13bf0000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000005a90000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000005a10000413d000000000705004b000005b80000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f00030000000103550000000102200190000006a10000613d0000001f02400039000000600520018f00000080025001bf000000400020043f000000200430008c000001240000413d000000800400043d000000070440006c000010610000813d000000a00450003900000516060000410000000000640435000000a40650003900000006070000290000000000760435000000c40650003900000000000604350000004406000039000100000006001d00000000006204350000014006500039000000400060043f00000120065000390000051707000041000000000076043500000100065001bf0000002005000039000300000005001d000200000006001d0000000000560435000000000502043300000000020004140000000806000029000000040660008c000009390000c13d0000000102000039000004fd0430009c000012f00000213d0000094d0000013d0000052d0640009c000012f00000213d0000004006400039000000400060043f000000000721034f000000010600003a00000000066404360000000007700350000000000707043b0000000000760435000009f80000613d000000f808500210000004fe09000041000000000505004b000000000908c0190000052e05700197000000000595019f0000000000560435000000400500043d0000000506000029000000600660008a000000000761034f000000000707043b000000800870008c0000098f0000413d00000080087002700000052f0970009c000000000807a0190000052f0970009c00000000090000190000001009002039000000080a9001bf000004fd0b80009c000000000a09a0190000004009800270000004fd0b80009c000000000908a019000000040ba001bf000004f50890009c000000000b0aa019000000200a900270000004f50890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000004fd0b90009c000012f00000213d000000010aa00190000012f00000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa00272000006300000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000006280000413d000000000a00004b000006320000613d000000000a050433000000000a0a004b000009f80000613d000000000a0904330000052e0aa00197000000f80b800210000000000aab019f000005300aa000410000000000a904350000000308800210000000f80880008900000000078701cf000000ff0880008c00000000070020190000002108500039000009a00000013d0000052d0640009c000012f00000213d0000004006400039000000400060043f000000000721034f000000010600003a00000000066404360000000007700350000000000707043b0000000000760435000009f80000613d000000f808500210000004fe09000041000000000505004b000000000908c0190000052e05700197000000000595019f0000000000560435000000400500043d0000000506000029000000400760008a000000000671034f000000000606043b000000800860008c000009ed0000413d00000080086002700000052f0960009c000000000806a0190000052f0960009c00000000090000190000001009002039000000080a9001bf000004fd0b80009c000000000a09a0190000004009800270000004fd0b80009c000000000908a019000000040ba001bf000004f50890009c000000000b0aa019000000200a900270000004f50890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000004fd0b90009c000012f00000213d000000010aa00190000012f00000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa002720000068f0000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000006870000413d000000000a00004b000006910000613d000000000a050433000000000a0a004b000009f80000613d000000000a0904330000052e0aa00197000000f80b800210000000000aab019f000005300aa000410000000000a904350000000308800210000000f80880008900000000068601cf000000ff0880008c0000000006002019000000210850003900000abc0000013d000000400200043d0000001f0430018f0000000505300272000006ae0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000006a60000413d000000000604004b000006bd0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000004f501000041000004f50420009c000000000201801900000040012002100000006002300210000000000121019f000013d000010430000004f501100197000000000113034f0000000002640049000004f50220019700000000012103df000000c0025002100000050c022001970000050e022001c700000000012103af000080100200003913ce13c90000040f00000000030100190000006003300270000104f50030019d000004f50530019700030000000103550000000102200190000009fc0000613d0000003f025000390000050f02200197000000400600043d0000000002260019000000000362004b00000000030000190000000103004039000004fd0420009c000012f00000213d0000000103300190000012f00000c13d000000400020043f0000000004560436000000020200036700000000030000310000001f075000390000000507700272000006f20000613d000000000832034f0000000009000019000000050a900210000000000ba40019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000006ea0000413d000000000700004b000006f40000613d0000001f0750018f0000000505500272000007000000613d00000000080000190000000509800210000000000a940019000000000991034f000000000909043b00000000009a04350000000108800039000000000958004b000006f80000413d000000000807004b0000070f0000613d0000000505500210000000000151034f00000000055400190000000307700210000000000805043300000000087801cf000000000878022f000000000101043b0000010007700089000000000171022f00000000017101cf000000000181019f00000000001504350000000001060433000000200110008c00000a3e0000c13d00000009060000290000000001630049000000230510008a000702040060003d0000000701200360000000000101043b000004fe06000041000000000751004b00000000070000190000000007068019000004fe05500197000004fe08100197000000000958004b0000000006008019000000000558013f000004fe0550009c000000000607c019000000000506004b000001240000c13d0000000004040433000400000004001d0000000801100029000000000412034f000000000504043b000004fd0450009c000001240000213d000000050450021000000000034300490000002006100039000004fe01000041000000000736004b00000000070000190000000007012019000004fe03300197000004fe08600197000000000938004b0000000001008019000000000338013f000004fe0330009c000000000107c019000000000101004b000001240000c13d000000400100043d000000200310003900000537055001980000074a0000613d000000000262034f000000000600001900000005076002100000000008730019000000000772034f000000000707043b00000000007804350000000106600039000000000756004b000007420000413d000000000200004b0000074c0000613d00000000004104350000003f02400039000000200400008a000000000242016f0000000002210019000000000412004b00000000040000190000000104004039000004fd0520009c000012f00000213d0000000104400190000012f00000c13d000000400020043f000004f502000041000004f50430009c000000000302801900000040033002100000000001010433000004f50410009c00000000010280190000006001100210000000000131019f0000000003000414000004f50430009c0000000003028019000000c002300210000000000112019f00000500011001c7000080100200003913ce13bf0000040f0000000102200190000001240000613d0000000002000031000000090320006a000000230530008a000000070300002900000020043000390000000203000367000000000443034f000000000404043b000004fe06000041000000000754004b00000000070000190000000007068019000004fe05500197000004fe08400197000000000958004b0000000006008019000000000558013f000004fe0550009c000000000607c019000000000101043b000700000001001d000000000106004b000001240000c13d0000000801400029000000000413034f000000000404043b000004fd0540009c000001240000213d00000000054200490000002001100039000004fe06000041000000000751004b00000000070000190000000007062019000004fe05500197000004fe08100197000000000958004b0000000006008019000000000558013f000004fe0550009c000000000607c019000000000506004b000001240000c13d00000000050004140000000006140019000000000446004b000000000400001900000001040040390000000104400190000012560000c13d000000000462004b000012560000413d000004f50450009c000002900000213d000004f501100197000000000113034f0000000002620049000004f50220019700000000012103df000000c0025002100000050c022001970000050e022001c700000000012103af000080100200003913ce13c90000040f00000000030100190000006003300270000104f50030019d000004f50330019700030000000103550000000102200190000011690000613d0000003f023000390000050f02200197000000400500043d0000000002250019000000000452004b00000000040000190000000104004039000004fd0620009c000012f00000213d0000000104400190000012f00000c13d000000400020043f000000000235043600000002040003670000001f063000390000000506600272000007cf0000613d000000000740036800000000080000190000000509800210000000000a920019000000000997034f000000000909043b00000000009a04350000000108800039000000000968004b000007c70000413d000000000600004b000007d10000613d0000001f0630018f0000000503300272000007dd0000613d000000000700001900000005087002100000000009820019000000000881034f000000000808043b00000000008904350000000107700039000000000837004b000007d50000413d000000000706004b000007ec0000613d0000000503300210000000000131034f00000000033200190000000306600210000000000703043300000000076701cf000000000767022f000000000101043b0000010006600089000000000161022f00000000016101cf000000000171019f00000000001304350000000001050433000000200110008c00000a3e0000c13d000000090c0000290000006401c00039000000000114034f0000004403c00039000000000534034f0000002403c00039000000000634034f0000012403c00039000000000734034f0000000508400360000000e403c00039000000000934034f000000c403c00039000000000a34034f000000a403c00039000000000b34034f0000008403c00039000000000c34034f0000000803400360000000000303043b000000000406043b000000000505043b000000000601043b000000000c0c043b000000000b0b043b000000000a0a043b000000000909043b000000000808043b000000000707043b0000000002020433000000400100043d000001c00d10003900000000002d0435000001a002100039000000070d0000290000000000d204350000018002100039000000040d0000290000000000d2043500000160021000390000000000720435000001400210003900000000008204350000012002100039000000000092043500000100021000390000000000a20435000000e0021000390000000000b20435000000c0021000390000000000c20435000000a0021000390000000000620435000000800210003900000000005204350000006002100039000000000042043500000040021000390000000000320435000000200210003900000539030000410000000000320435000001c00300003900000000003104350000053a0310009c000012f00000213d000001e003100039000000400030043f000004f504000041000004f50320009c000000000204801900000040022002100000000001010433000004f50310009c00000000010480190000006001100210000000000121019f0000000002000414000004f50320009c0000000002048019000000c002200210000000000112019f00000500011001c7000080100200003913ce13bf0000040f0000000102200190000001240000613d000000000101043b000500000001001d000000400100043d000700000001001d0000052b0100004100000000001004390000000001000414000004f50210009c000004f501008041000000c0011002100000052c011001c70000800b0200003913ce13bf0000040f00000001022001900000127a0000613d00000007040000290000002002400039000000000101043b0000053b0300004100000000003204350000008003400039000000000013043500000060014000390000053c03000041000000000031043500000040014000390000053d030000410000000000310435000000800100003900000000001404350000053e0140009c000012f00000213d0000000704000029000000a001400039000000400010043f000004f501000041000004f50320009c000000000201801900000040022002100000000003040433000004f50430009c00000000030180190000006003300210000000000223019f0000000003000414000004f50430009c0000000003018019000000c001300210000000000121019f00000500011001c7000080100200003913ce13bf0000040f0000000102200190000001240000613d000000000301043b000000400100043d00000042021000390000000504000029000000000042043500000020021000390000053f04000041000000000042043500000022041000390000000000340435000000420300003900000000003104350000051d0310009c000012f00000213d0000008003100039000000400030043f000004f503000041000004f50420009c000000000203801900000040022002100000000001010433000004f50410009c00000000010380190000006001100210000000000121019f0000000002000414000004f50420009c0000000002038019000000c002200210000000000112019f000012340000013d0000052d0720009c000012f00000213d0000004007200039000000400070043f000000010700003a00000000077204360000000008500350000000000808043b0000000000870435000009f80000613d000000f809600210000004fe0a000041000000000606004b000000000a09c0190000052e068001970000000006a6019f0000000000670435000000400600043d000500000006001d00000020076000390000000006010433000000000806004b000008ba0000613d000000000800001900000000097800190000002008800039000000000a180019000000000a0a04330000000000a90435000000000968004b000008b30000413d000000000176001900000000000104350000000007020433000000000807004b000008c70000613d000000000800001900000000091800190000002008800039000000000a280019000000000a0a04330000000000a90435000000000978004b000008c00000413d000000000117001900000000000104350000000001670019000000050600002900000000001604350000003f011000390001002000000092000000010110017f0000000002610019000000000112004b00000000010000190000000101004039000400000002001d000004fd0220009c000012f00000213d0000000101100190000012f00000c13d0000000401000029000000400010043f0000052d0110009c000012f00000213d00000009070000290000004401700039000000000113034f000000000101043b00000004080000290000004002800039000000400020043f000000200280003900000531060000410000000000620435000000150200003900000000002804350000006001100210000000210280003900000000001204350000012401700039000000000213034f000000400600043d000300000006001d000000000202043b000000800620008c00000b680000413d00000080062002700000052f0720009c000000000602a0190000052f0720009c0000000007000019000000100700203900000008087001bf000004fd0960009c000000000807a0190000004007600270000004fd0960009c000000000706a01900000004098001bf000004f50670009c000000000908a0190000002008700270000004f50670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c00000001066020390000004107600039000000010770017f0000000307700029000000030870006c00000000080000190000000108004039000004fd0970009c000012f00000213d0000000108800190000012f00000c13d000000400070043f00000002076000390000000308000029000000000778043600000021086000390000000508800272000009250000613d0000000009000019000000050a900210000000000ba70019000000000aa5034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b0000091d0000413d000000000800004b000009270000613d00000003080000290000000008080433000000000808004b000009f80000613d00000000080704330000052e08800197000000f809600210000000000889019f000005300880004100000000008704350000000306600210000000f80660008900000000026201cf000000ff0660008c00000000020020190000000306000029000000210660003900000b7a0000013d000004f501000041000004f50350009c000000000501801900000060035002100000004004400210000000000343019f000004f50420009c0000000002018019000000c001200210000000000113019f000000080200002913ce13ba0000040f000400600000003d000000010220018f000300000001035500000000030100190000006003300270000104f50030019d000004f503300198000009790000613d0000003f04300039000000200500008a000000000454016f000000400500043d0000000004450019000400000005001d000000000554004b00000000050000190000000105004039000004fd0640009c000012f00000213d0000000105500190000012f00000c13d000000400040043f0000001f0430018f000000040500002900000000083504360000000503300272000009690000613d000000000500001900000005065002100000000007680019000000000661034f000000000606043b00000000006704350000000105500039000000000635004b000009610000413d000900000008001d000000000504004b000009790000613d0000000503300210000000000131034f00000009033000290000000304400210000000000503043300000000054501cf000000000545022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000013043500000004010000290000000001010433000000000202004b00000a170000c13d000000000201004b00000a360000c13d000000400300043d000900000003001d000005030100004100000000001304350000000401300039000000030200002900000000002104350000002402300039000000020100002913ce13a60000040f00000009040000290000000001410049000004f502000041000004f50310009c000000000102801900000a3a0000013d0000052d0850009c000012f00000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b0000000000980435000009f80000613d000000f80a700210000004fe0b000041000000000707004b000000000b0ac0190000052e079001970000000007b7019f0000000000780435000000400700043d000000400660008a000000000861034f000000000808043b000000800980008c00000a450000413d00000080098002700000052f0a80009c000000000908a0190000052f0a80009c000000000a000019000000100a002039000000080ba001bf000004fd0c90009c000000000b0aa019000000400a900270000004fd0c90009c000000000a09a019000000040cb001bf000004f509a0009c000000000c0ba019000000200ba00270000004f509a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa70019000000000b7a004b000000000b000019000000010b004039000004fd0ca0009c000012f00000213d000000010bb00190000012f00000c13d0000004000a0043f000000020a900039000000000aa70436000000210b900039000000050bb00272000009db0000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b000009d30000413d000000000b00004b000009dd0000613d000000000b070433000000000b0b004b000009f80000613d000000000b0a04330000052e0bb00197000000f80c900210000000000bbc019f000005300bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c0000000008002019000000210970003900000a560000013d0000052d0850009c000012f00000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b000000000098043500000ab60000c13d0000054601000041000000000010043500000032010000390000003c0000013d0000001f0350018f000000050250027200000a070000613d00000000040000190000000506400210000000000761034f000000000707043b00000000007604350000000104400039000000000624004b00000a000000413d000000000403004b00000a150000613d00000003033002100000000502200210000000000402043300000000043401cf000000000434022f000000000121034f000000000101043b0000010003300089000000000131022f00000000013101cf000000000141019f00000000001204350000006001500210000013d000010430000000000201004b00000bc40000c13d0000051801000041000000000010043900000008010000290000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000519011001c7000080020200003913ce13bf0000040f00000001022001900000127a0000613d000000000101043b000000000101004b00000bc00000c13d000000400100043d00000044021000390000052103000041000000000032043500000024021000390000001d0300003900000000003204350000050302000041000000000021043500000004021000390000000303000029000002a20000013d000004f502000041000004f50310009c00000000010280190000000904000029000004f50340009c00000000040280190000004002400210000002440000013d000000400100043d00000044021000390000053803000041000000000032043500000024021000390000001f030000390000029d0000013d0000052d0970009c000012f00000213d0000004009700039000000400090043f000000000a21034f000000010900003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000009f80000613d000000f80b800210000004fe0c000041000000000808004b000000000c0bc0190000052e08a001970000000008c8019f0000000000890435000000400900043d0000052d0890009c000012f00000213d000000200860008a000000000881034f000000000808043b000000400a9000390000004000a0043f000000200a900039000005310b0000410000000000ba0435000000150a0000390000000000a904350000006008800210000000210a90003900000000008a0435000000c006600039000000000661034f000000400800043d000000000606043b000700000006001d000000800a60008c00000cd50000413d0000000706000029000000800a6002700000052f0b60009c000000000a06a0190000052f0b60009c000000000b000019000000100b002039000000080cb001bf000004fd0da0009c000000000c0ba019000000400ba00270000004fd0da0009c000000000b0aa019000000040dc001bf000004f50ab0009c000000000d0ca019000000200cb00270000004f50ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000004fd0db0009c000012f00000213d000000010cc00190000012f00000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc0027200000aa30000613d000000000d21034f000000000e000019000000050fe002100000000006fb0019000000000ffd034f000000000f0f043b0000000000f60435000000010ee000390000000006ce004b00000a9b0000413d000000000600004b00000aa50000613d0000000006080433000000000606004b000009f80000613d00000000060b04330000052e06600197000000f80ca0021000000000066c019f000005300660004100000000006b04350000000306a00210000000f806600089000000070a6001ef000000ff0660008c000000000a00201900000021068000390000000000a6043500000ce80000013d000000f80a600210000004fe0b000041000000000606004b000000000b0ac0190000052e069001970000000006b6019f0000000000680435000000400600043d000000200770008a000000000871034f000000000808043b000000800980008c00000b090000413d00000080098002700000052f0a80009c000000000908a0190000052f0a80009c000000000a000019000000100a002039000000080ba001bf000004fd0c90009c000000000b0aa019000000400a900270000004fd0c90009c000000000a09a019000000040cb001bf000004f509a0009c000000000c0ba019000000200ba00270000004f509a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa60019000000000b6a004b000000000b000019000000010b004039000004fd0ca0009c000012f00000213d000000010bb00190000012f00000c13d0000004000a0043f000000020a900039000000000aa60436000000210b900039000000050bb0027200000af70000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b00000aef0000413d000000000b00004b00000af90000613d000000000b060433000000000b0b004b000009f80000613d000000000b0a04330000052e0bb00197000000f80c900210000000000bbc019f000005300bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c0000000008002019000000210960003900000b1a0000013d0000052d0960009c000012f00000213d0000004009600039000000400090043f000000000a21034f000000010900003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000009f80000613d000000f80b800210000004fe0c000041000000000808004b000000000c0bc0190000052e08a001970000000008c8019f0000000000890435000000400800043d00070040007000920000000709100360000000000909043b000000800a90008c00000bfa0000413d000000800a9002700000052f0b90009c000000000a09a0190000052f0b90009c000000000b000019000000100b002039000000080cb001bf000004fd0da0009c000000000c0ba019000000400ba00270000004fd0da0009c000000000b0aa019000000040dc001bf000004f50ab0009c000000000d0ca019000000200cb00270000004f50ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000004fd0db0009c000012f00000213d000000010cc00190000012f00000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc0027200000b550000613d000000000d21034f000000000e000019000000050fe002100000000007fb0019000000000ffd034f000000000f0f043b0000000000f70435000000010ee000390000000007ce004b00000b4d0000413d000000000700004b00000b570000613d0000000007080433000000000707004b000009f80000613d00000000070b04330000052e07700197000000f80ca0021000000000077c019f000005300770004100000000007b04350000000307a00210000000f80770008900000000097901cf000000ff0770008c00000000090020190000002107800039000000000097043500000c0c0000013d00000003060000290000052d0660009c000012f00000213d00000003070000290000004006700039000000400060043f000000010600003a00000000066704360000000007500350000000000707043b0000000000760435000009f80000613d000000f808200210000004fe09000041000000000202004b000000000908c0190000052e02700197000000000292019f0000000000260435000000080640006a000000a001100039000000000213034f000000000202043b0000001f0660008a000004fe07600197000004fe08200197000004fe09000041000000000a78004b000000000a000019000000000a094019000000000778013f000000000862004b0000000009004019000004fe0770009c000000000a09c01900000000070a004b000001240000c13d0000000808200029000000000783034f000000000707043b000004fd0970009c000001240000213d00000000097400490000002008800039000004fe0a000041000000000b98004b000000000b000019000000000b0a2019000004fe09900197000004fe0c800197000000000d9c004b000000000a00801900000000099c013f000004fe0990009c000000000a0bc01900000000090a004b000001240000c13d000000010970008c00000e8d0000c13d000000000583034f000000000505043b000000010700008a000004fe08000041000000000775004b00000000070000190000000007082019000004fe05500197000004fe0950009c0000000008008019000004fe05500167000004fe0550009c000000000807c019000200600000003d000000000508004b00000ec90000c13d000000400500043d000200000005001d0000052d0550009c000012f00000213d00000002080000290000004005800039000000400050043f0000002005800039000005300700004100000000007504350000000105000039000000000058043500000ec90000013d00000004010000290000000001010433000000000201004b00000be70000613d000004fe02000041000000200310008c00000000030000190000000003024019000004fe01100197000000000401004b000000000200a019000004fe0110009c000000000203c019000000000102004b000001240000c13d00000009010000290000000001010433000000000201004b0000000002000019000000010200c039000000000221004b000001240000c13d000000000101004b00000be70000c13d000000400100043d00000064021000390000051f03000041000000000032043500000044021000390000052003000041000000000032043500000024021000390000002a0300003900000000003204350000050302000041000000000021043500000004021000390000000303000029000001070000013d000000400300043d00000024013000390000000602000029000000000021043500000514010000410000000000130435000900000003001d00000004013000390000000502000029000000000021043500000000010004140000000802000029000000040220008c00000c6f0000c13d0000000103000031000000200130008c0000000004030019000000200400803900000ca10000013d0000052d0780009c000012f00000213d0000004007800039000000400070043f000000000721034f000000010a00003a000000000aa804360000000007700350000000000b07043b0000000000ba0435000009f80000613d000000f807900210000004fe0c000041000000000909004b000000000c07c0190000052e07b001970000000007c7019f00000000007a0435000000400a00043d0000052d07a0009c000012f00000213d000000070c0000290000002007c0008a000000000771034f000000000707043b0000004009a00039000000400090043f0000002009a00039000005310b0000410000000000b90435000000150900003900000000009a043500000060077002100000002109a000390000000000790435000000c007c00039000000000771034f000000400900043d000000000707043b000700000007001d000000800b70008c00000db20000413d0000000707000029000000800b7002700000052f0c70009c000000000b07a0190000052f0c70009c000000000c000019000000100c002039000000080dc001bf000004fd0eb0009c000000000d0ca019000000400cb00270000004fd0eb0009c000000000c0ba019000000040ed001bf000004f50bc0009c000000000e0da019000000200dc00270000004f50bc0009c000000000d0ca0190000000207e001bf0000ffff0cd0008c00000000070ea019000000100cd00270000000000c0da019000000ff0cc0008c0000000107702039000000200c00008a000500000007001d000000410d700039000000000ccd016f000000000cc90019000000000d9c004b000000000d000019000000010d004039000004fd0ec0009c000012f00000213d000000010dd00190000012f00000c13d0000004000c0043f0000000507000029000000020c700039000000000cc90436000000210d700039000000050dd0027200000c5b0000613d000000000e21034f000000000f0000190000000507f00210000000000b7c001900000000077e034f000000000707043b00000000007b0435000000010ff000390000000007df004b00000c530000413d000000000700004b00000c5d0000613d0000000007090433000000000707004b000009f80000613d00000000070c04330000052e07700197000000050d000029000000f80bd0021000000000077b019f000005300770004100000000007c04350000000307d00210000000f807700089000000070b7001ef000000ff0770008c000000000b00201900000021079000390000000000b7043500000dc50000013d000004f502000041000004f50310009c00000000010280190000000904000029000004f50340009c00000000020440190000004002200210000000c001100210000000000121019f0000051a011001c7000000080200002913ce13bf0000040f000000090a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000c8e0000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000c860000413d000000000705004b00000c9d0000613d0000000506600210000000000761034f00000009066000290000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f0003000000010355000000010220019000000d950000613d0000001f01400039000000600210018f0000000901200029000000000221004b00000000020000190000000102004039000004fd0410009c000012f00000213d0000000102200190000012f00000c13d000000400010043f000000200230008c000001240000413d0000004404100039000000240510003900000009020000290000000002020433000000000202004b00000e810000c13d0000002002100039000005160600004100000000006204350000000606000029000000000065043500000007050000290000000000540435000000010400002900000000004104350000051d0410009c000012f00000213d0000008004100039000900000004001d000000400040043f0000051e0410009c000012f00000213d000000c004100039000000400040043f000000030400002900000009050000290000000000450435000000a00410003900000517050000410000000000540435000000000401043300000000010004140000000805000029000000040550008c00000f810000c13d0000000102000039000004fd0130009c000012f00000213d00000f970000013d0000052d0680009c000012f00000213d0000004006800039000000400060043f000000000621034f000000010a00003a000000000aa804360000000006600350000000000b06043b0000000000ba0435000009f80000613d000000070d000029000000f806d00210000004fe0c000041000000000d0d004b000000000c06c0190000052e06b001970000000006c6019f00000000006a0435000000400600043d000000200b600039000000000a030433000000000c0a004b00000cf50000613d000000000c000019000000000dbc0019000000200cc00039000000000e3c0019000000000e0e04330000000000ed0435000000000dac004b00000cee0000413d0000000003ba0019000000000003043500000000036a0019000000200b300039000000000a040433000000000c0a004b00000d040000613d000000000c000019000000000dbc0019000000200cc00039000000000e4c0019000000000e0e04330000000000ed0435000000000dac004b00000cfd0000413d0000000004ba0019000000000004043500000000033a0019000000200a3000390000000004050433000000000b04004b00000d130000613d000000000b000019000000000cab0019000000200bb00039000000000d5b0019000000000d0d04330000000000dc0435000000000c4b004b00000d0c0000413d0000000005a400190000000000050435000000000334001900000020053000390000000004070433000000000a04004b00000d220000613d000000000a000019000000000b5a0019000000200aa00039000000000c7a0019000000000c0c04330000000000cb0435000000000b4a004b00000d1b0000413d00000000055400190000000000050435000000000334001900000020053000390000000004090433000000000704004b00000d310000613d0000000007000019000000000a5700190000002007700039000000000b970019000000000b0b04330000000000ba0435000000000a47004b00000d2a0000413d00000000055400190000000000050435000000000334001900000020053000390000000004080433000000000704004b00000d400000613d000000000700001900000000095700190000002007700039000000000a870019000000000a0a04330000000000a90435000000000947004b00000d390000413d000000000554001900000000000504350000000003630049000000000334001900000000003604350000003f04300039000000200300008a000000000434016f0000000007640019000000000447004b00000000040000190000000104004039000004fd0570009c000012f00000213d0000000104400190000012f00000c13d000000400070043f0000000905000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b000004fe08000041000000000954004b00000000090000190000000009088019000004fe05500197000004fe0a400197000000000b5a004b000000000800801900000000055a013f000004fe0550009c000000000809c019000000000508004b000001240000c13d0000000805400029000000000451034f000000000404043b000004fd0840009c000001240000213d00000000084200490000002005500039000004fe09000041000000000a85004b000000000a000019000000000a092019000004fe08800197000004fe0b500197000000000c8b004b000000000900801900000000088b013f000004fe0880009c00000000090ac019000000000809004b000001240000c13d000000010840008c00000fd60000c13d000000000851034f000000000808043b000000010900008a000004fe0a000041000000000998004b000000000900001900000000090a2019000004fe08800197000004fe0b80009c000000000a008019000004fe08800167000004fe0880009c000000000a09c019000000600800003900000000090a004b000010740000c13d0000052d0870009c000012f00000213d0000004008700039000000400080043f000000200870003900000530090000410000000000980435000000010800003900000000008704350000000008070019000010740000013d000000400200043d0000001f0430018f000000050530027200000da20000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000d9a0000413d000000000604004b00000db10000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000006bd0000013d0000052d0790009c000012f00000213d0000004007900039000000400070043f000000000721034f000000010b00003a000000000bb904360000000007700350000000000c07043b0000000000cb0435000009f80000613d000000070e000029000000f807e00210000004fe0d000041000000000e0e004b000000000d07c0190000052e07c001970000000007d7019f00000000007b0435000000400700043d000000200c700039000000000b030433000000000d0b004b00000dd20000613d000000000d000019000000000ecd0019000000200dd00039000000000f3d0019000000000f0f04330000000000fe0435000000000ebd004b00000dcb0000413d0000000003cb0019000000000003043500000000037b0019000000200c300039000000000b040433000000000d0b004b00000de10000613d000000000d000019000000000ecd0019000000200dd00039000000000f4d0019000000000f0f04330000000000fe0435000000000ebd004b00000dda0000413d0000000004cb0019000000000004043500000000033b0019000000200b3000390000000004050433000000000c04004b00000df00000613d000000000c000019000000000dbc0019000000200cc00039000000000e5c0019000000000e0e04330000000000ed0435000000000d4c004b00000de90000413d0000000005b400190000000000050435000000000334001900000020053000390000000004060433000000000b04004b00000dff0000613d000000000b000019000000000c5b0019000000200bb00039000000000d6b0019000000000d0d04330000000000dc0435000000000c4b004b00000df80000413d00000000055400190000000000050435000000000334001900000020053000390000000004080433000000000604004b00000e0e0000613d0000000006000019000000000b5600190000002006600039000000000c860019000000000c0c04330000000000cb0435000000000b46004b00000e070000413d000000000554001900000000000504350000000003340019000000200530003900000000040a0433000000000604004b00000e1d0000613d000000000600001900000000085600190000002006600039000000000ba60019000000000b0b04330000000000b80435000000000846004b00000e160000413d00000000055400190000000000050435000000000334001900000020053000390000000004090433000000000604004b00000e2c0000613d000000000600001900000000085600190000002006600039000000000a960019000000000a0a04330000000000a80435000000000846004b00000e250000413d000000000554001900000000000504350000000003730049000000000334001900000000003704350000003f04300039000000200300008a000000000434016f0000000006740019000000000446004b00000000040000190000000104004039000004fd0560009c000012f00000213d0000000104400190000012f00000c13d000000400060043f0000000905000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b000004fe08000041000000000954004b00000000090000190000000009088019000004fe05500197000004fe0a400197000000000b5a004b000000000800801900000000055a013f000004fe0550009c000000000809c019000000000508004b000001240000c13d0000000805400029000000000451034f000000000404043b000004fd0840009c000001240000213d00000000084200490000002005500039000004fe09000041000000000a85004b000000000a000019000000000a092019000004fe08800197000004fe0b500197000000000c8b004b000000000900801900000000088b013f000004fe0880009c00000000090ac019000000000809004b000001240000c13d000000010840008c000011840000c13d000000000851034f000000000808043b000000010900008a000004fe0a000041000000000998004b000000000900001900000000090a2019000004fe08800197000004fe0b80009c000000000a008019000004fe08800167000004fe0880009c000000000a09c019000000600800003900000000090a004b000012ed0000c13d0000052d0860009c000012f00000213d0000004008600039000000400080043f000000200860003900000530090000410000000000980435000000010800003900000000008604350000000008060019000012ed0000013d00000503020000410000000000210435000000040210003900000003030000290000000000320435000000360200003900000000002504350000051b02000041000000000024043500000064021000390000051c03000041000001070000013d000000400800043d000200000008001d000000380870008c00000eb80000413d0000002009700270000004f50870009c000000000907a019000004f50870009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000000020a0000290000052d0aa0009c000012f00000213d000000000898019f000000020a0000290000004009a00039000000400090043f000000020980003a00000000099a04360000000005500350000000000505043b0000000000590435000009f80000613d0000052e05500197000000f80a80021000000000055a019f00000532055001c700000000005904350000000305800210000000f80550015f00000000055701cf00000002070000290000002107700039000000000057043500000ec90000013d00000002080000290000052d0880009c000012f00000213d00000002090000290000004008900039000000400080043f000000010800003a00000000088904360000000005500350000000000505043b0000000000580435000009f80000613d000000f8077002100000052e05500197000000000575019f000004fe055001670000000000580435000000800110008a000000000513034f0000006001000039000000000505043b000000000505004b00000f2a0000c13d000004fe05000041000000000762004b00000000070000190000000007058019000004fe06600197000004fe08200197000000000968004b0000000005008019000000000668013f000004fe0660009c000000000507c019000000000505004b000001240000c13d000000070500002900000000060504330000000505000029000000000705043300000004050000290000000008050433000000030500002900000000090504330000000205000029000000000a0504330000000805200029000000000253034f000000000202043b000004fd0b20009c000001240000213d000000000b2400490000002005500039000004fe0c000041000000000db5004b000000000d000019000000000d0c2019000004fe0bb00197000004fe0e500197000000000fbe004b000000000c008019000000000bbe013f000004fe0bb0009c000000000c0dc019000000000b0c004b000001240000c13d0000000006670019000000000686001900000000069600190000000006a60019000000000626001900000000070104330000000006760019000000400700043d000004fd06600197000000380860008c000010b40000413d0000002009600270000004f50860009c000000000906a019000004f50860009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c000000000900001900000001090020390000052d0a70009c000012f00000213d000000000898019f0000004009700039000000400090043f000000000943034f000000020480003a00000000044704360000000009900350000000000909043b0000000000940435000009f80000613d0000052e09900197000000f80a80021000000000099a019f00000534099001c700000000009404350000000304800210000000f80440015f00000000044601cf00000021067000390000000000460435000010c40000013d0000052b010000410000000000100439000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000052c011001c70000800b0200003913ce13bf0000040f00000001022001900000127a0000613d000000400200043d000000000101043b000000800310008c00000ffe0000413d00000080031002700000052f0410009c000000000301a0190000052f0410009c0000000004000019000000100400203900000008054001bf000004fd0630009c000000000504a0190000004004300270000004fd0630009c000000000403a01900000004035001bf000004f50640009c000000000305a0190000002006400270000004f50540009c000000000604a01900000002053001bf0000ffff0460008c000000000503a0190000001003600270000000000306a019000000ff0330008c00000001055020390000004103500039000000010330017f0000000003320019000000000423004b00000000040000190000000104004039000004fd0630009c000012f00000213d0000000104400190000012f00000c13d000000400030043f00000002035000390000000006320436000000020300036700000000040000310000002107500039000000050770027200000f6f0000613d000000000843034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000f670000413d000000000700004b00000f710000613d0000000007020433000000000707004b000009f80000613d00000000070604330000052e07700197000000f808500210000000000778019f000005300770004100000000007604350000000305500210000000f80550008900000000015101cf000000ff0550008c00000000010020190000002105200039000010110000013d000004f503000041000004f50520009c00000000020380190000004002200210000004f50540009c00000000040380190000006004400210000000000224019f000004f50410009c0000000001038019000000c001100210000000000112019f000000080200002913ce13ba0000040f000700600000003d000600800000003d000000010220018f00030000000103550000006001100270000104f50010019d000004f50310019800000fc40000613d0000003f01300039000000200400008a000000000141016f000000400400043d0000000001140019000700000004001d000000000441004b00000000040000190000000104004039000004fd0510009c000012f00000213d0000000104400190000012f00000c13d000000400010043f0000001f0130018f000000070400002900000000083404360000000304000367000000050330027200000fb40000613d000000000500001900000005065002100000000007680019000000000664034f000000000606043b00000000006704350000000105500039000000000635004b00000fac0000413d000600000008001d000000000501004b00000fc40000613d0000000503300210000000000434034f00000006033000290000000301100210000000000503043300000000051501cf000000000515022f000000000404043b0000010001100089000000000414022f00000000011401cf000000000151019f000000000013043500000007010000290000000001010433000000000202004b000010360000c13d000000000201004b000010af0000c13d000000400300043d000800000003001d000005030100004100000000001304350000000401300039000000030200002900000000002104350000002402300039000000090100002913ce13a60000040f00000008040000290000098a0000013d000000380840008c000010630000413d0000002009400270000004f50840009c000000000904a019000004f50840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c000000000900001900000001090020390000052d0a70009c000012f00000213d000000000898019f0000004009700039000000400090043f000000000a21034f000000020980003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000009f80000613d0000052e0aa00197000000f80b800210000000000aab019f000005320aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf000000210970003900000000008904350000000008070019000010740000013d0000052d0320009c000012f00000213d0000004003200039000000400030043f000000010300003a000000000532043600000000040000310000000203000367000000000643034f0000000006600350000000000606043b0000000000650435000009f80000613d000000f807100210000004fe08000041000000000101004b000000000807c0190000052e01600197000000000181019f0000000000150435000000400100043d00000020061000390000000005020433000000000705004b0000101f0000613d000000000700001900000000086700190000002007700039000000000927001900000000090904330000000000980435000000000857004b000010180000413d000000000265001900000540060000410000000000620435000000020250003900000000002104350000004102500039000000010520017f0000000002150019000000000552004b00000000050000190000000105004039000004fd0620009c000012f00000213d0000000105500190000012f00000c13d0000000906000029000001c405600039000000400020043f000000000253034f0000000005640049000000230650008a000000000202043b00000ecf0000013d000000000201004b0000104d0000c13d0000051801000041000000000010043900000008010000290000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000519011001c7000080020200003913ce13bf0000040f00000001022001900000127a0000613d000000000101043b000000000101004b00000a2a0000613d00000007010000290000000001010433000000000201004b000010610000613d000004fe02000041000000200310008c00000000030000190000000003024019000004fe01100197000000000401004b000000000200a019000004fe0110009c000000000203c019000000000102004b000001240000c13d00000006010000290000000001010433000000000201004b0000000002000019000000010200c039000000000221004b000001240000c13d000000000101004b00000bd80000613d0000000001000019000013cf0001042e0000052d0870009c000012f00000213d0000004008700039000000400080043f000000000921034f000000010800003a00000000088704360000000009900350000000000909043b0000000000980435000009f80000613d000000f80a4002100000052e099001970000000009a9019f000004fe0990016700000000009804350000000008070019000000400700043d0000052d0970009c000012f00000213d0000004009700039000000400090043f000000000221034f000000010c00003a0000000009c704360000000002200350000000000b02043b0000000000b90435000009f80000613d0000052e02b00197000005330a2001c70000000000a9043500000000090604330000000009490019000000000a0804330000000009a90019000000000a0704330000000009a90019000000400a00043d000004fd09900197000000380d90008c000011ac0000413d000000200d900270000004f50c90009c000000000d09a019000004f50c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d0020390000052d0ea0009c000012f00000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000009f80000613d000000f80bc0021000000000022b019f00000534022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a000390000000000290435000011b90000013d000004f502000041000004f50310009c0000000001028019000000060400002900000a3a0000013d0000052d0870009c000012f00000213d0000004008700039000000400080043f000000000843034f000000010400003a00000000044704360000000008800350000000000808043b0000000000840435000009f80000613d0000052e08800197000000f806600210000000000686019f00000533066000410000000000640435000000400400043d00000020064000390000000008070433000000000908004b000010d10000613d0000000009000019000000000a6900190000002009900039000000000b790019000000000b0b04330000000000ba0435000000000a89004b000010ca0000413d000000000768001900000000000704350000000007480019000000200970003900000007080000290000000008080433000000000a08004b000010e10000613d000000000a000019000000000b9a0019000000200aa00039000000070ca00029000000000c0c04330000000000cb0435000000000b8a004b000010da0000413d000000000998001900000000000904350000000007780019000000200970003900000005080000290000000008080433000000000a08004b000010f10000613d000000000a000019000000000b9a0019000000200aa00039000000050ca00029000000000c0c04330000000000cb0435000000000b8a004b000010ea0000413d000000000998001900000000000904350000000007780019000000200970003900000004080000290000000008080433000000000a08004b000011010000613d000000000a000019000000000b9a0019000000200aa00039000000040ca00029000000000c0c04330000000000cb0435000000000b8a004b000010fa0000413d000000000998001900000000000904350000000007780019000000200970003900000003080000290000000008080433000000000a08004b000011110000613d000000000a000019000000000b9a0019000000200aa00039000000030ca00029000000000c0c04330000000000cb0435000000000b8a004b0000110a0000413d000000000998001900000000000904350000000007780019000000200970003900000002080000290000000008080433000000000a08004b000011210000613d000000000a000019000000000b9a0019000000200aa00039000000020ca00029000000000c0c04330000000000cb0435000000000b8a004b0000111a0000413d00000000099800190000000000090435000000000553034f00000000037800190000001f0720018f00000020083000390000000509200272000011320000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b0000112a0000413d000000000a07004b000011410000613d0000000509900210000000000595034f00000000089800190000000307700210000000000908043300000000097901cf000000000979022f000000000505043b0000010007700089000000000575022f00000000057501cf000000000595019f00000000005804350000000002230019000000200520003900000000000504350000000003010433000000000703004b0000114f0000613d000000000700001900000000085700190000002007700039000000000917001900000000090904330000000000980435000000000837004b000011480000413d000000000153001900000000000104350000000001420049000000000113001900000000001404350000003f01100039000000010210017f0000000001420019000000000221004b00000000020000190000000102004039000004fd0310009c000012f00000213d0000000102200190000012f00000c13d000000400010043f000004f501000041000004f50260009c000000000601801900000040026002100000000003040433000004f50430009c00000000030180190000006003300210000000000223019f0000122f0000013d0000001f0430018f0000000502300272000011740000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b0000116d0000413d000000000504004b000011820000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013d000010430000000380840008c000012dc0000413d0000002009400270000004f50840009c000000000904a019000004f50840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c000000000900001900000001090020390000052d0a60009c000012f00000213d000000000898019f0000004009600039000000400090043f000000000a21034f000000020980003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000009f80000613d0000052e0aa00197000000f80b800210000000000aab019f000005320aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf000000210960003900000000008904350000000008060019000012ed0000013d0000052d0da0009c000012f00000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000009f80000613d000000f809900210000000000229019f000005330220004100000000002d0435000000400200043d0000002009200039000005350b0000410000000000b90435000000210c200039000000000b0a0433000000000d0b004b000011c90000613d000000000d000019000000000ecd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ebd004b000011c20000413d000000000acb001900000000000a0435000000000a2b0019000000210ca00039000000000b060433000000000d0b004b000011d80000613d000000000d000019000000000ecd0019000000200dd00039000000000f6d0019000000000f0f04330000000000fe0435000000000ebd004b000011d10000413d0000000006cb001900000000000604350000000006ab0019000000210b600039000000000a080433000000000c0a004b000011e70000613d000000000c000019000000000dbc0019000000200cc00039000000000e8c0019000000000e0e04330000000000ed0435000000000dac004b000011e00000413d0000000008ba00190000000000080435000000000551034f00000000016a00190000001f0640018f0000002108100039000000050a400272000011f80000613d000000000b000019000000050cb00210000000000dc80019000000000cc5034f000000000c0c043b0000000000cd0435000000010bb00039000000000cab004b000011f00000413d000000000b06004b000012070000613d000000050aa002100000000005a5034f0000000008a800190000000306600210000000000a080433000000000a6a01cf000000000a6a022f000000000505043b0000010006600089000000000565022f00000000056501cf0000000005a5019f00000000005804350000000001410019000000210510003900000000000504350000000004070433000000000604004b000012150000613d000000000600001900000000085600190000002006600039000000000a760019000000000a0a04330000000000a80435000000000846004b0000120e0000413d0000000005540019000000000005043500000000012100490000000001140019000000010410003900000000004204350000004001100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000004fd0410009c000012f00000213d0000000103300190000012f00000c13d000000400010043f000004f501000041000004f50390009c000000000901801900000040039002100000000002020433000004f50420009c00000000020180190000006002200210000000000232019f0000000003000414000004f50430009c0000000003018019000000c001300210000000000121019f00000500011001c7000080100200003913ce13bf0000040f0000000101200190000001240000613d0000000901000029000000e4041000390000000201000367000000000241034f000000000202043b000004ff02200198000500000004001d0000125a0000c13d000000800240008a000000000321034f000000400240008a000000000521034f000000000403043b000000000505043b00000000634500a9000000000605004b0000124d0000613d00000000655300d9000000000445004b000012560000c13d0000008002200039000000000121034f000000000101043b000700000031001d000000070110006b0000000001000019000000010100403900000001011001900000125f0000613d0000054601000041000000000010043500000011010000390000003c0000013d00000009020000290000012402200039000000000121034f000000000101043b000700000001001d0000054101000041000000000010043900000006010000290000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000519011001c70000800a0200003913ce13bf0000040f00000001022001900000127a0000613d000000000101043b000000070110006b0000127b0000a13d000000400100043d00000064021000390000054403000041000000000032043500000044021000390000054503000041000000000032043500000024021000390000002203000039000001020000013d000000000001042f0000000003000031000000090130006a000000230410008a000000050100002900000100011000390000000202000367000000000112034f000000000101043b000004fe05000041000000000641004b00000000060000190000000006058019000004fe04400197000004fe07100197000000000847004b0000000005008019000000000447013f000004fe0440009c000000000506c019000000000405004b000001240000c13d0000000804100029000000000142034f000000000101043b000004fd0510009c000001240000213d00000000061300490000002005400039000004fe04000041000000000765004b00000000070000190000000007042019000004fe06600197000004fe08500197000000000968004b0000000004008019000000000668013f000004fe0660009c000000000407c019000000000404004b000001240000c13d0000003f04100039000000200600008a000000000664016f000000400400043d0000000006640019000000000746004b00000000070000190000000107004039000004fd0860009c000012f00000213d0000000107700190000012f00000c13d000000400060043f00000000041404360000000006510019000000000336004b000001240000213d000000000352034f0000001f0210018f0000000505100272000012c20000613d000000000600001900000005076002100000000008740019000000000773034f000000000707043b00000000007804350000000106600039000000000756004b000012ba0000413d000000000602004b000012d10000613d0000000505500210000000000353034f00000000055400190000000302200210000000000605043300000000062601cf000000000626022f000000000303043b0000010002200089000000000323022f00000000022301cf000000000262019f0000000000250435000000000114001900000000000104350000054201000041000000400200043d0000000000120435000004f501000041000004f50320009c0000000002018019000000400120021000000543011001c7000013cf0001042e0000052d0860009c000012f00000213d0000004008600039000000400080043f000000000921034f000000010800003a00000000088604360000000009900350000000000909043b0000000000980435000009f80000613d000000f80a4002100000052e099001970000000009a9019f000004fe0990016700000000009804350000000008060019000000400600043d0000052d0960009c000012f40000a13d0000054601000041000000000010043500000041010000390000003c0000013d0000004009600039000000400090043f000000000221034f000000010c00003a0000000009c604360000000002200350000000000b02043b0000000000b90435000009f80000613d0000052e02b00197000005330a2001c70000000000a9043500000000090704330000000009490019000000000a0804330000000009a90019000000000a0604330000000009a90019000000400a00043d000004fd09900197000000380d90008c0000132c0000413d000000200d900270000004f50c90009c000000000d09a019000004f50c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d0020390000052d0ea0009c000012f00000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000009f80000613d000000f80bc0021000000000022b019f00000534022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a000390000000000290435000013390000013d0000052d0da0009c000012f00000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000009f80000613d000000f809900210000000000229019f000005330220004100000000002d0435000000400200043d0000002009200039000005000b0000410000000000b90435000000210c200039000000000b0a0433000000000d0b004b000013490000613d000000000d000019000000000ecd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ebd004b000013420000413d000000000acb001900000000000a0435000000000a2b0019000000210ca00039000000000b070433000000000d0b004b000013580000613d000000000d000019000000000ecd0019000000200dd00039000000000f7d0019000000000f0f04330000000000fe0435000000000ebd004b000013510000413d0000000007cb001900000000000704350000000007ab0019000000210b700039000000000a080433000000000c0a004b000013670000613d000000000c000019000000000dbc0019000000200cc00039000000000e8c0019000000000e0e04330000000000ed0435000000000dac004b000013600000413d0000000008ba00190000000000080435000000000551034f00000000017a00190000001f0740018f0000002108100039000000050a400272000013780000613d000000000b000019000000050cb00210000000000dc80019000000000cc5034f000000000c0c043b0000000000cd0435000000010bb00039000000000cab004b000013700000413d000000000b07004b000013870000613d000000050aa002100000000005a5034f0000000008a800190000000307700210000000000a080433000000000a7a01cf000000000a7a022f000000000505043b0000010007700089000000000575022f00000000057501cf0000000005a5019f00000000005804350000000001410019000000210510003900000000000504350000000004060433000000000704004b000013950000613d000000000700001900000000085700190000002007700039000000000a670019000000000a0a04330000000000a80435000000000847004b0000138e0000413d0000000005540019000000000005043500000000012100490000000001140019000000010410003900000000004204350000004001100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000004fd0410009c000012f00000213d0000000103300190000012f00000c13d000012250000013d00000000030104330000000002320436000000000403004b000013b20000613d000000000400001900000000052400190000002004400039000000000614001900000000060604330000000000650435000000000534004b000013ab0000413d000000000123001900000000000104350000001f01300039000000200300008a000000000131016f0000000001120019000000000001042d000000000001042f000013bd002104210000000102000039000000000001042d0000000002000019000000000001042d000013c2002104230000000102000039000000000001042d0000000002000019000000000001042d000013c7002104210000000102000039000000000001042d0000000002000019000000000001042d000013cc002104230000000102000039000000000001042d0000000002000019000000000001042d000013ce00000432000013cf0001042e000013d00001043000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000df9c158800000000000000000000000000000000000000000000000000000000df9c158900000000000000000000000000000000000000000000000000000000e2f318e300000000000000000000000000000000000000000000000000000000eeb8cb0900000000000000000000000000000000000000000000000000000000202bcce700000000000000000000000000000000000000000000000000000000a28c1aee000000000000000000000000000000000000000000000000ffffffffffffffff8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff02000000000000000000000000000000000000000000000000000000000000007261746f720000000000000000000000000000000000000000000000000000004661696c656420746f20706179207468652066656520746f20746865206f706508c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000840000000000000000000000000000000000000000000000000000000100000000000000000000000000000000ffffffff000000000000000000000000000000000000000000000000000000009c4d535affffffffffffffffffffffffffffffffffffffffffffffffffffffff9c4d535b00000000000000000000000000000000000000000000000000000000ecf95b8a000000000000000000000000000000000000000000000000000000003cda3351000000000000000000000000000000000000000000000000000000005d3827000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000000000000000000000000000000000000000000000100000100000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001ffffffe04f766572666c6f7700000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000008000000000000000008c5a344500000000000000000000000000000000000000000000000000000000949431dc00000000000000000000000000000000000000000000000000000000dd62ed3e000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000044000000800000000000000000095ea7b3000000000000000000000000000000000000000000000000000000005361666545524332303a206c6f772d6c6576656c2063616c6c206661696c65641806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b83020000020000000000000000000000000000002400000000000000000000000000000000000000000000000000000000000000440000000000000000000000005361666545524332303a20617070726f76652066726f6d206e6f6e2d7a65726f20746f206e6f6e2d7a65726f20616c6c6f77616e636500000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff7f000000000000000000000000000000000000000000000000ffffffffffffff3f6f742073756363656564000000000000000000000000000000000000000000005361666545524332303a204552433230206f7065726174696f6e20646964206e416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000000000000000000000000000000000000000006400000000000000000000000054686520617070726f76616c4261736564207061796d617374657220696e707574206d757374206265206174206c65617374203638206279746573206c6f6e670000000000000000000000000000000000000084000000800000000000000000556e737570706f72746564207061796d617374657220666c6f77000000000000546865207374616e64617264207061796d617374657220696e707574206d757374206265206174206c656173742034206279746573206c6f6e67000000000000e1239cd8000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000024000000a000000000000000009a8a0592ac89c5ad3bc6df8224c17b485976f597df104ee20d0df415241f670b0200000200000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffbf00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00000000000000000000000000000000ffffffffffffffffffffffffffffffff81000000000000000000000000000000000000000000000000000000000000009400000000000000000000000000000000000000000000000000000000000000b800000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000000f8000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000007ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff6b656363616b3235362072657475726e656420696e76616c6964206461746100848e1bfa1ac4e3576b728bda6721b215c70a7799a5b4866282a71bab954baac8000000000000000000000000000000000000000000000000fffffffffffffe1fc2f8787176b8ac6bf7215b4adcc1e069bf4ab82d9ab1df05a57a91d425935b6ead7c5bef027816a800da1736444fb58a807ef4c9603b7848673f7e3a68eb14a519b453ce45aaaaf3a300f5a9ec95869b4f28ab10430b572ee218c3a6a5e07d6f000000000000000000000000000000000000000000000000ffffffffffffff5f190100000000000000000000000000000000000000000000000000000000000080800000000000000000000000000000000000000000000000000000000000009cc7f708afc65944829bd487b90b72536b1951864fbfc14e125fc972a6507f39202bcce700000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002000000000000000000000000075650000000000000000000000000000000000000000000000000000000000004e6f7420656e6f7567682062616c616e636520666f7220666565202b2076616c4e487b71000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000456e636f64696e6720756e737570706f72746564207478000000000000000000000000000000000000000000000000000000000000000000000000000000000003a0b6db1c535c3eb557511f12bd7cdd9e744966ba523d3461ac1c1d3bedc017", + "deployedBytecode": "0x0004000000000002000b00000000000200000000030100190000006007300270000004f50670019700030000006103550002000000010355000004f50070019d0000008004000039000000400040043f00000001022001900000002c0000c13d000000040260008c000000340000413d000000000201043b000000e002200270000004f70320009c0000003f0000a13d000004f80320009c000000930000613d000004f90320009c000000c20000613d000004fa0220009c000000360000c13d000000040260008a000000200320008c000001240000413d0000000401100370000000000101043b000004fd0310009c000001240000213d0000000001120049000004fe02000041000002600310008c00000000030000190000000003024019000004fe01100197000000000401004b000000000200a019000004fe0110009c000000000203c019000000000102004b000010610000613d000001240000013d0000000001000416000000000101004b000001240000c13d000000200100003900000100001004430000012000000443000004f601000041000013cf0001042e000000000106004b000010610000613d0000000001000411000080010110008c000010610000c13d000005460100004100000000001004350000000101000039000000040010043f0000054701000041000013d000010430000004fb0320009c0000010e0000613d000900000004001d000004fc0220009c000000360000c13d000000040260008a000000600220008c000001240000413d0000004402100370000000000302043b000004fd0230009c000001240000213d00000004043000390000000005460049000004fe02000041000002600750008c00000000070000190000000007024019000004fe08500197000000000908004b000000000200a019000004fe0880009c000000000207c019000000000202004b000001240000c13d0000000002000411000080010220008c000010610000c13d0000000002000412000004ff072001970000000002000410000000000727004b000010610000c13d0000022403300039000000000731034f000000000707043b0000001f0550008a000004fe08000041000000000957004b00000000090000190000000009088019000004fe05500197000004fe0a700197000000000b5a004b000000000800801900000000055a013f000004fe0550009c000000000809c019000000000508004b000001240000c13d0000000005470019000000000451034f000000000404043b000004fd0740009c000001240000213d00000000074600490000002005500039000004fe08000041000000000975004b00000000090000190000000009082019000004fe07700197000004fe0a500197000000000b7a004b000000000800801900000000077a013f000004fe0770009c000000000809c019000000000708004b000001240000c13d000000030740008c000002470000213d0000050301000041000000800010043f0000002001000039000000840010043f0000003a01000039000000a40010043f0000052701000041000000c40010043f0000052801000041000000e40010043f0000052501000041000013d000010430000000040260008a000000600220008c000001240000413d0000004402100370000000000302043b000004fd0230009c000001240000213d00000004023000390000000005260049000004fe04000041000002600850008c00000000080000190000000008044019000004fe09500197000000000a09004b000000000400a019000004fe0990009c000000000408c019000000000404004b000001240000c13d0000000004000411000080010440008c000010610000c13d0000000004000412000004ff044001970000000008000410000000000484004b000010610000c13d0000004404300039000000000441034f0000012408300039000000000381034f000000000404043b000004ff04400197000000000303043b000005050930009c000002030000413d0000050301000041000000800010043f0000002001000039000000840010043f0000000801000039000000a40010043f0000051001000041000000c40010043f0000051101000041000013d000010430000000040360008a000000600230008c000001240000413d0000004402100370000000000202043b000004fd0420009c000001240000213d0000000003230049000004fe04000041000002600530008c00000000050000190000000005044019000004fe03300197000000000603004b000000000400a019000004fe0330009c000000000405c019000000000304004b000001240000c13d0000000003000411000080010330008c000010610000c13d0000000003000412000004ff033001970000000004000410000000000343004b000010610000c13d000000a403200039000000000331034f0000006402200039000000000121034f000000000101043b000000000203043b000000000302004b000001eb0000c13d00000000040004150000000b0440008a00000020044000c90000000001000414000b00000000001d000900000004001d000004f502000041000004f50310009c0000000001028019000000c001100210000080010200003913ce13ba0000040f000000090300002900030000000103550000006001100270000104f50010019d000000050130027000000001012001950000000101200190000010610000c13d000000400100043d00000064021000390000050103000041000000000032043500000044021000390000050203000041000000000032043500000024021000390000002503000039000000000032043500000503020000410000000000210435000000040210003900000020030000390000000000320435000004f502000041000004f50310009c0000000001028019000000400110021000000504011001c7000013d000010430000000040260008a000000600220008c000001240000413d0000004402100370000000000202043b000900000002001d000004fd0220009c000001240000213d0000000902000029000800040020003d000000080260006a000004fe03000041000002600420008c00000000040000190000000004034019000004fe02200197000000000502004b000000000300a019000004fe0220009c000000000304c019000000000203004b000001260000613d0000000001000019000013d0000104300000002402100370000000000202043b000700000002001d0000000002000411000080010220008c000010610000c13d0000000002000412000004ff022001970000000003000410000600000003001d000000000232004b000010610000c13d00000000020004140000052903000041000000a00030043f0000000903000029000501040030003d0000000501100360000000000101043b000000a40010043f0000002401000039000000800010043f000000e001000039000000400010043f000000c0012002100000050c011001970000052a011001c70000800302000039000000000300001900000000040000190000000005000019000000000600001913ce13ba0000040f000300000001035500000000030100190000006003300270000104f50030019d000004f5083001970000003f038000390000050f04300197000000400600043d0000000003640019000000000443004b00000000040000190000000104004039000004fd0530009c000012f00000213d0000000104400190000012f00000c13d000000400030043f000000000786043600000002030003670000000004000031000000000543034f0000001f098000390000000509900272000001680000613d000000000a000019000000050ba00210000000000cb70019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000001600000413d000000000900004b0000016a0000613d0000001f0980018f0000000508800272000001760000613d000000000a000019000000050ba00210000000000cb70019000000000bb1034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b0000016e0000413d000000000a09004b000001850000613d0000000508800210000000000181034f00000000088700190000000309900210000000000a080433000000000a9a01cf000000000a9a022f000000000101043b0000010009900089000000000191022f00000000019101cf0000000001a1019f000000000018043500000001012001900000023d0000613d000000070100006b000012390000c13d0000000501000029000001000110008a000000000113034f000000000101043b000000010210008c0000025a0000213d000000000201004b000002a90000613d000000010110008c000002970000c13d0000052b010000410000000000100439000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000052c011001c70000800b0200003913ce13bf0000040f00000001022001900000127a0000613d000000400300043d000000000401043b000000800140008c000004760000413d00000080014002700000052f0240009c000000000104a0190000052f0240009c0000000002000019000000100200203900000008052001bf000004fd0610009c000000000502a0190000004002100270000004fd0610009c000000000201a01900000004015001bf000004f50620009c000000000105a0190000002006200270000004f50520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000004fd0610009c000012f00000213d0000000102200190000012f00000c13d000000400010043f000000020150003900000000061304360000000201000367000000000200003100000021075000390000000507700272000001d90000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000001d10000413d000000000700004b000001db0000613d0000000007030433000000000707004b000009f80000613d00000000070604330000052e07700197000000f808500210000000000778019f000005300770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c00000000040020190000002105300039000004890000013d00000000431200a900000000422300d9000000000112004b000012560000c13d00000000040004150000000a0440008a00000020044000c90000000001000414000a00000000001d000000000203004b000000ea0000613d000004f502000041000004f50410009c0000000001028019000000c00110021000000500011001c700008009020000390000800104000039000000000500001913ce13ba0000040f00000000030004150000000a0330008a00000020033000c9000000f20000013d000000a008800039000000000881034f000000000808043b0000001f0550008a000004fe09000041000000000a58004b000000000a000019000000000a098019000004fe05500197000004fe0b800197000000000c5b004b000000000900801900000000055b013f000004fe0550009c00000000090ac019000000000509004b000001240000c13d0000000002280019000000000521034f000000000805043b000004fd0580009c000001240000213d00000000058600490000002009200039000004fe02000041000000000a59004b000000000a000019000000000a022019000004fe05500197000004fe0b900197000000000c5b004b000000000200801900000000055b013f000004fe0550009c00000000020ac019000000000202004b000001240000c13d0000000002000414000004f50520009c000000b80000213d000080060540008c0000000005000019000003d90000c13d000000040580008c0000000005000019000003d90000413d000000000a91034f0000000105000039000000000a0a043b000005060aa00197000005070ba0009c000003d50000213d0000050a0ba0009c000003d90000613d0000050b0aa0009c000003d90000613d0000000005000019000003d90000013d0000000001060433000004f502000041000004f50310009c0000000001028019000004f50370009c000000000702801900000040027002100000006001100210000000000121019f000013d000010430000000000751034f000000000707043b0000050607700197000005120870009c000010610000613d000005130770009c0000034f0000c13d000000430440008c000003b60000213d0000050301000041000000800010043f0000002001000039000000840010043f0000004001000039000000a40010043f0000052301000041000000c40010043f0000052401000041000000900000013d000000020210008c000002f70000613d000000710110008c000002970000c13d0000000902000029000001c401200039000000000113034f0000000002240049000000230220008a000000000101043b000004fe05000041000000000621004b00000000060000190000000006058019000004fe02200197000004fe07100197000000000827004b0000000005008019000000000227013f000004fe0220009c000000000506c019000000000205004b000001240000c13d0000000801100029000000000213034f000000000202043b000004fd0520009c000001240000213d00000000052400490000002001100039000004fe06000041000000000751004b00000000070000190000000007062019000004fe05500197000004fe08100197000000000958004b0000000006008019000000000558013f000004fe0550009c000000000607c019000000000506004b000001240000c13d00000000050004140000000006120019000000000226004b000000000200001900000001020040390000000102200190000012560000c13d000000000264004b000012560000413d000005360250009c000006c40000413d000000400100043d000000440210003900000510030000410000000000320435000000240210003900000008030000390000029d0000013d000000400100043d00000044021000390000054803000041000000000032043500000024021000390000001703000039000000000032043500000503020000410000000000210435000000040210003900000020030000390000000000320435000004f502000041000004f50310009c0000000001028019000000400110021000000522011001c7000013d0000104300000000501300360000000400200043d000700000002001d000000000101043b000000800210008c000003570000413d00000080021002700000052f0610009c000000000201a0190000052f0610009c0000000006000019000000100600203900000008076001bf000004fd0820009c000000000706a0190000004006200270000004fd0820009c000000000602a01900000004087001bf000004f50260009c000000000807a0190000002007600270000004f50260009c000000000706a01900000002028001bf0000ffff0670008c000000000208a0190000001006700270000000000607a019000000ff0660008c0000000102202039000000200600008a0000004107200039000000000667016f0000000706600029000000070760006c00000000070000190000000107004039000004fd0860009c000012f00000213d0000000107700190000012f00000c13d000000400060043f00000002062000390000000707000029000000000667043600000021072000390000000507700272000002e30000613d00000000080000190000000509800210000000000a960019000000000995034f000000000909043b00000000009a04350000000108800039000000000978004b000002db0000413d000000000700004b000002e50000613d00000007070000290000000007070433000000000707004b000009f80000613d00000000070604330000052e07700197000000f808200210000000000778019f000005300770004100000000007604350000000302200210000000f80220008900000000012101cf000000ff0220008c000000000100201900000007020000290000002102200039000003690000013d0000052b010000410000000000100439000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000052c011001c70000800b0200003913ce13bf0000040f00000001022001900000127a0000613d000000400300043d000000000401043b000000800140008c000004d50000413d00000080014002700000052f0240009c000000000104a0190000052f0240009c0000000002000019000000100200203900000008052001bf000004fd0610009c000000000502a0190000004002100270000004fd0610009c000000000201a01900000004015001bf000004f50620009c000000000105a0190000002006200270000004f50520009c000000000602a01900000002051001bf0000ffff0260008c000000000501a0190000001001600270000000000106a019000000ff0110008c0000000105502039000000200100008a0000004102500039000000000112016f0000000001130019000000000231004b00000000020000190000000102004039000004fd0610009c000012f00000213d0000000102200190000012f00000c13d000000400010043f0000000201500039000000000613043600000002010003670000000002000031000000210750003900000005077002720000033d0000613d000000000821034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000003350000413d000000000700004b0000033f0000613d0000000007030433000000000707004b000009f80000613d00000000070604330000052e07700197000000f808500210000000000778019f000005300770004100000000007604350000000305500210000000f80550008900000000045401cf000000ff0550008c00000000040020190000002105300039000004e80000013d0000050301000041000000800010043f0000002001000039000000840010043f0000001a01000039000000a40010043f0000052601000041000000bf0000013d00000007020000290000052d0220009c000012f00000213d00000007060000290000004002600039000000400020043f000000010200003a00000000022604360000000006500350000000000606043b0000000000620435000009f80000613d000000f807100210000004fe08000041000000000101004b000000000807c0190000052e01600197000000000181019f0000000000120435000000400100043d0000000502000029000000600220008a000000000623034f000000000606043b000000800760008c000005340000413d00000080076002700000052f0860009c000000000706a0190000052f0860009c0000000008000019000000100800203900000008098001bf000004fd0a70009c000000000908a0190000004008700270000004fd0a70009c000000000807a019000000040a9001bf000004f50780009c000000000a09a0190000002009800270000004f50780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008810019000000000918004b00000000090000190000000109004039000004fd0a80009c000012f00000213d0000000109900190000012f00000c13d000000400080043f0000000208700039000000000881043600000021097000390000000509900272000003a40000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b0000039c0000413d000000000900004b000003a60000613d0000000009010433000000000909004b000009f80000613d00000000090804330000052e09900197000000f80a70021000000000099a019f000005300990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c00000000060020190000002107100039000005440000013d0000000404500039000000000541034f000000000505043b000800000005001d000004ff0550009c000001240000213d000001400330008a000000000331034f0000002004400039000000000441034f000000000404043b000700000004001d000000000303043b0000051404000041000000800040043f000004ff02200197000500000002001d000000840020043f000004ff02300197000600000002001d000000a40020043f00000000020004140000000803000029000000040330008c000005900000c13d000000000161034f0000000103000031000000200230008c00000000040300190000002004008039000005bc0000013d000005080ba0009c000003d90000613d000005090aa0009c000000000500c019000000000a9800190000000006a6004b0000000006000019000000010600403900000000088a004b00000001066041bf000004f508900197000000000181034f000000000803004b000003f20000c13d0000000103600190000012560000c13d0000050d030000410000050e06000041000000000505004b000000000603c019000000c0022002100000050c02200197000000000226019f0000000003a70049000004f50330019700000000013103df00000000012103af0000000002040019000003fd0000013d0000000106600190000012560000c13d0000000006a70049000004f50660019700000000016103df000000c0022002100000050c022001970000050d022001c700000000012103af0000800902000039000000000600001913ce13c40000040f000300000001035500000000030100190000006003300270000104f50030019d000004f50330019700000001022001900000045b0000613d0000003f023000390000050f04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000004fd0640009c000012f00000213d0000000105500190000012f00000c13d000000400040043f00000000043204360000001f053000390000000505500272000004200000613d00000000060000310000000206600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b000004180000413d000000000500004b000004220000613d0000001f0530018f00000005033002720000042e0000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b000004260000413d000000000605004b0000043d0000613d0000000503300210000000000131034f00000000033400190000000304500210000000000503043300000000054501cf000000000545022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f0000000000130435000000400100043d00000020030000390000000004310436000000000302043300000000003404350000004004100039000000000503004b0000044d0000613d000000000500001900000000064500190000002005500039000000000725001900000000070704330000000000760435000000000635004b000004460000413d000000000243001900000000000204350000005f02300039000000200300008a000000000232016f000004f503000041000004f50420009c0000000002038019000004f50410009c000000000103801900000040011002100000006002200210000000000112019f000013cf0001042e0000001f0430018f0000000502300272000004660000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b0000045f0000413d000000000504004b000004740000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013d0000104300000052d0130009c000012f00000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000201000367000000000621034f0000000006600350000000000606043b0000000000650435000009f80000613d000000f807400210000004fe08000041000000000404004b000000000807c0190000052e04600197000000000484019f00000000004504350000000505100360000000400400043d000000000505043b000000800650008c000005e30000413d00000080065002700000052f0750009c000000000605a0190000052f0750009c0000000007000019000000100700203900000008087001bf000004fd0960009c000000000807a0190000004007600270000004fd0960009c000000000706a01900000004098001bf000004f50670009c000000000908a0190000002008700270000004f50670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007740019000000000847004b00000000080000190000000108004039000004fd0970009c000012f00000213d0000000108800190000012f00000c13d000000400070043f0000000207600039000000000774043600000021086000390000000508800272000004c30000613d000000000921034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b000004bb0000413d000000000800004b000004c50000613d0000000008040433000000000808004b000009f80000613d00000000080704330000052e08800197000000f809600210000000000889019f000005300880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106400039000005f40000013d0000052d0130009c000012f00000213d0000004001300039000000400010043f000000010100003a000000000513043600000000020000310000000201000367000000000621034f0000000006600350000000000606043b0000000000650435000009f80000613d000000f807400210000004fe08000041000000000404004b000000000807c0190000052e04600197000000000484019f00000000004504350000000505100360000000400400043d000000000505043b000000800650008c000006420000413d00000080065002700000052f0750009c000000000605a0190000052f0750009c0000000007000019000000100700203900000008087001bf000004fd0960009c000000000807a0190000004007600270000004fd0960009c000000000706a01900000004098001bf000004f50670009c000000000908a0190000002008700270000004f50670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c0000000106602039000000200700008a0000004108600039000000000778016f0000000007740019000000000847004b00000000080000190000000108004039000004fd0970009c000012f00000213d0000000108800190000012f00000c13d000000400070043f0000000207600039000000000774043600000021086000390000000508800272000005220000613d000000000921034f000000000a000019000000050ba00210000000000cb70019000000000bb9034f000000000b0b043b0000000000bc0435000000010aa00039000000000b8a004b0000051a0000413d000000000800004b000005240000613d0000000008040433000000000808004b000009f80000613d00000000080704330000052e08800197000000f809600210000000000889019f000005300880004100000000008704350000000306600210000000f80660008900000000056501cf000000ff0660008c00000000050020190000002106400039000006530000013d0000052d0710009c000012f00000213d0000004007100039000000400070043f000000010700003a00000000077104360000000008500350000000000808043b0000000000870435000009f80000613d000000f809600210000004fe0a000041000000000606004b000000000a09c0190000052e068001970000000006a6019f0000000000670435000000400220008a000000000623034f000000400200043d000000000606043b000000800760008c0000089b0000413d00000080076002700000052f0860009c000000000706a0190000052f0860009c0000000008000019000000100800203900000008098001bf000004fd0a70009c000000000908a0190000004008700270000004fd0a70009c000000000807a019000000040a9001bf000004f50780009c000000000a09a0190000002009800270000004f50780009c000000000908a0190000000207a001bf0000ffff0890008c00000000070aa0190000001008900270000000000809a019000000ff0880008c0000000107702039000000200800008a0000004109700039000000000889016f0000000008820019000000000928004b00000000090000190000000109004039000004fd0a80009c000012f00000213d0000000109900190000012f00000c13d000000400080043f00000002087000390000000008820436000000210970003900000005099002720000057e0000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b000005760000413d000000000900004b000005800000613d0000000009020433000000000909004b000009f80000613d00000000090804330000052e09900197000000f80a70021000000000099a019f000005300990004100000000009804350000000307700210000000f80770008900000000067601cf000000ff0770008c00000000060020190000002107200039000008ab0000013d000004f501000041000004f50320009c0000000002018019000000c00120021000000515011001c7000000080200002913ce13bf0000040f00000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000005a90000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000005a10000413d000000000705004b000005b80000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f00030000000103550000000102200190000006a10000613d0000001f02400039000000600520018f00000080025001bf000000400020043f000000200430008c000001240000413d000000800400043d000000070440006c000010610000813d000000a00450003900000516060000410000000000640435000000a40650003900000006070000290000000000760435000000c40650003900000000000604350000004406000039000100000006001d00000000006204350000014006500039000000400060043f00000120065000390000051707000041000000000076043500000100065001bf0000002005000039000300000005001d000200000006001d0000000000560435000000000502043300000000020004140000000806000029000000040660008c000009390000c13d0000000102000039000004fd0430009c000012f00000213d0000094d0000013d0000052d0640009c000012f00000213d0000004006400039000000400060043f000000000721034f000000010600003a00000000066404360000000007700350000000000707043b0000000000760435000009f80000613d000000f808500210000004fe09000041000000000505004b000000000908c0190000052e05700197000000000595019f0000000000560435000000400500043d0000000506000029000000600660008a000000000761034f000000000707043b000000800870008c0000098f0000413d00000080087002700000052f0970009c000000000807a0190000052f0970009c00000000090000190000001009002039000000080a9001bf000004fd0b80009c000000000a09a0190000004009800270000004fd0b80009c000000000908a019000000040ba001bf000004f50890009c000000000b0aa019000000200a900270000004f50890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000004fd0b90009c000012f00000213d000000010aa00190000012f00000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa00272000006300000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000006280000413d000000000a00004b000006320000613d000000000a050433000000000a0a004b000009f80000613d000000000a0904330000052e0aa00197000000f80b800210000000000aab019f000005300aa000410000000000a904350000000308800210000000f80880008900000000078701cf000000ff0880008c00000000070020190000002108500039000009a00000013d0000052d0640009c000012f00000213d0000004006400039000000400060043f000000000721034f000000010600003a00000000066404360000000007700350000000000707043b0000000000760435000009f80000613d000000f808500210000004fe09000041000000000505004b000000000908c0190000052e05700197000000000595019f0000000000560435000000400500043d0000000506000029000000400760008a000000000671034f000000000606043b000000800860008c000009ed0000413d00000080086002700000052f0960009c000000000806a0190000052f0960009c00000000090000190000001009002039000000080a9001bf000004fd0b80009c000000000a09a0190000004009800270000004fd0b80009c000000000908a019000000040ba001bf000004f50890009c000000000b0aa019000000200a900270000004f50890009c000000000a09a0190000000208b001bf0000ffff09a0008c00000000080ba0190000001009a0027000000000090aa019000000ff0990008c0000000108802039000000200900008a000000410a80003900000000099a016f0000000009950019000000000a59004b000000000a000019000000010a004039000004fd0b90009c000012f00000213d000000010aa00190000012f00000c13d000000400090043f00000002098000390000000009950436000000210a800039000000050aa002720000068f0000613d000000000b21034f000000000c000019000000050dc00210000000000ed90019000000000ddb034f000000000d0d043b0000000000de0435000000010cc00039000000000dac004b000006870000413d000000000a00004b000006910000613d000000000a050433000000000a0a004b000009f80000613d000000000a0904330000052e0aa00197000000f80b800210000000000aab019f000005300aa000410000000000a904350000000308800210000000f80880008900000000068601cf000000ff0880008c0000000006002019000000210850003900000abc0000013d000000400200043d0000001f0430018f0000000505300272000006ae0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000006a60000413d000000000604004b000006bd0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000004f501000041000004f50420009c000000000201801900000040012002100000006002300210000000000121019f000013d000010430000004f501100197000000000113034f0000000002640049000004f50220019700000000012103df000000c0025002100000050c022001970000050e022001c700000000012103af000080100200003913ce13c90000040f00000000030100190000006003300270000104f50030019d000004f50530019700030000000103550000000102200190000009fc0000613d0000003f025000390000050f02200197000000400600043d0000000002260019000000000362004b00000000030000190000000103004039000004fd0420009c000012f00000213d0000000103300190000012f00000c13d000000400020043f0000000004560436000000020200036700000000030000310000001f075000390000000507700272000006f20000613d000000000832034f0000000009000019000000050a900210000000000ba40019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b000006ea0000413d000000000700004b000006f40000613d0000001f0750018f0000000505500272000007000000613d00000000080000190000000509800210000000000a940019000000000991034f000000000909043b00000000009a04350000000108800039000000000958004b000006f80000413d000000000807004b0000070f0000613d0000000505500210000000000151034f00000000055400190000000307700210000000000805043300000000087801cf000000000878022f000000000101043b0000010007700089000000000171022f00000000017101cf000000000181019f00000000001504350000000001060433000000200110008c00000a3e0000c13d00000009060000290000000001630049000000230510008a000702040060003d0000000701200360000000000101043b000004fe06000041000000000751004b00000000070000190000000007068019000004fe05500197000004fe08100197000000000958004b0000000006008019000000000558013f000004fe0550009c000000000607c019000000000506004b000001240000c13d0000000004040433000400000004001d0000000801100029000000000412034f000000000504043b000004fd0450009c000001240000213d000000050450021000000000034300490000002006100039000004fe01000041000000000736004b00000000070000190000000007012019000004fe03300197000004fe08600197000000000938004b0000000001008019000000000338013f000004fe0330009c000000000107c019000000000101004b000001240000c13d000000400100043d000000200310003900000537055001980000074a0000613d000000000262034f000000000600001900000005076002100000000008730019000000000772034f000000000707043b00000000007804350000000106600039000000000756004b000007420000413d000000000200004b0000074c0000613d00000000004104350000003f02400039000000200400008a000000000242016f0000000002210019000000000412004b00000000040000190000000104004039000004fd0520009c000012f00000213d0000000104400190000012f00000c13d000000400020043f000004f502000041000004f50430009c000000000302801900000040033002100000000001010433000004f50410009c00000000010280190000006001100210000000000131019f0000000003000414000004f50430009c0000000003028019000000c002300210000000000112019f00000500011001c7000080100200003913ce13bf0000040f0000000102200190000001240000613d0000000002000031000000090320006a000000230530008a000000070300002900000020043000390000000203000367000000000443034f000000000404043b000004fe06000041000000000754004b00000000070000190000000007068019000004fe05500197000004fe08400197000000000958004b0000000006008019000000000558013f000004fe0550009c000000000607c019000000000101043b000700000001001d000000000106004b000001240000c13d0000000801400029000000000413034f000000000404043b000004fd0540009c000001240000213d00000000054200490000002001100039000004fe06000041000000000751004b00000000070000190000000007062019000004fe05500197000004fe08100197000000000958004b0000000006008019000000000558013f000004fe0550009c000000000607c019000000000506004b000001240000c13d00000000050004140000000006140019000000000446004b000000000400001900000001040040390000000104400190000012560000c13d000000000462004b000012560000413d000004f50450009c000002900000213d000004f501100197000000000113034f0000000002620049000004f50220019700000000012103df000000c0025002100000050c022001970000050e022001c700000000012103af000080100200003913ce13c90000040f00000000030100190000006003300270000104f50030019d000004f50330019700030000000103550000000102200190000011690000613d0000003f023000390000050f02200197000000400500043d0000000002250019000000000452004b00000000040000190000000104004039000004fd0620009c000012f00000213d0000000104400190000012f00000c13d000000400020043f000000000235043600000002040003670000001f063000390000000506600272000007cf0000613d000000000740036800000000080000190000000509800210000000000a920019000000000997034f000000000909043b00000000009a04350000000108800039000000000968004b000007c70000413d000000000600004b000007d10000613d0000001f0630018f0000000503300272000007dd0000613d000000000700001900000005087002100000000009820019000000000881034f000000000808043b00000000008904350000000107700039000000000837004b000007d50000413d000000000706004b000007ec0000613d0000000503300210000000000131034f00000000033200190000000306600210000000000703043300000000076701cf000000000767022f000000000101043b0000010006600089000000000161022f00000000016101cf000000000171019f00000000001304350000000001050433000000200110008c00000a3e0000c13d000000090c0000290000006401c00039000000000114034f0000004403c00039000000000534034f0000002403c00039000000000634034f0000012403c00039000000000734034f0000000508400360000000e403c00039000000000934034f000000c403c00039000000000a34034f000000a403c00039000000000b34034f0000008403c00039000000000c34034f0000000803400360000000000303043b000000000406043b000000000505043b000000000601043b000000000c0c043b000000000b0b043b000000000a0a043b000000000909043b000000000808043b000000000707043b0000000002020433000000400100043d000001c00d10003900000000002d0435000001a002100039000000070d0000290000000000d204350000018002100039000000040d0000290000000000d2043500000160021000390000000000720435000001400210003900000000008204350000012002100039000000000092043500000100021000390000000000a20435000000e0021000390000000000b20435000000c0021000390000000000c20435000000a0021000390000000000620435000000800210003900000000005204350000006002100039000000000042043500000040021000390000000000320435000000200210003900000539030000410000000000320435000001c00300003900000000003104350000053a0310009c000012f00000213d000001e003100039000000400030043f000004f504000041000004f50320009c000000000204801900000040022002100000000001010433000004f50310009c00000000010480190000006001100210000000000121019f0000000002000414000004f50320009c0000000002048019000000c002200210000000000112019f00000500011001c7000080100200003913ce13bf0000040f0000000102200190000001240000613d000000000101043b000500000001001d000000400100043d000700000001001d0000052b0100004100000000001004390000000001000414000004f50210009c000004f501008041000000c0011002100000052c011001c70000800b0200003913ce13bf0000040f00000001022001900000127a0000613d00000007040000290000002002400039000000000101043b0000053b0300004100000000003204350000008003400039000000000013043500000060014000390000053c03000041000000000031043500000040014000390000053d030000410000000000310435000000800100003900000000001404350000053e0140009c000012f00000213d0000000704000029000000a001400039000000400010043f000004f501000041000004f50320009c000000000201801900000040022002100000000003040433000004f50430009c00000000030180190000006003300210000000000223019f0000000003000414000004f50430009c0000000003018019000000c001300210000000000121019f00000500011001c7000080100200003913ce13bf0000040f0000000102200190000001240000613d000000000301043b000000400100043d00000042021000390000000504000029000000000042043500000020021000390000053f04000041000000000042043500000022041000390000000000340435000000420300003900000000003104350000051d0310009c000012f00000213d0000008003100039000000400030043f000004f503000041000004f50420009c000000000203801900000040022002100000000001010433000004f50410009c00000000010380190000006001100210000000000121019f0000000002000414000004f50420009c0000000002038019000000c002200210000000000112019f000012340000013d0000052d0720009c000012f00000213d0000004007200039000000400070043f000000010700003a00000000077204360000000008500350000000000808043b0000000000870435000009f80000613d000000f809600210000004fe0a000041000000000606004b000000000a09c0190000052e068001970000000006a6019f0000000000670435000000400600043d000500000006001d00000020076000390000000006010433000000000806004b000008ba0000613d000000000800001900000000097800190000002008800039000000000a180019000000000a0a04330000000000a90435000000000968004b000008b30000413d000000000176001900000000000104350000000007020433000000000807004b000008c70000613d000000000800001900000000091800190000002008800039000000000a280019000000000a0a04330000000000a90435000000000978004b000008c00000413d000000000117001900000000000104350000000001670019000000050600002900000000001604350000003f011000390001002000000092000000010110017f0000000002610019000000000112004b00000000010000190000000101004039000400000002001d000004fd0220009c000012f00000213d0000000101100190000012f00000c13d0000000401000029000000400010043f0000052d0110009c000012f00000213d00000009070000290000004401700039000000000113034f000000000101043b00000004080000290000004002800039000000400020043f000000200280003900000531060000410000000000620435000000150200003900000000002804350000006001100210000000210280003900000000001204350000012401700039000000000213034f000000400600043d000300000006001d000000000202043b000000800620008c00000b680000413d00000080062002700000052f0720009c000000000602a0190000052f0720009c0000000007000019000000100700203900000008087001bf000004fd0960009c000000000807a0190000004007600270000004fd0960009c000000000706a01900000004098001bf000004f50670009c000000000908a0190000002008700270000004f50670009c000000000807a01900000002069001bf0000ffff0780008c000000000609a0190000001007800270000000000708a019000000ff0770008c00000001066020390000004107600039000000010770017f0000000307700029000000030870006c00000000080000190000000108004039000004fd0970009c000012f00000213d0000000108800190000012f00000c13d000000400070043f00000002076000390000000308000029000000000778043600000021086000390000000508800272000009250000613d0000000009000019000000050a900210000000000ba70019000000000aa5034f000000000a0a043b0000000000ab04350000000109900039000000000a89004b0000091d0000413d000000000800004b000009270000613d00000003080000290000000008080433000000000808004b000009f80000613d00000000080704330000052e08800197000000f809600210000000000889019f000005300880004100000000008704350000000306600210000000f80660008900000000026201cf000000ff0660008c00000000020020190000000306000029000000210660003900000b7a0000013d000004f501000041000004f50350009c000000000501801900000060035002100000004004400210000000000343019f000004f50420009c0000000002018019000000c001200210000000000113019f000000080200002913ce13ba0000040f000400600000003d000000010220018f000300000001035500000000030100190000006003300270000104f50030019d000004f503300198000009790000613d0000003f04300039000000200500008a000000000454016f000000400500043d0000000004450019000400000005001d000000000554004b00000000050000190000000105004039000004fd0640009c000012f00000213d0000000105500190000012f00000c13d000000400040043f0000001f0430018f000000040500002900000000083504360000000503300272000009690000613d000000000500001900000005065002100000000007680019000000000661034f000000000606043b00000000006704350000000105500039000000000635004b000009610000413d000900000008001d000000000504004b000009790000613d0000000503300210000000000131034f00000009033000290000000304400210000000000503043300000000054501cf000000000545022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000013043500000004010000290000000001010433000000000202004b00000a170000c13d000000000201004b00000a360000c13d000000400300043d000900000003001d000005030100004100000000001304350000000401300039000000030200002900000000002104350000002402300039000000020100002913ce13a60000040f00000009040000290000000001410049000004f502000041000004f50310009c000000000102801900000a3a0000013d0000052d0850009c000012f00000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b0000000000980435000009f80000613d000000f80a700210000004fe0b000041000000000707004b000000000b0ac0190000052e079001970000000007b7019f0000000000780435000000400700043d000000400660008a000000000861034f000000000808043b000000800980008c00000a450000413d00000080098002700000052f0a80009c000000000908a0190000052f0a80009c000000000a000019000000100a002039000000080ba001bf000004fd0c90009c000000000b0aa019000000400a900270000004fd0c90009c000000000a09a019000000040cb001bf000004f509a0009c000000000c0ba019000000200ba00270000004f509a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa70019000000000b7a004b000000000b000019000000010b004039000004fd0ca0009c000012f00000213d000000010bb00190000012f00000c13d0000004000a0043f000000020a900039000000000aa70436000000210b900039000000050bb00272000009db0000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b000009d30000413d000000000b00004b000009dd0000613d000000000b070433000000000b0b004b000009f80000613d000000000b0a04330000052e0bb00197000000f80c900210000000000bbc019f000005300bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c0000000008002019000000210970003900000a560000013d0000052d0850009c000012f00000213d0000004008500039000000400080043f000000000921034f000000010800003a00000000088504360000000009900350000000000909043b000000000098043500000ab60000c13d0000054601000041000000000010043500000032010000390000003c0000013d0000001f0350018f000000050250027200000a070000613d00000000040000190000000506400210000000000761034f000000000707043b00000000007604350000000104400039000000000624004b00000a000000413d000000000403004b00000a150000613d00000003033002100000000502200210000000000402043300000000043401cf000000000434022f000000000121034f000000000101043b0000010003300089000000000131022f00000000013101cf000000000141019f00000000001204350000006001500210000013d000010430000000000201004b00000bc40000c13d0000051801000041000000000010043900000008010000290000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000519011001c7000080020200003913ce13bf0000040f00000001022001900000127a0000613d000000000101043b000000000101004b00000bc00000c13d000000400100043d00000044021000390000052103000041000000000032043500000024021000390000001d0300003900000000003204350000050302000041000000000021043500000004021000390000000303000029000002a20000013d000004f502000041000004f50310009c00000000010280190000000904000029000004f50340009c00000000040280190000004002400210000002440000013d000000400100043d00000044021000390000053803000041000000000032043500000024021000390000001f030000390000029d0000013d0000052d0970009c000012f00000213d0000004009700039000000400090043f000000000a21034f000000010900003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000009f80000613d000000f80b800210000004fe0c000041000000000808004b000000000c0bc0190000052e08a001970000000008c8019f0000000000890435000000400900043d0000052d0890009c000012f00000213d000000200860008a000000000881034f000000000808043b000000400a9000390000004000a0043f000000200a900039000005310b0000410000000000ba0435000000150a0000390000000000a904350000006008800210000000210a90003900000000008a0435000000c006600039000000000661034f000000400800043d000000000606043b000700000006001d000000800a60008c00000cd50000413d0000000706000029000000800a6002700000052f0b60009c000000000a06a0190000052f0b60009c000000000b000019000000100b002039000000080cb001bf000004fd0da0009c000000000c0ba019000000400ba00270000004fd0da0009c000000000b0aa019000000040dc001bf000004f50ab0009c000000000d0ca019000000200cb00270000004f50ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000004fd0db0009c000012f00000213d000000010cc00190000012f00000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc0027200000aa30000613d000000000d21034f000000000e000019000000050fe002100000000006fb0019000000000ffd034f000000000f0f043b0000000000f60435000000010ee000390000000006ce004b00000a9b0000413d000000000600004b00000aa50000613d0000000006080433000000000606004b000009f80000613d00000000060b04330000052e06600197000000f80ca0021000000000066c019f000005300660004100000000006b04350000000306a00210000000f806600089000000070a6001ef000000ff0660008c000000000a00201900000021068000390000000000a6043500000ce80000013d000000f80a600210000004fe0b000041000000000606004b000000000b0ac0190000052e069001970000000006b6019f0000000000680435000000400600043d000000200770008a000000000871034f000000000808043b000000800980008c00000b090000413d00000080098002700000052f0a80009c000000000908a0190000052f0a80009c000000000a000019000000100a002039000000080ba001bf000004fd0c90009c000000000b0aa019000000400a900270000004fd0c90009c000000000a09a019000000040cb001bf000004f509a0009c000000000c0ba019000000200ba00270000004f509a0009c000000000b0aa0190000000209c001bf0000ffff0ab0008c00000000090ca019000000100ab00270000000000a0ba019000000ff0aa0008c0000000109902039000000200a00008a000000410b900039000000000aab016f000000000aa60019000000000b6a004b000000000b000019000000010b004039000004fd0ca0009c000012f00000213d000000010bb00190000012f00000c13d0000004000a0043f000000020a900039000000000aa60436000000210b900039000000050bb0027200000af70000613d000000000c21034f000000000d000019000000050ed00210000000000fea0019000000000eec034f000000000e0e043b0000000000ef0435000000010dd00039000000000ebd004b00000aef0000413d000000000b00004b00000af90000613d000000000b060433000000000b0b004b000009f80000613d000000000b0a04330000052e0bb00197000000f80c900210000000000bbc019f000005300bb000410000000000ba04350000000309900210000000f80990008900000000089801cf000000ff0990008c0000000008002019000000210960003900000b1a0000013d0000052d0960009c000012f00000213d0000004009600039000000400090043f000000000a21034f000000010900003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000009f80000613d000000f80b800210000004fe0c000041000000000808004b000000000c0bc0190000052e08a001970000000008c8019f0000000000890435000000400800043d00070040007000920000000709100360000000000909043b000000800a90008c00000bfa0000413d000000800a9002700000052f0b90009c000000000a09a0190000052f0b90009c000000000b000019000000100b002039000000080cb001bf000004fd0da0009c000000000c0ba019000000400ba00270000004fd0da0009c000000000b0aa019000000040dc001bf000004f50ab0009c000000000d0ca019000000200cb00270000004f50ab0009c000000000c0ba019000000020ad001bf0000ffff0bc0008c000000000a0da019000000100bc00270000000000b0ca019000000ff0bb0008c000000010aa02039000000200b00008a000000410ca00039000000000bbc016f000000000bb80019000000000c8b004b000000000c000019000000010c004039000004fd0db0009c000012f00000213d000000010cc00190000012f00000c13d0000004000b0043f000000020ba00039000000000bb80436000000210ca00039000000050cc0027200000b550000613d000000000d21034f000000000e000019000000050fe002100000000007fb0019000000000ffd034f000000000f0f043b0000000000f70435000000010ee000390000000007ce004b00000b4d0000413d000000000700004b00000b570000613d0000000007080433000000000707004b000009f80000613d00000000070b04330000052e07700197000000f80ca0021000000000077c019f000005300770004100000000007b04350000000307a00210000000f80770008900000000097901cf000000ff0770008c00000000090020190000002107800039000000000097043500000c0c0000013d00000003060000290000052d0660009c000012f00000213d00000003070000290000004006700039000000400060043f000000010600003a00000000066704360000000007500350000000000707043b0000000000760435000009f80000613d000000f808200210000004fe09000041000000000202004b000000000908c0190000052e02700197000000000292019f0000000000260435000000080640006a000000a001100039000000000213034f000000000202043b0000001f0660008a000004fe07600197000004fe08200197000004fe09000041000000000a78004b000000000a000019000000000a094019000000000778013f000000000862004b0000000009004019000004fe0770009c000000000a09c01900000000070a004b000001240000c13d0000000808200029000000000783034f000000000707043b000004fd0970009c000001240000213d00000000097400490000002008800039000004fe0a000041000000000b98004b000000000b000019000000000b0a2019000004fe09900197000004fe0c800197000000000d9c004b000000000a00801900000000099c013f000004fe0990009c000000000a0bc01900000000090a004b000001240000c13d000000010970008c00000e8d0000c13d000000000583034f000000000505043b000000010700008a000004fe08000041000000000775004b00000000070000190000000007082019000004fe05500197000004fe0950009c0000000008008019000004fe05500167000004fe0550009c000000000807c019000200600000003d000000000508004b00000ec90000c13d000000400500043d000200000005001d0000052d0550009c000012f00000213d00000002080000290000004005800039000000400050043f0000002005800039000005300700004100000000007504350000000105000039000000000058043500000ec90000013d00000004010000290000000001010433000000000201004b00000be70000613d000004fe02000041000000200310008c00000000030000190000000003024019000004fe01100197000000000401004b000000000200a019000004fe0110009c000000000203c019000000000102004b000001240000c13d00000009010000290000000001010433000000000201004b0000000002000019000000010200c039000000000221004b000001240000c13d000000000101004b00000be70000c13d000000400100043d00000064021000390000051f03000041000000000032043500000044021000390000052003000041000000000032043500000024021000390000002a0300003900000000003204350000050302000041000000000021043500000004021000390000000303000029000001070000013d000000400300043d00000024013000390000000602000029000000000021043500000514010000410000000000130435000900000003001d00000004013000390000000502000029000000000021043500000000010004140000000802000029000000040220008c00000c6f0000c13d0000000103000031000000200130008c0000000004030019000000200400803900000ca10000013d0000052d0780009c000012f00000213d0000004007800039000000400070043f000000000721034f000000010a00003a000000000aa804360000000007700350000000000b07043b0000000000ba0435000009f80000613d000000f807900210000004fe0c000041000000000909004b000000000c07c0190000052e07b001970000000007c7019f00000000007a0435000000400a00043d0000052d07a0009c000012f00000213d000000070c0000290000002007c0008a000000000771034f000000000707043b0000004009a00039000000400090043f0000002009a00039000005310b0000410000000000b90435000000150900003900000000009a043500000060077002100000002109a000390000000000790435000000c007c00039000000000771034f000000400900043d000000000707043b000700000007001d000000800b70008c00000db20000413d0000000707000029000000800b7002700000052f0c70009c000000000b07a0190000052f0c70009c000000000c000019000000100c002039000000080dc001bf000004fd0eb0009c000000000d0ca019000000400cb00270000004fd0eb0009c000000000c0ba019000000040ed001bf000004f50bc0009c000000000e0da019000000200dc00270000004f50bc0009c000000000d0ca0190000000207e001bf0000ffff0cd0008c00000000070ea019000000100cd00270000000000c0da019000000ff0cc0008c0000000107702039000000200c00008a000500000007001d000000410d700039000000000ccd016f000000000cc90019000000000d9c004b000000000d000019000000010d004039000004fd0ec0009c000012f00000213d000000010dd00190000012f00000c13d0000004000c0043f0000000507000029000000020c700039000000000cc90436000000210d700039000000050dd0027200000c5b0000613d000000000e21034f000000000f0000190000000507f00210000000000b7c001900000000077e034f000000000707043b00000000007b0435000000010ff000390000000007df004b00000c530000413d000000000700004b00000c5d0000613d0000000007090433000000000707004b000009f80000613d00000000070c04330000052e07700197000000050d000029000000f80bd0021000000000077b019f000005300770004100000000007c04350000000307d00210000000f807700089000000070b7001ef000000ff0770008c000000000b00201900000021079000390000000000b7043500000dc50000013d000004f502000041000004f50310009c00000000010280190000000904000029000004f50340009c00000000020440190000004002200210000000c001100210000000000121019f0000051a011001c7000000080200002913ce13bf0000040f000000090a00002900000000030100190000006003300270000004f503300197000000200430008c000000000403001900000020040080390000001f0540018f000000050640027200000c8e0000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b00000c860000413d000000000705004b00000c9d0000613d0000000506600210000000000761034f00000009066000290000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f0003000000010355000000010220019000000d950000613d0000001f01400039000000600210018f0000000901200029000000000221004b00000000020000190000000102004039000004fd0410009c000012f00000213d0000000102200190000012f00000c13d000000400010043f000000200230008c000001240000413d0000004404100039000000240510003900000009020000290000000002020433000000000202004b00000e810000c13d0000002002100039000005160600004100000000006204350000000606000029000000000065043500000007050000290000000000540435000000010400002900000000004104350000051d0410009c000012f00000213d0000008004100039000900000004001d000000400040043f0000051e0410009c000012f00000213d000000c004100039000000400040043f000000030400002900000009050000290000000000450435000000a00410003900000517050000410000000000540435000000000401043300000000010004140000000805000029000000040550008c00000f810000c13d0000000102000039000004fd0130009c000012f00000213d00000f970000013d0000052d0680009c000012f00000213d0000004006800039000000400060043f000000000621034f000000010a00003a000000000aa804360000000006600350000000000b06043b0000000000ba0435000009f80000613d000000070d000029000000f806d00210000004fe0c000041000000000d0d004b000000000c06c0190000052e06b001970000000006c6019f00000000006a0435000000400600043d000000200b600039000000000a030433000000000c0a004b00000cf50000613d000000000c000019000000000dbc0019000000200cc00039000000000e3c0019000000000e0e04330000000000ed0435000000000dac004b00000cee0000413d0000000003ba0019000000000003043500000000036a0019000000200b300039000000000a040433000000000c0a004b00000d040000613d000000000c000019000000000dbc0019000000200cc00039000000000e4c0019000000000e0e04330000000000ed0435000000000dac004b00000cfd0000413d0000000004ba0019000000000004043500000000033a0019000000200a3000390000000004050433000000000b04004b00000d130000613d000000000b000019000000000cab0019000000200bb00039000000000d5b0019000000000d0d04330000000000dc0435000000000c4b004b00000d0c0000413d0000000005a400190000000000050435000000000334001900000020053000390000000004070433000000000a04004b00000d220000613d000000000a000019000000000b5a0019000000200aa00039000000000c7a0019000000000c0c04330000000000cb0435000000000b4a004b00000d1b0000413d00000000055400190000000000050435000000000334001900000020053000390000000004090433000000000704004b00000d310000613d0000000007000019000000000a5700190000002007700039000000000b970019000000000b0b04330000000000ba0435000000000a47004b00000d2a0000413d00000000055400190000000000050435000000000334001900000020053000390000000004080433000000000704004b00000d400000613d000000000700001900000000095700190000002007700039000000000a870019000000000a0a04330000000000a90435000000000947004b00000d390000413d000000000554001900000000000504350000000003630049000000000334001900000000003604350000003f04300039000000200300008a000000000434016f0000000007640019000000000447004b00000000040000190000000104004039000004fd0570009c000012f00000213d0000000104400190000012f00000c13d000000400070043f0000000905000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b000004fe08000041000000000954004b00000000090000190000000009088019000004fe05500197000004fe0a400197000000000b5a004b000000000800801900000000055a013f000004fe0550009c000000000809c019000000000508004b000001240000c13d0000000805400029000000000451034f000000000404043b000004fd0840009c000001240000213d00000000084200490000002005500039000004fe09000041000000000a85004b000000000a000019000000000a092019000004fe08800197000004fe0b500197000000000c8b004b000000000900801900000000088b013f000004fe0880009c00000000090ac019000000000809004b000001240000c13d000000010840008c00000fd60000c13d000000000851034f000000000808043b000000010900008a000004fe0a000041000000000998004b000000000900001900000000090a2019000004fe08800197000004fe0b80009c000000000a008019000004fe08800167000004fe0880009c000000000a09c019000000600800003900000000090a004b000010740000c13d0000052d0870009c000012f00000213d0000004008700039000000400080043f000000200870003900000530090000410000000000980435000000010800003900000000008704350000000008070019000010740000013d000000400200043d0000001f0430018f000000050530027200000da20000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b00000d9a0000413d000000000604004b00000db10000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000006bd0000013d0000052d0790009c000012f00000213d0000004007900039000000400070043f000000000721034f000000010b00003a000000000bb904360000000007700350000000000c07043b0000000000cb0435000009f80000613d000000070e000029000000f807e00210000004fe0d000041000000000e0e004b000000000d07c0190000052e07c001970000000007d7019f00000000007b0435000000400700043d000000200c700039000000000b030433000000000d0b004b00000dd20000613d000000000d000019000000000ecd0019000000200dd00039000000000f3d0019000000000f0f04330000000000fe0435000000000ebd004b00000dcb0000413d0000000003cb0019000000000003043500000000037b0019000000200c300039000000000b040433000000000d0b004b00000de10000613d000000000d000019000000000ecd0019000000200dd00039000000000f4d0019000000000f0f04330000000000fe0435000000000ebd004b00000dda0000413d0000000004cb0019000000000004043500000000033b0019000000200b3000390000000004050433000000000c04004b00000df00000613d000000000c000019000000000dbc0019000000200cc00039000000000e5c0019000000000e0e04330000000000ed0435000000000d4c004b00000de90000413d0000000005b400190000000000050435000000000334001900000020053000390000000004060433000000000b04004b00000dff0000613d000000000b000019000000000c5b0019000000200bb00039000000000d6b0019000000000d0d04330000000000dc0435000000000c4b004b00000df80000413d00000000055400190000000000050435000000000334001900000020053000390000000004080433000000000604004b00000e0e0000613d0000000006000019000000000b5600190000002006600039000000000c860019000000000c0c04330000000000cb0435000000000b46004b00000e070000413d000000000554001900000000000504350000000003340019000000200530003900000000040a0433000000000604004b00000e1d0000613d000000000600001900000000085600190000002006600039000000000ba60019000000000b0b04330000000000b80435000000000846004b00000e160000413d00000000055400190000000000050435000000000334001900000020053000390000000004090433000000000604004b00000e2c0000613d000000000600001900000000085600190000002006600039000000000a960019000000000a0a04330000000000a80435000000000846004b00000e250000413d000000000554001900000000000504350000000003730049000000000334001900000000003704350000003f04300039000000200300008a000000000434016f0000000006740019000000000446004b00000000040000190000000104004039000004fd0560009c000012f00000213d0000000104400190000012f00000c13d000000400060043f0000000905000029000001c404500039000000000441034f0000000005520049000000230550008a000000000404043b000004fe08000041000000000954004b00000000090000190000000009088019000004fe05500197000004fe0a400197000000000b5a004b000000000800801900000000055a013f000004fe0550009c000000000809c019000000000508004b000001240000c13d0000000805400029000000000451034f000000000404043b000004fd0840009c000001240000213d00000000084200490000002005500039000004fe09000041000000000a85004b000000000a000019000000000a092019000004fe08800197000004fe0b500197000000000c8b004b000000000900801900000000088b013f000004fe0880009c00000000090ac019000000000809004b000001240000c13d000000010840008c000011840000c13d000000000851034f000000000808043b000000010900008a000004fe0a000041000000000998004b000000000900001900000000090a2019000004fe08800197000004fe0b80009c000000000a008019000004fe08800167000004fe0880009c000000000a09c019000000600800003900000000090a004b000012ed0000c13d0000052d0860009c000012f00000213d0000004008600039000000400080043f000000200860003900000530090000410000000000980435000000010800003900000000008604350000000008060019000012ed0000013d00000503020000410000000000210435000000040210003900000003030000290000000000320435000000360200003900000000002504350000051b02000041000000000024043500000064021000390000051c03000041000001070000013d000000400800043d000200000008001d000000380870008c00000eb80000413d0000002009700270000004f50870009c000000000907a019000004f50870009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c00000000090000190000000109002039000000020a0000290000052d0aa0009c000012f00000213d000000000898019f000000020a0000290000004009a00039000000400090043f000000020980003a00000000099a04360000000005500350000000000505043b0000000000590435000009f80000613d0000052e05500197000000f80a80021000000000055a019f00000532055001c700000000005904350000000305800210000000f80550015f00000000055701cf00000002070000290000002107700039000000000057043500000ec90000013d00000002080000290000052d0880009c000012f00000213d00000002090000290000004008900039000000400080043f000000010800003a00000000088904360000000005500350000000000505043b0000000000580435000009f80000613d000000f8077002100000052e05500197000000000575019f000004fe055001670000000000580435000000800110008a000000000513034f0000006001000039000000000505043b000000000505004b00000f2a0000c13d000004fe05000041000000000762004b00000000070000190000000007058019000004fe06600197000004fe08200197000000000968004b0000000005008019000000000668013f000004fe0660009c000000000507c019000000000505004b000001240000c13d000000070500002900000000060504330000000505000029000000000705043300000004050000290000000008050433000000030500002900000000090504330000000205000029000000000a0504330000000805200029000000000253034f000000000202043b000004fd0b20009c000001240000213d000000000b2400490000002005500039000004fe0c000041000000000db5004b000000000d000019000000000d0c2019000004fe0bb00197000004fe0e500197000000000fbe004b000000000c008019000000000bbe013f000004fe0bb0009c000000000c0dc019000000000b0c004b000001240000c13d0000000006670019000000000686001900000000069600190000000006a60019000000000626001900000000070104330000000006760019000000400700043d000004fd06600197000000380860008c000010b40000413d0000002009600270000004f50860009c000000000906a019000004f50860009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c000000000900001900000001090020390000052d0a70009c000012f00000213d000000000898019f0000004009700039000000400090043f000000000943034f000000020480003a00000000044704360000000009900350000000000909043b0000000000940435000009f80000613d0000052e09900197000000f80a80021000000000099a019f00000534099001c700000000009404350000000304800210000000f80440015f00000000044601cf00000021067000390000000000460435000010c40000013d0000052b010000410000000000100439000004f5010000410000000002000414000004f50320009c0000000002018019000000c0012002100000052c011001c70000800b0200003913ce13bf0000040f00000001022001900000127a0000613d000000400200043d000000000101043b000000800310008c00000ffe0000413d00000080031002700000052f0410009c000000000301a0190000052f0410009c0000000004000019000000100400203900000008054001bf000004fd0630009c000000000504a0190000004004300270000004fd0630009c000000000403a01900000004035001bf000004f50640009c000000000305a0190000002006400270000004f50540009c000000000604a01900000002053001bf0000ffff0460008c000000000503a0190000001003600270000000000306a019000000ff0330008c00000001055020390000004103500039000000010330017f0000000003320019000000000423004b00000000040000190000000104004039000004fd0630009c000012f00000213d0000000104400190000012f00000c13d000000400030043f00000002035000390000000006320436000000020300036700000000040000310000002107500039000000050770027200000f6f0000613d000000000843034f0000000009000019000000050a900210000000000ba60019000000000aa8034f000000000a0a043b0000000000ab04350000000109900039000000000a79004b00000f670000413d000000000700004b00000f710000613d0000000007020433000000000707004b000009f80000613d00000000070604330000052e07700197000000f808500210000000000778019f000005300770004100000000007604350000000305500210000000f80550008900000000015101cf000000ff0550008c00000000010020190000002105200039000010110000013d000004f503000041000004f50520009c00000000020380190000004002200210000004f50540009c00000000040380190000006004400210000000000224019f000004f50410009c0000000001038019000000c001100210000000000112019f000000080200002913ce13ba0000040f000700600000003d000600800000003d000000010220018f00030000000103550000006001100270000104f50010019d000004f50310019800000fc40000613d0000003f01300039000000200400008a000000000141016f000000400400043d0000000001140019000700000004001d000000000441004b00000000040000190000000104004039000004fd0510009c000012f00000213d0000000104400190000012f00000c13d000000400010043f0000001f0130018f000000070400002900000000083404360000000304000367000000050330027200000fb40000613d000000000500001900000005065002100000000007680019000000000664034f000000000606043b00000000006704350000000105500039000000000635004b00000fac0000413d000600000008001d000000000501004b00000fc40000613d0000000503300210000000000434034f00000006033000290000000301100210000000000503043300000000051501cf000000000515022f000000000404043b0000010001100089000000000414022f00000000011401cf000000000151019f000000000013043500000007010000290000000001010433000000000202004b000010360000c13d000000000201004b000010af0000c13d000000400300043d000800000003001d000005030100004100000000001304350000000401300039000000030200002900000000002104350000002402300039000000090100002913ce13a60000040f00000008040000290000098a0000013d000000380840008c000010630000413d0000002009400270000004f50840009c000000000904a019000004f50840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c000000000900001900000001090020390000052d0a70009c000012f00000213d000000000898019f0000004009700039000000400090043f000000000a21034f000000020980003a0000000009970436000000000aa00350000000000a0a043b0000000000a90435000009f80000613d0000052e0aa00197000000f80b800210000000000aab019f000005320aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf000000210970003900000000008904350000000008070019000010740000013d0000052d0320009c000012f00000213d0000004003200039000000400030043f000000010300003a000000000532043600000000040000310000000203000367000000000643034f0000000006600350000000000606043b0000000000650435000009f80000613d000000f807100210000004fe08000041000000000101004b000000000807c0190000052e01600197000000000181019f0000000000150435000000400100043d00000020061000390000000005020433000000000705004b0000101f0000613d000000000700001900000000086700190000002007700039000000000927001900000000090904330000000000980435000000000857004b000010180000413d000000000265001900000540060000410000000000620435000000020250003900000000002104350000004102500039000000010520017f0000000002150019000000000552004b00000000050000190000000105004039000004fd0620009c000012f00000213d0000000105500190000012f00000c13d0000000906000029000001c405600039000000400020043f000000000253034f0000000005640049000000230650008a000000000202043b00000ecf0000013d000000000201004b0000104d0000c13d0000051801000041000000000010043900000008010000290000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000519011001c7000080020200003913ce13bf0000040f00000001022001900000127a0000613d000000000101043b000000000101004b00000a2a0000613d00000007010000290000000001010433000000000201004b000010610000613d000004fe02000041000000200310008c00000000030000190000000003024019000004fe01100197000000000401004b000000000200a019000004fe0110009c000000000203c019000000000102004b000001240000c13d00000006010000290000000001010433000000000201004b0000000002000019000000010200c039000000000221004b000001240000c13d000000000101004b00000bd80000613d0000000001000019000013cf0001042e0000052d0870009c000012f00000213d0000004008700039000000400080043f000000000921034f000000010800003a00000000088704360000000009900350000000000909043b0000000000980435000009f80000613d000000f80a4002100000052e099001970000000009a9019f000004fe0990016700000000009804350000000008070019000000400700043d0000052d0970009c000012f00000213d0000004009700039000000400090043f000000000221034f000000010c00003a0000000009c704360000000002200350000000000b02043b0000000000b90435000009f80000613d0000052e02b00197000005330a2001c70000000000a9043500000000090604330000000009490019000000000a0804330000000009a90019000000000a0704330000000009a90019000000400a00043d000004fd09900197000000380d90008c000011ac0000413d000000200d900270000004f50c90009c000000000d09a019000004f50c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d0020390000052d0ea0009c000012f00000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000009f80000613d000000f80bc0021000000000022b019f00000534022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a000390000000000290435000011b90000013d000004f502000041000004f50310009c0000000001028019000000060400002900000a3a0000013d0000052d0870009c000012f00000213d0000004008700039000000400080043f000000000843034f000000010400003a00000000044704360000000008800350000000000808043b0000000000840435000009f80000613d0000052e08800197000000f806600210000000000686019f00000533066000410000000000640435000000400400043d00000020064000390000000008070433000000000908004b000010d10000613d0000000009000019000000000a6900190000002009900039000000000b790019000000000b0b04330000000000ba0435000000000a89004b000010ca0000413d000000000768001900000000000704350000000007480019000000200970003900000007080000290000000008080433000000000a08004b000010e10000613d000000000a000019000000000b9a0019000000200aa00039000000070ca00029000000000c0c04330000000000cb0435000000000b8a004b000010da0000413d000000000998001900000000000904350000000007780019000000200970003900000005080000290000000008080433000000000a08004b000010f10000613d000000000a000019000000000b9a0019000000200aa00039000000050ca00029000000000c0c04330000000000cb0435000000000b8a004b000010ea0000413d000000000998001900000000000904350000000007780019000000200970003900000004080000290000000008080433000000000a08004b000011010000613d000000000a000019000000000b9a0019000000200aa00039000000040ca00029000000000c0c04330000000000cb0435000000000b8a004b000010fa0000413d000000000998001900000000000904350000000007780019000000200970003900000003080000290000000008080433000000000a08004b000011110000613d000000000a000019000000000b9a0019000000200aa00039000000030ca00029000000000c0c04330000000000cb0435000000000b8a004b0000110a0000413d000000000998001900000000000904350000000007780019000000200970003900000002080000290000000008080433000000000a08004b000011210000613d000000000a000019000000000b9a0019000000200aa00039000000020ca00029000000000c0c04330000000000cb0435000000000b8a004b0000111a0000413d00000000099800190000000000090435000000000553034f00000000037800190000001f0720018f00000020083000390000000509200272000011320000613d000000000a000019000000050ba00210000000000cb80019000000000bb5034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b0000112a0000413d000000000a07004b000011410000613d0000000509900210000000000595034f00000000089800190000000307700210000000000908043300000000097901cf000000000979022f000000000505043b0000010007700089000000000575022f00000000057501cf000000000595019f00000000005804350000000002230019000000200520003900000000000504350000000003010433000000000703004b0000114f0000613d000000000700001900000000085700190000002007700039000000000917001900000000090904330000000000980435000000000837004b000011480000413d000000000153001900000000000104350000000001420049000000000113001900000000001404350000003f01100039000000010210017f0000000001420019000000000221004b00000000020000190000000102004039000004fd0310009c000012f00000213d0000000102200190000012f00000c13d000000400010043f000004f501000041000004f50260009c000000000601801900000040026002100000000003040433000004f50430009c00000000030180190000006003300210000000000223019f0000122f0000013d0000001f0430018f0000000502300272000011740000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b0000116d0000413d000000000504004b000011820000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000013d000010430000000380840008c000012dc0000413d0000002009400270000004f50840009c000000000904a019000004f50840009c000000000a000019000000040a0020390000000208a001bf0000ffff0b90008c00000000080aa019000000100a900270000000000a09a019000000ff09a0008c000000000900001900000001090020390000052d0a60009c000012f00000213d000000000898019f0000004009600039000000400090043f000000000a21034f000000020980003a0000000009960436000000000aa00350000000000a0a043b0000000000a90435000009f80000613d0000052e0aa00197000000f80b800210000000000aab019f000005320aa001c70000000000a904350000000308800210000000f80880015f00000000088401cf000000210960003900000000008904350000000008060019000012ed0000013d0000052d0da0009c000012f00000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000009f80000613d000000f809900210000000000229019f000005330220004100000000002d0435000000400200043d0000002009200039000005350b0000410000000000b90435000000210c200039000000000b0a0433000000000d0b004b000011c90000613d000000000d000019000000000ecd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ebd004b000011c20000413d000000000acb001900000000000a0435000000000a2b0019000000210ca00039000000000b060433000000000d0b004b000011d80000613d000000000d000019000000000ecd0019000000200dd00039000000000f6d0019000000000f0f04330000000000fe0435000000000ebd004b000011d10000413d0000000006cb001900000000000604350000000006ab0019000000210b600039000000000a080433000000000c0a004b000011e70000613d000000000c000019000000000dbc0019000000200cc00039000000000e8c0019000000000e0e04330000000000ed0435000000000dac004b000011e00000413d0000000008ba00190000000000080435000000000551034f00000000016a00190000001f0640018f0000002108100039000000050a400272000011f80000613d000000000b000019000000050cb00210000000000dc80019000000000cc5034f000000000c0c043b0000000000cd0435000000010bb00039000000000cab004b000011f00000413d000000000b06004b000012070000613d000000050aa002100000000005a5034f0000000008a800190000000306600210000000000a080433000000000a6a01cf000000000a6a022f000000000505043b0000010006600089000000000565022f00000000056501cf0000000005a5019f00000000005804350000000001410019000000210510003900000000000504350000000004070433000000000604004b000012150000613d000000000600001900000000085600190000002006600039000000000a760019000000000a0a04330000000000a80435000000000846004b0000120e0000413d0000000005540019000000000005043500000000012100490000000001140019000000010410003900000000004204350000004001100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000004fd0410009c000012f00000213d0000000103300190000012f00000c13d000000400010043f000004f501000041000004f50390009c000000000901801900000040039002100000000002020433000004f50420009c00000000020180190000006002200210000000000232019f0000000003000414000004f50430009c0000000003018019000000c001300210000000000121019f00000500011001c7000080100200003913ce13bf0000040f0000000101200190000001240000613d0000000901000029000000e4041000390000000201000367000000000241034f000000000202043b000004ff02200198000500000004001d0000125a0000c13d000000800240008a000000000321034f000000400240008a000000000521034f000000000403043b000000000505043b00000000634500a9000000000605004b0000124d0000613d00000000655300d9000000000445004b000012560000c13d0000008002200039000000000121034f000000000101043b000700000031001d000000070110006b0000000001000019000000010100403900000001011001900000125f0000613d0000054601000041000000000010043500000011010000390000003c0000013d00000009020000290000012402200039000000000121034f000000000101043b000700000001001d0000054101000041000000000010043900000006010000290000000400100443000004f5010000410000000002000414000004f50320009c0000000002018019000000c00120021000000519011001c70000800a0200003913ce13bf0000040f00000001022001900000127a0000613d000000000101043b000000070110006b0000127b0000a13d000000400100043d00000064021000390000054403000041000000000032043500000044021000390000054503000041000000000032043500000024021000390000002203000039000001020000013d000000000001042f0000000003000031000000090130006a000000230410008a000000050100002900000100011000390000000202000367000000000112034f000000000101043b000004fe05000041000000000641004b00000000060000190000000006058019000004fe04400197000004fe07100197000000000847004b0000000005008019000000000447013f000004fe0440009c000000000506c019000000000405004b000001240000c13d0000000804100029000000000142034f000000000101043b000004fd0510009c000001240000213d00000000061300490000002005400039000004fe04000041000000000765004b00000000070000190000000007042019000004fe06600197000004fe08500197000000000968004b0000000004008019000000000668013f000004fe0660009c000000000407c019000000000404004b000001240000c13d0000003f04100039000000200600008a000000000664016f000000400400043d0000000006640019000000000746004b00000000070000190000000107004039000004fd0860009c000012f00000213d0000000107700190000012f00000c13d000000400060043f00000000041404360000000006510019000000000336004b000001240000213d000000000352034f0000001f0210018f0000000505100272000012c20000613d000000000600001900000005076002100000000008740019000000000773034f000000000707043b00000000007804350000000106600039000000000756004b000012ba0000413d000000000602004b000012d10000613d0000000505500210000000000353034f00000000055400190000000302200210000000000605043300000000062601cf000000000626022f000000000303043b0000010002200089000000000323022f00000000022301cf000000000262019f0000000000250435000000000114001900000000000104350000054201000041000000400200043d0000000000120435000004f501000041000004f50320009c0000000002018019000000400120021000000543011001c7000013cf0001042e0000052d0860009c000012f00000213d0000004008600039000000400080043f000000000921034f000000010800003a00000000088604360000000009900350000000000909043b0000000000980435000009f80000613d000000f80a4002100000052e099001970000000009a9019f000004fe0990016700000000009804350000000008060019000000400600043d0000052d0960009c000012f40000a13d0000054601000041000000000010043500000041010000390000003c0000013d0000004009600039000000400090043f000000000221034f000000010c00003a0000000009c604360000000002200350000000000b02043b0000000000b90435000009f80000613d0000052e02b00197000005330a2001c70000000000a9043500000000090704330000000009490019000000000a0804330000000009a90019000000000a0604330000000009a90019000000400a00043d000004fd09900197000000380d90008c0000132c0000413d000000200d900270000004f50c90009c000000000d09a019000004f50c90009c000000000e000019000000040e002039000000020ce001bf0000ffff0fd0008c000000000c0ea019000000100ed00270000000000e0da019000000ff0de0008c000000000d000019000000010d0020390000052d0ea0009c000012f00000213d000000000cdc019f000000400da000390000004000d0043f000000200da000390000000000bd0435000000020bc0003a0000000000ba0435000009f80000613d000000f80bc0021000000000022b019f00000534022001c700000000002d04350000000302c00210000000f80220015f00000000022901cf0000002109a000390000000000290435000013390000013d0000052d0da0009c000012f00000213d000000400da000390000004000d0043f000000200da000390000000000bd04350000000000ca0435000000000b0c004b000009f80000613d000000f809900210000000000229019f000005330220004100000000002d0435000000400200043d0000002009200039000005000b0000410000000000b90435000000210c200039000000000b0a0433000000000d0b004b000013490000613d000000000d000019000000000ecd0019000000200dd00039000000000fad0019000000000f0f04330000000000fe0435000000000ebd004b000013420000413d000000000acb001900000000000a0435000000000a2b0019000000210ca00039000000000b070433000000000d0b004b000013580000613d000000000d000019000000000ecd0019000000200dd00039000000000f7d0019000000000f0f04330000000000fe0435000000000ebd004b000013510000413d0000000007cb001900000000000704350000000007ab0019000000210b700039000000000a080433000000000c0a004b000013670000613d000000000c000019000000000dbc0019000000200cc00039000000000e8c0019000000000e0e04330000000000ed0435000000000dac004b000013600000413d0000000008ba00190000000000080435000000000551034f00000000017a00190000001f0740018f0000002108100039000000050a400272000013780000613d000000000b000019000000050cb00210000000000dc80019000000000cc5034f000000000c0c043b0000000000cd0435000000010bb00039000000000cab004b000013700000413d000000000b07004b000013870000613d000000050aa002100000000005a5034f0000000008a800190000000307700210000000000a080433000000000a7a01cf000000000a7a022f000000000505043b0000010007700089000000000575022f00000000057501cf0000000005a5019f00000000005804350000000001410019000000210510003900000000000504350000000004060433000000000704004b000013950000613d000000000700001900000000085700190000002007700039000000000a670019000000000a0a04330000000000a80435000000000847004b0000138e0000413d0000000005540019000000000005043500000000012100490000000001140019000000010410003900000000004204350000004001100039000000000331016f0000000001230019000000000331004b00000000030000190000000103004039000004fd0410009c000012f00000213d0000000103300190000012f00000c13d000012250000013d00000000030104330000000002320436000000000403004b000013b20000613d000000000400001900000000052400190000002004400039000000000614001900000000060604330000000000650435000000000534004b000013ab0000413d000000000123001900000000000104350000001f01300039000000200300008a000000000131016f0000000001120019000000000001042d000000000001042f000013bd002104210000000102000039000000000001042d0000000002000019000000000001042d000013c2002104230000000102000039000000000001042d0000000002000019000000000001042d000013c7002104210000000102000039000000000001042d0000000002000019000000000001042d000013cc002104230000000102000039000000000001042d0000000002000019000000000001042d000013ce00000432000013cf0001042e000013d00001043000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000df9c158800000000000000000000000000000000000000000000000000000000df9c158900000000000000000000000000000000000000000000000000000000e2f318e300000000000000000000000000000000000000000000000000000000eeb8cb0900000000000000000000000000000000000000000000000000000000202bcce700000000000000000000000000000000000000000000000000000000a28c1aee000000000000000000000000000000000000000000000000ffffffffffffffff8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff02000000000000000000000000000000000000000000000000000000000000007261746f720000000000000000000000000000000000000000000000000000004661696c656420746f20706179207468652066656520746f20746865206f706508c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000840000000000000000000000000000000000000000000000000000000100000000000000000000000000000000ffffffff000000000000000000000000000000000000000000000000000000009c4d535affffffffffffffffffffffffffffffffffffffffffffffffffffffff9c4d535b00000000000000000000000000000000000000000000000000000000ecf95b8a000000000000000000000000000000000000000000000000000000003cda3351000000000000000000000000000000000000000000000000000000005d3827000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000000000000000000000000000000000000000000000100000100000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001ffffffe04f766572666c6f7700000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000008000000000000000008c5a344500000000000000000000000000000000000000000000000000000000949431dc00000000000000000000000000000000000000000000000000000000dd62ed3e000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000044000000800000000000000000095ea7b3000000000000000000000000000000000000000000000000000000005361666545524332303a206c6f772d6c6576656c2063616c6c206661696c65641806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b83020000020000000000000000000000000000002400000000000000000000000000000000000000000000000000000000000000440000000000000000000000005361666545524332303a20617070726f76652066726f6d206e6f6e2d7a65726f20746f206e6f6e2d7a65726f20616c6c6f77616e636500000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff7f000000000000000000000000000000000000000000000000ffffffffffffff3f6f742073756363656564000000000000000000000000000000000000000000005361666545524332303a204552433230206f7065726174696f6e20646964206e416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000000000000000000000000000000000000000006400000000000000000000000054686520617070726f76616c4261736564207061796d617374657220696e707574206d757374206265206174206c65617374203638206279746573206c6f6e670000000000000000000000000000000000000084000000800000000000000000556e737570706f72746564207061796d617374657220666c6f77000000000000546865207374616e64617264207061796d617374657220696e707574206d757374206265206174206c656173742034206279746573206c6f6e67000000000000e1239cd8000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000024000000a000000000000000009a8a0592ac89c5ad3bc6df8224c17b485976f597df104ee20d0df415241f670b0200000200000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffbf00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00000000000000000000000000000000ffffffffffffffffffffffffffffffff81000000000000000000000000000000000000000000000000000000000000009400000000000000000000000000000000000000000000000000000000000000b800000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000000f8000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000007ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff6b656363616b3235362072657475726e656420696e76616c6964206461746100848e1bfa1ac4e3576b728bda6721b215c70a7799a5b4866282a71bab954baac8000000000000000000000000000000000000000000000000fffffffffffffe1fc2f8787176b8ac6bf7215b4adcc1e069bf4ab82d9ab1df05a57a91d425935b6ead7c5bef027816a800da1736444fb58a807ef4c9603b7848673f7e3a68eb14a519b453ce45aaaaf3a300f5a9ec95869b4f28ab10430b572ee218c3a6a5e07d6f000000000000000000000000000000000000000000000000ffffffffffffff5f190100000000000000000000000000000000000000000000000000000000000080800000000000000000000000000000000000000000000000000000000000009cc7f708afc65944829bd487b90b72536b1951864fbfc14e125fc972a6507f39202bcce700000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002000000000000000000000000075650000000000000000000000000000000000000000000000000000000000004e6f7420656e6f7567682062616c616e636520666f7220666565202b2076616c4e487b71000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000456e636f64696e6720756e737570706f72746564207478000000000000000000000000000000000000000000000000000000000000000000000000000000000003a0b6db1c535c3eb557511f12bd7cdd9e744966ba523d3461ac1c1d3bedc017", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/EcAdd.yul.zbin b/.test-node-subtree/src/deps/contracts/EcAdd.yul.zbin new file mode 100644 index 00000000..d7942db1 Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/EcAdd.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/EcMul.yul.zbin b/.test-node-subtree/src/deps/contracts/EcMul.yul.zbin new file mode 100644 index 00000000..6fd9e212 Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/EcMul.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/EcPairing.yul.zbin b/.test-node-subtree/src/deps/contracts/EcPairing.yul.zbin new file mode 100644 index 00000000..a98f18cd Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/EcPairing.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/Ecrecover.yul.zbin b/.test-node-subtree/src/deps/contracts/Ecrecover.yul.zbin new file mode 100644 index 00000000..6ea47838 Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/Ecrecover.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/EmptyContract.json b/.test-node-subtree/src/deps/contracts/EmptyContract.json new file mode 100644 index 00000000..783e7ee7 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/EmptyContract.json @@ -0,0 +1,20 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "EmptyContract", + "sourceName": "cache-zk/solpp-generated-contracts/EmptyContract.sol", + "abi": [ + { + "stateMutability": "payable", + "type": "fallback" + }, + { + "stateMutability": "payable", + "type": "receive" + } + ], + "bytecode": "0x0000000101200190000000040000c13d0000000001000019000000110001042e0000008001000039000000400010043f0000000001000416000000000101004b0000000e0000c13d0000002001000039000001000010044300000120000004430000000501000041000000110001042e000000000100001900000012000104300000001000000432000000110001042e0000001200010430000000000000000000000002000000000000000000000000000000400000010000000000000000009e235065aa0577b3e903db8a24442815e1c341b39711aa9b663fbb415c47716a", + "deployedBytecode": "0x0000000101200190000000040000c13d0000000001000019000000110001042e0000008001000039000000400010043f0000000001000416000000000101004b0000000e0000c13d0000002001000039000001000010044300000120000004430000000501000041000000110001042e000000000100001900000012000104300000001000000432000000110001042e0000001200010430000000000000000000000002000000000000000000000000000000400000010000000000000000009e235065aa0577b3e903db8a24442815e1c341b39711aa9b663fbb415c47716a", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/EventWriter.yul.zbin b/.test-node-subtree/src/deps/contracts/EventWriter.yul.zbin new file mode 100644 index 00000000..cd15a102 Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/EventWriter.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/ImmutableSimulator.json b/.test-node-subtree/src/deps/contracts/ImmutableSimulator.json new file mode 100644 index 00000000..ed847fa9 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/ImmutableSimulator.json @@ -0,0 +1,66 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "ImmutableSimulator", + "sourceName": "cache-zk/solpp-generated-contracts/ImmutableSimulator.sol", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_dest", + "type": "address" + }, + { + "internalType": "uint256", + "name": "_index", + "type": "uint256" + } + ], + "name": "getImmutable", + "outputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_dest", + "type": "address" + }, + { + "components": [ + { + "internalType": "uint256", + "name": "index", + "type": "uint256" + }, + { + "internalType": "bytes32", + "name": "value", + "type": "bytes32" + } + ], + "internalType": "struct ImmutableData[]", + "name": "_immutables", + "type": "tuple[]" + } + ], + "name": "setImmutables", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "bytecode": "0x00010000000000020007000000000002000000000701034f00000000000703550000008001000039000000400010043f000000000107001900000060011002700000002f0110019700000001022001900000002d0000c13d000000040210008c0000005c0000413d000000000207043b000000e002200270000000310320009c000000350000613d000000320220009c0000005c0000c13d0000000002000416000000000202004b0000005c0000c13d000000040110008a000000400110008c0000005c0000413d0000000401700370000000000101043b000000330210009c0000005c0000213d0000000000100435000000200000043f0000000001000019000700000007035300b800a10000040f000000070200035f0000002402200370000000000202043b0000000000200435000000200010043f000000000100001900b800a10000040f000000000101041a000000800010043f0000003b01000041000000b90001042e0000000001000416000000000101004b0000005c0000c13d0000002001000039000001000010044300000120000004430000003001000041000000b90001042e0000000002000416000000000202004b0000005c0000c13d000000040210008a000000400220008c0000005c0000413d0000000402700370000000000202043b000300000002001d000000330220009c0000005c0000213d0000002402700370000000000202043b000000340320009c0000005c0000213d00000023032000390000003504000041000000000513004b000000000500001900000000050480190000003503300197000000000603004b0000000004008019000000350330009c000000000405c019000000000304004b0000005c0000c13d0000000403200039000000000337034f000000000303043b000200000003001d000000340330009c0000005c0000213d000100240020003d000000020200002900000006022002100000000102200029000000000112004b0000005e0000a13d0000000001000019000000ba000104300000000001000411000080060110008c000000950000c13d000000020100006b000000930000613d0000002f0400004100008010050000390000000002000019000700000005001d000500000002001d00000006012002100000000101100029000000200210003900000000022003670000000001100367000000000101043b000600000001001d000000000102043b000400000001001d00000003010000290000000000100435000000200000043f00000000010004140000002f0210009c0000000001048019000000c0011002100000003a011001c7000000000205001900b800b30000040f00000001022001900000005c0000613d000000000101043b00000006020000290000000000200435000000200010043f00000000010004140000002f0210009c0000002f01008041000000c0011002100000003a011001c7000000070200002900b800b30000040f00000001022001900000005c0000613d000000000101043b0000000402000029000000000021041b00000005020000290000000102200039000000020120006c0000002f040000410000000705000029000000670000413d0000000001000019000000b90001042e0000003601000041000000800010043f0000002001000039000000840010043f0000002d01000039000000a40010043f0000003701000041000000c40010043f0000003801000041000000e40010043f0000003901000041000000ba000104300000002f020000410000002f0310009c000000000102801900000000030004140000002f0430009c0000000003028019000000c0023002100000004001100210000000000121019f0000003a011001c7000080100200003900b800b30000040f0000000102200190000000b10000613d000000000101043b000000000001042d0000000001000019000000ba00010430000000b6002104230000000102000039000000000001042d0000000002000019000000000001042d000000b800000432000000b90001042e000000ba00010430000000000000000000000000000000000000000000000000000000000000000000000000ffffffff000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000ad7e232e00000000000000000000000000000000000000000000000000000000310ab089000000000000000000000000ffffffffffffffffffffffffffffffffffffffff000000000000000000000000000000000000000000000000ffffffffffffffff800000000000000000000000000000000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c7920627920746865206465706c6f7965722073797374656d20636f6e74726163740000000000000000000000000000000000000000000000000000000000000000000000000000840000008000000000000000000200000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000002000000080000000000000000028a16027fc82a9cfec45fb7b822769cfc1cc87e98487cabeb992a9c550ae7f06", + "deployedBytecode": "0x00010000000000020007000000000002000000000701034f00000000000703550000008001000039000000400010043f000000000107001900000060011002700000002f0110019700000001022001900000002d0000c13d000000040210008c0000005c0000413d000000000207043b000000e002200270000000310320009c000000350000613d000000320220009c0000005c0000c13d0000000002000416000000000202004b0000005c0000c13d000000040110008a000000400110008c0000005c0000413d0000000401700370000000000101043b000000330210009c0000005c0000213d0000000000100435000000200000043f0000000001000019000700000007035300b800a10000040f000000070200035f0000002402200370000000000202043b0000000000200435000000200010043f000000000100001900b800a10000040f000000000101041a000000800010043f0000003b01000041000000b90001042e0000000001000416000000000101004b0000005c0000c13d0000002001000039000001000010044300000120000004430000003001000041000000b90001042e0000000002000416000000000202004b0000005c0000c13d000000040210008a000000400220008c0000005c0000413d0000000402700370000000000202043b000300000002001d000000330220009c0000005c0000213d0000002402700370000000000202043b000000340320009c0000005c0000213d00000023032000390000003504000041000000000513004b000000000500001900000000050480190000003503300197000000000603004b0000000004008019000000350330009c000000000405c019000000000304004b0000005c0000c13d0000000403200039000000000337034f000000000303043b000200000003001d000000340330009c0000005c0000213d000100240020003d000000020200002900000006022002100000000102200029000000000112004b0000005e0000a13d0000000001000019000000ba000104300000000001000411000080060110008c000000950000c13d000000020100006b000000930000613d0000002f0400004100008010050000390000000002000019000700000005001d000500000002001d00000006012002100000000101100029000000200210003900000000022003670000000001100367000000000101043b000600000001001d000000000102043b000400000001001d00000003010000290000000000100435000000200000043f00000000010004140000002f0210009c0000000001048019000000c0011002100000003a011001c7000000000205001900b800b30000040f00000001022001900000005c0000613d000000000101043b00000006020000290000000000200435000000200010043f00000000010004140000002f0210009c0000002f01008041000000c0011002100000003a011001c7000000070200002900b800b30000040f00000001022001900000005c0000613d000000000101043b0000000402000029000000000021041b00000005020000290000000102200039000000020120006c0000002f040000410000000705000029000000670000413d0000000001000019000000b90001042e0000003601000041000000800010043f0000002001000039000000840010043f0000002d01000039000000a40010043f0000003701000041000000c40010043f0000003801000041000000e40010043f0000003901000041000000ba000104300000002f020000410000002f0310009c000000000102801900000000030004140000002f0430009c0000000003028019000000c0023002100000004001100210000000000121019f0000003a011001c7000080100200003900b800b30000040f0000000102200190000000b10000613d000000000101043b000000000001042d0000000001000019000000ba00010430000000b6002104230000000102000039000000000001042d0000000002000019000000000001042d000000b800000432000000b90001042e000000ba00010430000000000000000000000000000000000000000000000000000000000000000000000000ffffffff000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000ad7e232e00000000000000000000000000000000000000000000000000000000310ab089000000000000000000000000ffffffffffffffffffffffffffffffffffffffff000000000000000000000000000000000000000000000000ffffffffffffffff800000000000000000000000000000000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c7920627920746865206465706c6f7965722073797374656d20636f6e74726163740000000000000000000000000000000000000000000000000000000000000000000000000000840000008000000000000000000200000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000002000000080000000000000000028a16027fc82a9cfec45fb7b822769cfc1cc87e98487cabeb992a9c550ae7f06", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/Keccak256.yul.zbin b/.test-node-subtree/src/deps/contracts/Keccak256.yul.zbin new file mode 100644 index 00000000..143dd2af Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/Keccak256.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/KnownCodesStorage.json b/.test-node-subtree/src/deps/contracts/KnownCodesStorage.json new file mode 100644 index 00000000..4979ae9c --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/KnownCodesStorage.json @@ -0,0 +1,81 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "KnownCodesStorage", + "sourceName": "cache-zk/solpp-generated-contracts/KnownCodesStorage.sol", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "bytes32", + "name": "bytecodeHash", + "type": "bytes32" + }, + { + "indexed": true, + "internalType": "bool", + "name": "sendBytecodeToL1", + "type": "bool" + } + ], + "name": "MarkedAsKnown", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "_hash", + "type": "bytes32" + } + ], + "name": "getMarker", + "outputs": [ + { + "internalType": "uint256", + "name": "marker", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "_bytecodeHash", + "type": "bytes32" + } + ], + "name": "markBytecodeAsPublished", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bool", + "name": "_shouldSendToL1", + "type": "bool" + }, + { + "internalType": "bytes32[]", + "name": "_hashes", + "type": "bytes32[]" + } + ], + "name": "markFactoryDeps", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "bytecode": "0x0001000000000002000800000000000200000000000103550000008003000039000000400030043f000000000301001900000060033002700000005f033001970000000102200190000000200000c13d000000040230008c000001180000413d000000000201043b000000e002200270000000610420009c000000280000613d000000620420009c0000007f0000613d000000630220009c000001180000c13d0000000002000416000000000202004b000001180000c13d000000040230008a000000200220008c000001180000413d0000000401100370000000000101043b000000000101041a000000800010043f0000007b01000041000001790001042e0000000001000416000000000101004b000001180000c13d0000002001000039000001000010044300000120000004430000006001000041000001790001042e0000000002000416000000000202004b000001180000c13d000000040230008a000000400220008c000001180000413d0000000402100370000000000402043b000000000204004b0000000002000019000000010200c039000200000004001d000000000224004b000001180000c13d0000002402100370000000000202043b000000640420009c000001180000213d00000023042000390000006505000041000000000634004b000000000600001900000000060580190000006504400197000000000704004b0000000005008019000000650440009c000000000506c019000000000405004b000001180000c13d0000000404200039000000000441034f000000000404043b000800000004001d000000640440009c000001180000213d000700240020003d000000080200002900000005022002100000000702200029000000000232004b000001180000213d0000000002000411000080010220008c000000c00000c13d000000080200006b000000be0000613d000000020200006b000000c80000c13d000500010000003d0004800d0000003d000300030000003d0000000004000019000000610000013d0000000104400039000000080240006c000000be0000813d00000005024002100000000702200029000000000221034f000000000502043b000000000205041a000000000202004b0000005e0000c13d00000069015001970000006a0110009c0000011a0000c13d000600000004001d0000006b015001980000012f0000613d0000000501000029000000000015041b00000000010004140000005f0210009c0000005f01008041000000c00110021000000071011001c700000004020000290000000303000029000000720400004100000000060000190178016e0000040f0000000001000367000000010220019000000006040000290000005e0000c13d000001180000013d0000000002000416000000000202004b000001180000c13d000000040230008a000000200220008c000001180000413d0000000401100370000000000501043b00000000010004110000800e0110008c000000990000c13d000000000105041a000000000101004b000000be0000c13d00000069015001970000006a0110009c000000a30000c13d0000006b01500198000000af0000c13d0000006601000041000000800010043f0000002001000039000000840010043f000000a40010043f0000007701000041000000a00000013d0000006601000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f0000007901000041000000c40010043f00000068010000410000017a000104300000006601000041000000800010043f0000002001000039000000840010043f0000002201000039000000a40010043f0000007501000041000000c40010043f0000007401000041000000e40010043f0000007a010000410000017a000104300000000101000039000000000015041b0000005f0100004100000000020004140000005f0320009c0000000002018019000000c00120021000000071011001c70000800d020000390000000303000039000000720400004100000000060000190178016e0000040f0000000101200190000001180000613d0000000001000019000001790001042e0000006601000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f0000006701000041000000a00000013d000580080000003d000180020000003d0000000004000019000000cf0000013d0000000104400039000000080240006c000000be0000813d00000005024002100000000702200029000000000221034f000000000302043b000000000203041a000000000202004b000000cc0000c13d00000069013001970000006a0110009c0000011a0000c13d000400000004001d000600000003001d0000006b013001980000012f0000613d0000006c0100004100000000001004390000000501000029000000040010044300000000010004140000005f0210009c0000005f01008041000000c0011002100000006d011001c70000000102000029017801730000040f0000000102200190000001400000613d000000000101043b000000000101004b0000000602000029000001180000613d000000400400043d0000006e0100004100000000001404350000000401400039000000000021043500000000010004140000005f0210009c0000005f0300004100000000010380190000005f0240009c000300000004001d000000000203001900000000020440190000004002200210000000c001100210000000000121019f0000006f011001c700000005020000290178016e0000040f0000000102200190000001410000613d0000000302000029000000700120009c000001670000813d000000400020043f00000001010000390000000605000029000000000015041b00000000010004140000005f0210009c0000005f01008041000000c00110021000000071011001c70000800d020000390000000303000039000000720400004100000002060000290178016e0000040f000000000100036700000001022001900000000404000029000000cc0000c13d00000000010000190000017a00010430000000400100043d000000640210003900000074030000410000000000320435000000440210003900000075030000410000000000320435000000240210003900000022030000390000000000320435000000660200004100000000002104350000000402100039000000200300003900000000003204350000005f020000410000005f0310009c0000000001028019000000400110021000000076011001c70000017a00010430000000400100043d00000044021000390000007703000041000000000032043500000066020000410000000000210435000000240210003900000020030000390000000000320435000000040210003900000000003204350000005f020000410000005f0310009c0000000001028019000000400110021000000078011001c70000017a00010430000000000001042f000000400200043d000000000301001900000060033002700000001f0430018f0000005f033001970000000505300272000001510000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000001490000413d000000000604004b000001600000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f00000000001504350000005f010000410000005f0420009c000000000201801900000040012002100000006002300210000000000121019f0000017a00010430000000730100004100000000001004350000004101000039000000040010043f0000006f010000410000017a00010430000000000001042f00000171002104210000000102000039000000000001042d0000000002000019000000000001042d00000176002104230000000102000039000000000001042d0000000002000019000000000001042d0000017800000432000001790001042e0000017a00010430000000000000000000000000000000000000000000000000000000000000000000000000ffffffff000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000e516761e0000000000000000000000000000000000000000000000000000000079c4f929000000000000000000000000000000000000000000000000000000004c6314f0000000000000000000000000000000000000000000000000ffffffffffffffff800000000000000000000000000000000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c792062792074686520626f6f746c6f61646572000000000000000000000000000000000000000064000000800000000000000000ffff000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000001806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b83020000020000000000000000000000000000002400000000000000000000000039b34c6e00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000000000000000000000000000000000000000000000000000000000000000000000100000000000000000200000000000000000000000000000000000000000000000000000000000000c94722ff13eacf53547c4741dab5228353a05938ffcdd5d4a2d533ae0e6182874e487b71000000000000000000000000000000000000000000000000000000007368000000000000000000000000000000000000000000000000000000000000496e636f72726563746c7920666f726d61747465642062797465636f646548610000000000000000000000000000000000000084000000000000000000000000436f6465206c656e67746820696e20776f726473206d757374206265206f6464000000000000000000000000000000000000006400000000000000000000000043616c6c61626c65206f6e6c792062792074686520636f6d70726573736f7200000000000000000000000000000000000000008400000080000000000000000000000000000000000000000000000000000000200000008000000000000000006b28fb10fc8cfbfedd440d6eee04453824b9bb37938a7d0a0e4f0cd4cafa9d62", + "deployedBytecode": "0x0001000000000002000800000000000200000000000103550000008003000039000000400030043f000000000301001900000060033002700000005f033001970000000102200190000000200000c13d000000040230008c000001180000413d000000000201043b000000e002200270000000610420009c000000280000613d000000620420009c0000007f0000613d000000630220009c000001180000c13d0000000002000416000000000202004b000001180000c13d000000040230008a000000200220008c000001180000413d0000000401100370000000000101043b000000000101041a000000800010043f0000007b01000041000001790001042e0000000001000416000000000101004b000001180000c13d0000002001000039000001000010044300000120000004430000006001000041000001790001042e0000000002000416000000000202004b000001180000c13d000000040230008a000000400220008c000001180000413d0000000402100370000000000402043b000000000204004b0000000002000019000000010200c039000200000004001d000000000224004b000001180000c13d0000002402100370000000000202043b000000640420009c000001180000213d00000023042000390000006505000041000000000634004b000000000600001900000000060580190000006504400197000000000704004b0000000005008019000000650440009c000000000506c019000000000405004b000001180000c13d0000000404200039000000000441034f000000000404043b000800000004001d000000640440009c000001180000213d000700240020003d000000080200002900000005022002100000000702200029000000000232004b000001180000213d0000000002000411000080010220008c000000c00000c13d000000080200006b000000be0000613d000000020200006b000000c80000c13d000500010000003d0004800d0000003d000300030000003d0000000004000019000000610000013d0000000104400039000000080240006c000000be0000813d00000005024002100000000702200029000000000221034f000000000502043b000000000205041a000000000202004b0000005e0000c13d00000069015001970000006a0110009c0000011a0000c13d000600000004001d0000006b015001980000012f0000613d0000000501000029000000000015041b00000000010004140000005f0210009c0000005f01008041000000c00110021000000071011001c700000004020000290000000303000029000000720400004100000000060000190178016e0000040f0000000001000367000000010220019000000006040000290000005e0000c13d000001180000013d0000000002000416000000000202004b000001180000c13d000000040230008a000000200220008c000001180000413d0000000401100370000000000501043b00000000010004110000800e0110008c000000990000c13d000000000105041a000000000101004b000000be0000c13d00000069015001970000006a0110009c000000a30000c13d0000006b01500198000000af0000c13d0000006601000041000000800010043f0000002001000039000000840010043f000000a40010043f0000007701000041000000a00000013d0000006601000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f0000007901000041000000c40010043f00000068010000410000017a000104300000006601000041000000800010043f0000002001000039000000840010043f0000002201000039000000a40010043f0000007501000041000000c40010043f0000007401000041000000e40010043f0000007a010000410000017a000104300000000101000039000000000015041b0000005f0100004100000000020004140000005f0320009c0000000002018019000000c00120021000000071011001c70000800d020000390000000303000039000000720400004100000000060000190178016e0000040f0000000101200190000001180000613d0000000001000019000001790001042e0000006601000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f0000006701000041000000a00000013d000580080000003d000180020000003d0000000004000019000000cf0000013d0000000104400039000000080240006c000000be0000813d00000005024002100000000702200029000000000221034f000000000302043b000000000203041a000000000202004b000000cc0000c13d00000069013001970000006a0110009c0000011a0000c13d000400000004001d000600000003001d0000006b013001980000012f0000613d0000006c0100004100000000001004390000000501000029000000040010044300000000010004140000005f0210009c0000005f01008041000000c0011002100000006d011001c70000000102000029017801730000040f0000000102200190000001400000613d000000000101043b000000000101004b0000000602000029000001180000613d000000400400043d0000006e0100004100000000001404350000000401400039000000000021043500000000010004140000005f0210009c0000005f0300004100000000010380190000005f0240009c000300000004001d000000000203001900000000020440190000004002200210000000c001100210000000000121019f0000006f011001c700000005020000290178016e0000040f0000000102200190000001410000613d0000000302000029000000700120009c000001670000813d000000400020043f00000001010000390000000605000029000000000015041b00000000010004140000005f0210009c0000005f01008041000000c00110021000000071011001c70000800d020000390000000303000039000000720400004100000002060000290178016e0000040f000000000100036700000001022001900000000404000029000000cc0000c13d00000000010000190000017a00010430000000400100043d000000640210003900000074030000410000000000320435000000440210003900000075030000410000000000320435000000240210003900000022030000390000000000320435000000660200004100000000002104350000000402100039000000200300003900000000003204350000005f020000410000005f0310009c0000000001028019000000400110021000000076011001c70000017a00010430000000400100043d00000044021000390000007703000041000000000032043500000066020000410000000000210435000000240210003900000020030000390000000000320435000000040210003900000000003204350000005f020000410000005f0310009c0000000001028019000000400110021000000078011001c70000017a00010430000000000001042f000000400200043d000000000301001900000060033002700000001f0430018f0000005f033001970000000505300272000001510000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000001490000413d000000000604004b000001600000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f00000000001504350000005f010000410000005f0420009c000000000201801900000040012002100000006002300210000000000121019f0000017a00010430000000730100004100000000001004350000004101000039000000040010043f0000006f010000410000017a00010430000000000001042f00000171002104210000000102000039000000000001042d0000000002000019000000000001042d00000176002104230000000102000039000000000001042d0000000002000019000000000001042d0000017800000432000001790001042e0000017a00010430000000000000000000000000000000000000000000000000000000000000000000000000ffffffff000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000e516761e0000000000000000000000000000000000000000000000000000000079c4f929000000000000000000000000000000000000000000000000000000004c6314f0000000000000000000000000000000000000000000000000ffffffffffffffff800000000000000000000000000000000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c792062792074686520626f6f746c6f61646572000000000000000000000000000000000000000064000000800000000000000000ffff000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000001806aa1896bbf26568e884a7374b41e002500962caba6a15023a8d90e8508b83020000020000000000000000000000000000002400000000000000000000000039b34c6e00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000000000000000000000000000000000000000000000000000000000000000000000100000000000000000200000000000000000000000000000000000000000000000000000000000000c94722ff13eacf53547c4741dab5228353a05938ffcdd5d4a2d533ae0e6182874e487b71000000000000000000000000000000000000000000000000000000007368000000000000000000000000000000000000000000000000000000000000496e636f72726563746c7920666f726d61747465642062797465636f646548610000000000000000000000000000000000000084000000000000000000000000436f6465206c656e67746820696e20776f726473206d757374206265206f6464000000000000000000000000000000000000006400000000000000000000000043616c6c61626c65206f6e6c792062792074686520636f6d70726573736f7200000000000000000000000000000000000000008400000080000000000000000000000000000000000000000000000000000000200000008000000000000000006b28fb10fc8cfbfedd440d6eee04453824b9bb37938a7d0a0e4f0cd4cafa9d62", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/L1Messenger.json b/.test-node-subtree/src/deps/contracts/L1Messenger.json new file mode 100644 index 00000000..f87ef827 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/L1Messenger.json @@ -0,0 +1,169 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "L1Messenger", + "sourceName": "cache-zk/solpp-generated-contracts/L1Messenger.sol", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "bytes32", + "name": "_bytecodeHash", + "type": "bytes32" + } + ], + "name": "BytecodeL1PublicationRequested", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "_sender", + "type": "address" + }, + { + "indexed": true, + "internalType": "bytes32", + "name": "_hash", + "type": "bytes32" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "_message", + "type": "bytes" + } + ], + "name": "L1MessageSent", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "components": [ + { + "internalType": "uint8", + "name": "l2ShardId", + "type": "uint8" + }, + { + "internalType": "bool", + "name": "isService", + "type": "bool" + }, + { + "internalType": "uint16", + "name": "txNumberInBlock", + "type": "uint16" + }, + { + "internalType": "address", + "name": "sender", + "type": "address" + }, + { + "internalType": "bytes32", + "name": "key", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "value", + "type": "bytes32" + } + ], + "indexed": false, + "internalType": "struct L2ToL1Log", + "name": "_l2log", + "type": "tuple" + } + ], + "name": "L2ToL1LogSent", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "_totalL2ToL1PubdataAndStateDiffs", + "type": "bytes" + } + ], + "name": "publishPubdataAndClearState", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "_bytecodeHash", + "type": "bytes32" + } + ], + "name": "requestBytecodeL1Publication", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bool", + "name": "_isService", + "type": "bool" + }, + { + "internalType": "bytes32", + "name": "_key", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "_value", + "type": "bytes32" + } + ], + "name": "sendL2ToL1Log", + "outputs": [ + { + "internalType": "uint256", + "name": "logIdInMerkleTree", + "type": "uint256" + } + ], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "_message", + "type": "bytes" + } + ], + "name": "sendToL1", + "outputs": [ + { + "internalType": "bytes32", + "name": "hash", + "type": "bytes32" + } + ], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "bytecode": "0x0002000000000002000e000000000002000100000001035500000000030100190000006005300270000002420050019d0000008004000039000000400040043f00000242035001970000000102200190000000310000c13d000000040230008c000001250000413d000000000201043b000000e002200270000002440620009c000000390000213d000002470420009c000000710000613d000002480220009c000001250000c13d0000000002000416000000000202004b000001250000c13d000000040230008a000000600220008c000001250000413d0000000401100370000000000301043b000000000103004b0000000001000019000000010100c039000000000113004b000001250000c13d0000000002000411000002870120009c000000ec0000413d0000025d01000041000000800010043f0000002001000039000000840010043f0000003401000039000000a40010043f0000028901000041000000c40010043f0000028a01000041000000e40010043f0000028b0100004100000904000104300000000001000416000000000101004b000001250000c13d0000002001000039000001000010044300000120000004430000024301000041000009030001042e000002450620009c000000ae0000613d000002460220009c000001250000c13d0000000002000416000000000202004b000001250000c13d000000040230008a000000200220008c000001250000413d0000000402100370000000000202043b000002490620009c000001250000213d00000023062000390000024a07000041000000000836004b000000000800001900000000080780190000024a06600197000000000906004b00000000070080190000024a0660009c000000000708c019000000000607004b000001250000c13d0000000406200039000000000661034f000000000706043b000002490670009c000001250000213d00000024082000390000000002870019000000000323004b000001250000413d000000000900041400000000030004140000024b0630009c0000014a0000413d00000044014000390000025f0200004100000000002104350000002401400039000000080200003900000000002104350000025d0100004100000000001404350000000401400039000000200200003900000000002104350000024201000041000002420240009c000000000401801900000040014002100000025e011001c700000904000104300000000002000416000000000202004b000001250000c13d000000040230008a000000200220008c000001250000413d0000000002000411000080040220008c000000e20000c13d0000000401100370000000000201043b0000000301000039000d00000001001d000000000101041a000000a00010043f000e00000002001d000000c00020043f0000004001000039000000800010043f000000e001000039000000400010043f00000242010000410000000002000414000002420320009c0000000002018019000000c0012002100000028d011001c70000801002000039090208f80000040f0000000102200190000001250000613d000000000101043b0000000d02000029000000000012041b000000000100041300000242031001970000000e06000029000000e0016002700000ffff0210018f000000050120021000000004041001bf00000000514300a900000000544100d9000000000343004b0000019d0000c13d0000000102200270000000010320003900000007423000c9000000075420011a000000000343004b0000019d0000c13d00000000012100190000028e0210009c000001df0000413d000000400100043d00000044021000390000025f03000041000000000032043500000024021000390000000803000039000005fe0000013d0000000002000416000000000202004b000001250000c13d000000040230008a000000200220008c000001250000413d0000000402100370000000000202043b000002490420009c000001250000213d00000023042000390000024a05000041000000000634004b000000000600001900000000060580190000024a04400197000000000704004b00000000050080190000024a0440009c000000000506c019000000000405004b000001250000c13d0000000404200039000000000541034f000000000505043b000b00000005001d000002490550009c000001250000213d0000002402200039000a00000002001d0000000b02200029000000000232004b000001250000213d0000000002000411000080010220008c000001a30000c13d0000000b02000029000000040220008c000001250000413d0000002002400039000000000221034f000000000402043b000002620240009c0000029b0000413d0000025d01000041000000800010043f0000002001000039000000840010043f0000001401000039000000a40010043f0000028601000041000000e90000013d0000025d01000041000000800010043f0000002001000039000000840010043f0000001401000039000000a40010043f0000028c01000041000000c40010043f00000261010000410000090400010430000e00000003001d000d00000002001d0000025101000041000000800010043f00000242010000410000000002000414000002420320009c0000000002018019000000c00120021000000288011001c70000800b02000039090208f80000040f000000000301001900000060033002700000024203300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000010a0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000001020000413d000000000705004b000001190000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000001270000613d0000001f01400039000000600210018f00000080082001bf000000400080043f000000200130008c0000000e05000029000001250000413d000000800100043d0000ffff0310008c000001ab0000a13d00000000010000190000090400010430000000400200043d0000001f0430018f0000000505300272000001340000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000012c0000413d000000000604004b000001430000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f00000000001504350000024201000041000002420420009c000000000201801900000040012002100000006002300210000000000121019f0000090400010430000e00000009001d000d00000007001d000c00000008001d0000024204800197000000000141034f0000000002250049000002420220019700000000012103df000000c0023002100000024c022001970000024d022001c700000000012103af0000801002000039090208fd0000040f0000000003010019000000600330027000000242033001970000000102200190000001ea0000613d0000003f023000390000024e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000002490640009c000001db0000213d0000000105500190000001db0000c13d000000400040043f00000000043204360000001f053000390000000505500272000001780000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b000001700000413d000000000500004b0000017a0000613d0000001f0530018f00000005033002720000000e09000029000001870000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b0000017f0000413d000000000605004b000001960000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f00000000001304350000000001020433000000200110008c000005f80000c13d00000000040404330000000002000414000000000129004b000003ad0000813d000002840100004100000000001004350000001101000039000000040010043f000002850100004100000904000104300000025d01000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f0000026001000041000000e90000013d0000014003200039000000400030043f0000000000080435000000a003200039000b00000003001d00000000005304350000025504000041000000000305004b0000000004006019000000e003200039000e00000003001d0000000d090000290000000000930435000000c003200039000900000003001d000000000013043500000001030003670000002405300370000000000505043b000001200720003900000100022001bf000a00000002001d00000000005204350000004402300370000000000602043b000c00000007001d00000000006704350000000002080433000000f807200210000000400200043d0000002003200039000000000073043500000021072000390000000000470435000000f00110021000000022042000390000000000140435000000600190021000000024042000390000000000140435000000580120003900000000006104350000003801200039000000000051043500000058010000390000000000120435000002560120009c000002050000a13d000002840100004100000000001004350000004101000039000001a00000013d00000028011000390000000002100420000000400100043d000000000202004b000002880000c13d00000044021000390000025c03000041000000000032043500000024021000390000001403000039000005fe0000013d0000001f0430018f0000000502300272000001f50000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000001ee0000413d000000000504004b000002030000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f0000000000120435000000600130021000000904000104300000008001200039000000400010043f0000024201000041000002420430009c000000000301801900000040033002100000000002020433000002420420009c00000000020180190000006002200210000000000232019f0000000003000414000002420430009c0000000003018019000000c001300210000000000121019f00000250011001c70000801002000039000d00000008001d090208f80000040f0000000102200190000001250000613d000000000201043b000000400100043d0000004003100039000000000400041a000000000023043500000020021000390000000000420435000000400300003900000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f0000024203000041000002420420009c000000000203801900000040022002100000000001010433000002420410009c00000000010380190000006001100210000000000121019f0000000002000414000002420420009c0000000002038019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f0000000102200190000001250000613d000000000101043b000000000010041b0000000103000039000000000203041a000000010100008a000800000002001d000000000112004b0000019d0000613d00000008010000290000000101100039000000000013041b0000000d010000290000000001010433000000ff0110018f000000400200043d00000000011204360000000b040000290000000004040433000000000404004b0000000004000019000000010400c0390000000000410435000000090100002900000000010104330000ffff0110018f000000400420003900000000001404350000000e0100002900000000010104330000025401100197000000600420003900000000001404350000000a010000290000000001010433000000800420003900000000001404350000000c010000290000000001010433000000a00420003900000000001404350000024205000041000002420120009c00000000020580190000000001000414000002420410009c00000000010580190000004002200210000000c001100210000000000121019f00000257011001c70000800d020000390000025804000041090208f30000040f0000000101200190000001250000613d00000078010000390000000003100420000000400100043d000002420210009c000002420200004100000000020140190000004002200210000000000303004b000005060000c13d00000044031000390000025c0400004100000000004304350000002403100039000000140400003900000000004304350000025d0300004100000000003104350000000401100039000000200300003900000000003104350000025e012001c70000090400010430000000000061043500000242020000410000000003000414000002420430009c0000000003028019000002420410009c00000000010280190000004001100210000000c002300210000000000112019f0000028f011001c70000800d0200003900000001030000390000029004000041090208f30000040f0000000101200190000001250000613d0000000001000019000009030001042e000000000131034f000600000004001d000000e0064002700000026302000041000000400020043f0000080002000039000700000002001d000000800020043f000000a00200003900000000030000190000000504300210000000000441034f000000000404043b00000000024204360000000103300039000008000430008c000002a50000413d000000040200003900000006010000290000024d0110009c00000000080000190000030a0000813d000000000100041a000000000118004b000003980000c13d000d00000002001d0000000601000029000002670110009c000002c20000213d0000026801000041000000800200043d000000000262004b000003060000a13d0000000502600210000000a0022000390000000000120435000007ff0260008c0000000106600039000002b90000413d000900400000003d000880100000003d0000000701000029000600000001001d000700010010027800000000040000190000000101400210000000800200043d000000000312004b000003060000a13d00000001011001bf000000000212004b000003060000a13d0000000501100210000000a0011000390000000002010433000e00000004001d0000000601400210000000a001100039000c00000001001d0000000003010433000000400100043d0000004004100039000000000024043500000020021000390000000000320435000000090300002900000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f000002420320009c0000024204000041000000000204801900000040022002100000000001010433000002420310009c00000000010480190000006001100210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000000802000029090208f80000040f0000000102200190000001250000613d000000800200043d0000000e04000029000000000242004b000003060000a13d00000005024002100000000c02200069000000000101043b00000000001204350000000104400039000000070140006c000002c80000413d0000000601000029000000030110008c000002c40000213d000000800100043d000000000101004b0000050a0000c13d000002840100004100000000001004350000003201000039000001a00000013d0000000401000039000900590000009200000000070000190000000008000019000800000006001d0000005803100039000d00000003001d0000000b0230006c000001250000213d0000000a0210002900000000010004140000024203200197000000090420006c0000019d0000213d00000058022000390000000004000031000000000524004b0000019d0000413d000c00000008001d000e00000007001d0000000103300367000002420510009c000000a70000213d0000000002240049000002420220019700000000022303df000000c0011002100000024c011001970000024d011001c700000000011203af0000801002000039090208fd0000040f0000000003010019000000600330027000000242033001970000000102200190000004ce0000613d0000003f023000390000024e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000002490640009c000001db0000213d0000000105500190000001db0000c13d000000400040043f00000000043204360000001f0530003900000005055002720000034a0000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b000003420000413d000000000500004b0000034c0000613d0000000505300272000003570000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000034f0000413d0000001f03300190000003660000613d0000000505500210000000000151034f00000000055400190000000303300210000000000605043300000000063601cf000000000636022f000000000101043b0000010003300089000000000131022f00000000013101cf000000000161019f00000000001504350000000001020433000000200110008c0000000e030000290000000c05000029000005f80000c13d000000800100043d000000000131004b000003060000a13d00000000020404330000000501300210000000a0011000390000000000210435000000400100043d000000400310003900000000002304350000004002000039000000000221043600000000005204350000024f0310009c000001db0000213d0000006003100039000000400030043f000002420320009c0000024204000041000000000204801900000040022002100000000001010433000002420310009c00000000010480190000006001100210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f000000010220019000000008060000290000000e07000029000001250000613d000000000801043b0000000107700039000000000167004b0000000d0200002900000000010200190000030f0000413d000002b10000013d000000400100043d00000064021000390000026403000041000000000032043500000044021000390000026503000041000000000032043500000024021000390000003c0300003900000000003204350000025d0200004100000000002104350000000402100039000000200300003900000000003204350000024202000041000002420310009c0000000001028019000000400110021000000266011001c70000090400010430000800000002001d0000000201000039000b00000001001d000000000301041a000000400100043d0000004002100039000a00000004001d0000000000420435000000200210003900000000003204350000004003000039000900000003001d00000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f0000024204000041000002420320009c000000000204801900000040022002100000000001010433000002420310009c00000000010480190000006001100210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f0000000102200190000001250000613d000000000101043b0000000b02000029000000000012041b0000025101000041000000400400043d000b00000004001d00000000001404350000000001000414000002420210009c00000242030000410000000001038019000002420240009c00000000030440190000004002300210000000c001100210000000000121019f00000252011001c70000800b02000039090208f80000040f0000000b0a000029000000000301001900000060033002700000024203300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000003f70000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b000003ef0000413d00000000090a0019000000000705004b000004070000613d0000000506600210000000000761034f00000000066900190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000004e90000613d0000001f01400039000000600110018f0000000002910019000000000112004b00000000010000190000000101004039000700000002001d000002490220009c000001db0000213d0000000101100190000001db0000c13d0000000701000029000000400010043f000000200130008c000001250000413d00000000010904330000ffff0210008c000001250000213d0000000702000029000002530220009c000001db0000213d0000000703000029000000c002300039000000400020043f000000000400041000000254024001970000006005300039000500000005001d000000000025043500000020053000390000000102000039000b00000002001d000300000005001d0000000000250435000000a0023000390000000a07000029000600000002001d000000000072043500000080023000390000000008000411000400000002001d000000000082043500000000000304350000004002300039000200000002001d0000000000120435000000400200043d00000020032000390000000000030435000000210520003900000255060000410000000000650435000000f0011002100000002205200039000000000015043500000060014002100000002404200039000000000014043500000058012000390000000000710435000000580100003900000000001204350000003801200039000100000008001d0000000000810435000002560120009c000001db0000213d0000008001200039000000400010043f0000024201000041000002420430009c000000000301801900000040033002100000000002020433000002420420009c00000000020180190000006002200210000000000232019f0000000003000414000002420430009c0000000003018019000000c001300210000000000121019f00000250011001c70000801002000039090208f80000040f0000000102200190000001250000613d000000000201043b000000400100043d0000004003100039000000000400041a000000000023043500000020021000390000000000420435000000090300002900000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f0000024203000041000002420420009c000000000203801900000040022002100000000001010433000002420410009c00000000010380190000006001100210000000000121019f0000000002000414000002420420009c0000000002038019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f0000000102200190000001250000613d000000000101043b000000000010041b0000000b01000029000000000101041a000000010200008a000000000221004b0000019d0000613d00000001011000390000000b03000029000000000013041b00000007010000290000000001010433000000ff0110018f000000400200043d000000000112043600000003040000290000000004040433000000000404004b0000000004000019000000010400c0390000000000410435000000020100002900000000010104330000ffff0110018f0000004004200039000000000014043500000005010000290000000001010433000002540110019700000060042000390000000000140435000000040100002900000000010104330000008004200039000000000014043500000006010000290000000001010433000000a00420003900000000001404350000024201000041000002420420009c00000000020180190000000005000414000002420450009c00000000050180190000004001200210000000c002500210000000000112019f00000257011001c70000800d020000390000025804000041090208f30000040f00000001012001900000000d01000029000001250000613d0000005c021000390000000001000413000002420310019700000000412300a90000025902200197000002590410019700000000422400d9000000000223004b00000008030000290000019d0000c13d0000000e02300069000000a0031000390000000001230019000000000231004b0000000002000019000000010200403900000001022001900000019d0000c13d0000024b0210009c000006e00000413d000000400400043d000000600000013d0000001f0430018f0000000502300272000004d90000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000004d20000413d000000000504004b000004e70000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000090400010430000000400200043d0000001f0430018f0000000505300272000004f60000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000004ee0000413d000000000604004b000005050000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000001430000013d000000080300002900000000003104350000025b012001c7000009030001042e000000050100008a000800000001001d0000000d0110006b0000019d0000213d0000000d0100002900000004031000390000000b0130006c000001250000213d000000a00100043d000500000001001d0000000d020000290000000a012000290000000101100367000000000101043b0000024d0210009c0000000009000019000005620000813d0000000201000039000400000001001d000000000101041a000000000119004b0000060a0000c13d0000000002030019000000080120006c0000019d0000213d00000004032000390000000b0130006c000001250000213d0000000a012000290000000101100367000000000101043b0000024d0210009c00000000090000190000063d0000813d00000000050300190000000301000039000d00000001001d000000000101041a000000000119004b000006e50000c13d0000000b0150006c000003060000813d0000000a015000290000000102000367000000000312034f000000000303043b0000027a03300197000002550330009c000007380000c13d0000000004050019000000080340006c0000019d0000213d00000004034000390000000b0430006c000001250000213d0000000101100039000000000112034f000000000101043b0000000b0430006c000003060000813d000000e8011002700000000a03300029000000000432034f0000000503500039000c00000031001d0000000c0510006b00000000060000190000000106004039000000000504043b00000001046001900000019d0000c13d0000000c060000290000000b0460006c000001250000213d0000000c040000290000027d0440009c000007720000413d000000400100043d0000004402100039000002830300004100000000003204350000025d0200004100000000002104350000002402100039000000200300003900000000003204350000000402100039000006030000013d000700e00010027800000000080000190000000009000019000000080130006c0000019d0000213d00000004023000390000000b0120006c000001250000213d0000000a033000290000000101000367000000000331034f000000000303043b000000e0053002700000000007250019000000000357004b0000000003000019000000010300403900000001033001900000019d0000c13d0000000b0370006c000001250000213d0000000a04200029000002420340019700000000020004140000000004450019000000000554004b0000000005000019000000010500403900000001055001900000019d0000c13d0000000005000031000000000645004b0000019d0000413d000e00000009001d000c00000008001d000d00000007001d000002420620009c000000a70000213d000000000131034f0000000003450049000002420330019700000000013103df000000c0022002100000024c022001970000024d022001c700000000012103af0000801002000039090208fd0000040f0000000003010019000000600330027000000242033001970000000102200190000006220000613d0000003f023000390000024e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000002490640009c000001db0000213d0000000105500190000001db0000c13d000000400040043f00000000043204360000001f053000390000000505500272000005b20000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b000005aa0000413d000000000500004b000005b40000613d00000005053002720000000e09000029000005c00000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000005b80000413d0000001f03300190000005cf0000613d0000000505500210000000000151034f00000000055400190000000303300210000000000605043300000000063601cf000000000636022f000000000101043b0000010003300089000000000131022f00000000013101cf000000000161019f00000000001504350000000001020433000000200110008c000005f80000c13d0000000002040433000000400100043d0000004003100039000000000023043500000020021000390000000000920435000000090300002900000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f000002420320009c0000024204000041000000000204801900000040022002100000000001010433000002420310009c00000000010480190000006001100210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f00000001022001900000000d030000290000000c08000029000001250000613d000000000901043b0000000108800039000000070180006c000005650000413d0000051b0000013d000000400100043d00000044021000390000026903000041000000000032043500000024021000390000001f0300003900000000003204350000025d0200004100000000002104350000000402100039000000200300003900000000003204350000024202000041000002420310009c000000000102801900000040011002100000025e011001c70000090400010430000000400100043d00000084021000390000026a03000041000000000032043500000064021000390000026b03000041000000000032043500000044021000390000026c0300004100000000003204350000002402100039000000440300003900000000003204350000025d0200004100000000002104350000000402100039000000200300003900000000003204350000024202000041000002420310009c000000000102801900000040011002100000026d011001c700000904000104300000001f0430018f00000005023002720000062d0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000006260000413d000000000504004b0000063b0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000090400010430000600e00010027800000000080000190000000009000019000000080130006c0000019d0000213d00000004023000390000000b0120006c000001250000213d0000000a033000290000000101000367000000000331034f000000000303043b000000e00a30027000000000072a00190000000004a7004b0000000004000019000000010400403900000001044001900000019d0000c13d0000000b0470006c000001250000213d0000026e04300198000007420000c13d000002700430009c000007460000813d00000271033001980000074a0000613d0000000a042000290000024203400197000000000200041400000000044a00190000000005a4004b0000000005000019000000010500403900000001055001900000019d0000c13d0000000005000031000000000645004b0000019d0000413d000d0000000a001d000e00000009001d000700000008001d000c00000007001d000002420620009c000000a70000213d000000000131034f0000000003450049000002420330019700000000013103df000000c0022002100000024c022001970000024d022001c700000000012103af0000000202000039090208fd0000040f0000000003010019000000600330027000000242033001970000000102200190000007510000613d0000003f023000390000024e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000002490640009c000001db0000213d0000000105500190000001db0000c13d000000400040043f00000000043204360000001f0530003900000005055002720000000d0a000029000006950000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b0000068d0000413d000000000500004b000006970000613d00000005053002720000000e09000029000006a30000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000069b0000413d0000001f03300190000006b20000613d0000000505500210000000000151034f00000000055400190000000303300210000000000605043300000000063601cf000000000636022f000000000101043b0000010003300089000000000131022f00000000013101cf000000000161019f0000000000150435000000400100043d0000000002020433000000200220008c0000076c0000c13d00000000020404330000027302200197000000db03a002100000027403300197000000000223019f00000255022001c70000004003100039000000000023043500000020021000390000000000920435000000090300002900000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f000002420320009c0000024204000041000000000204801900000040022002100000000001010433000002420310009c00000000010480190000006001100210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f00000001022001900000000c030000290000000708000029000001250000613d000000000901043b0000000108800039000000060180006c000006400000413d0000052c0000013d0000000002100420000000400100043d000000000202004b000006f20000c13d000001e40000013d000000400100043d00000084021000390000027703000041000000000032043500000064021000390000027803000041000000000032043500000044021000390000027903000041000000000032043500000024021000390000005e03000039000006160000013d000000200200003900000000022104360000000d0500002900000000005204350000001f0350018f00000040021000390000000c0400002900000001044003670000000505500272000007050000613d000000000600001900000005076002100000000008720019000000000774034f000000000707043b00000000007804350000000106600039000000000756004b000006fd0000413d000000000603004b000007140000613d0000000505500210000000000454034f00000000055200190000000303300210000000000605043300000000063601cf000000000636022f000000000404043b0000010003300089000000000434022f00000000033401cf000000000363019f00000000003504350000000d03000029000000000232001900000000000204350000005f02300039000000200300008a000000000232016f0000024204000041000002420310009c00000000010480190000004001100210000002420320009c00000000020480190000006002200210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000800d0200003900000003030000390000025a0400004100000001050000290000000a06000029090208f30000040f0000000101200190000001250000613d000000400100043d0000000a020000290000000000210435000002420210009c000002420100804100000040011002100000025b011001c7000009030001042e000000400100043d00000064021000390000027b03000041000000000032043500000044021000390000027c03000041000000000032043500000024021000390000002703000039000003a10000013d000000400100043d00000044021000390000026f030000410000074d0000013d000000400100043d000000440210003900000276030000410000074d0000013d000000400100043d00000044021000390000027503000041000000000032043500000024021000390000000403000029000005fe0000013d0000001f0430018f00000005023002720000075c0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000007550000413d000000000504004b0000076a0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000009040001043000000044021000390000027203000041000000000032043500000024021000390000001903000039000005fe0000013d0000000c0400002900000004064000390000000b0460006c000001250000213d0000000c070000290000000a04700029000000000442034f000000000804043b000000e00780027000000110947000c90000024d0880009c000007810000413d00000000987400d9000001100880008c0000019d0000c13d0000000009640019000900000009001d0000000b0890006c000001250000213d000000f805500270000000400a00043d0000004408a00039000000800900003900000000009804350000002408a0003900000000005804350000027e0500004100000000005a04350000000a066000290000008405a0003900000000004504350000000405a000390000000000750435000000000862034f0000001f0740018f000e0000000a001d000000a406a000390000000509400272000007a20000613d000000000a000019000000050ba00210000000000cb60019000000000bb8034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b0000079a0000413d0000000a03300029000000000a07004b000007b20000613d0000000509900210000000000898034f00000000099600190000000307700210000000000a090433000000000a7a01cf000000000a7a022f000000000808043b0000010007700089000000000878022f00000000077801cf0000000007a7019f0000000000790435000000000746001900000000000704350000001f044000390000027f04400197000000000646001900000000045600490000000e0500002900000064055000390000000000450435000000000432034f0000001f0310018f00000000021604360000000505100272000007c90000613d000000000600001900000005076002100000000008720019000000000774034f000000000707043b00000000007804350000000106600039000000000756004b000007c10000413d000000000603004b000007d80000613d0000000505500210000000000454034f00000000055200190000000303300210000000000605043300000000063601cf000000000636022f000000000404043b0000010003300089000000000434022f00000000033401cf000000000363019f0000000000350435000000000312001900000000000304350000001f0110003900000280011001970000000e04000029000000000141004900000000012100190000024202000041000002420340009c000000000302001900000000030440190000004003300210000002420410009c00000000010280190000006001100210000000000131019f0000000003000414000002420430009c0000000003028019000000c002300210000000000112019f0000800e02000039090208f30000040f000000000301001900000060033002700000024203300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000008010000613d000000000700001900000005087002100000000e09800029000000000881034f000000000808043b00000000008904350000000107700039000000000867004b000007f90000413d000000000705004b000008100000613d0000000506600210000000000761034f0000000e066000290000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000008360000613d0000001f01400039000000600210018f0000000e01200029000000000221004b00000000020000190000000102004039000002490410009c000001db0000213d0000000102200190000001db0000c13d000000400010043f000000200230008c000001250000413d00000009030000290000000b0230006c000008530000c13d0000000e010000290000000001010433000e00000001001d0000000501000029000000000010041d0000000a010000290000000c020000290902085c0000040f0000000102000039000000000012041d00000004010000290000000e03000029000000000031041d000000000000041b000000000002041b000000000001041b0000000d01000029000000000001041b0000000001000019000009030001042e000000400200043d0000001f0430018f0000000505300272000008430000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000083b0000413d000000000604004b000008520000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000001430000013d00000064021000390000028103000041000000000032043500000044021000390000028203000041000000000032043500000024021000390000002a03000039000003a10000013d00000000030004140000000004120019000000000224004b0000000005000019000000010500403900000242021001970000000101500190000008b50000c13d0000000001000031000000000541004b000008b50000413d00000001022003670000024b0530009c000008b90000813d0000000001410049000002420110019700000000011203df000000c0023002100000024c022001970000024d022001c700000000012103af0000801002000039090208fd0000040f0000000003010019000000600330027000000242033001970000000102200190000008c00000613d0000003f023000390000024e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000002490640009c000008db0000213d0000000105500190000008db0000c13d000000400040043f00000000043204360000001f053000390000000505500272000008930000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b0000088b0000413d000000000500004b000008950000613d0000001f0530018f0000000503300272000008a10000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b000008990000413d000000000605004b000008b00000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f00000000001304350000000001020433000000200110008c000008e10000c13d0000000001040433000000000001042d000002840100004100000000001004350000001101000039000008de0000013d000000400100043d00000044021000390000025f03000041000000000032043500000024021000390000000803000039000008e70000013d0000001f0430018f0000000502300272000008cb0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000008c40000413d000000000504004b000008d90000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000090400010430000002840100004100000000001004350000004101000039000000040010043f00000285010000410000090400010430000000400100043d00000044021000390000026903000041000000000032043500000024021000390000001f0300003900000000003204350000025d0200004100000000002104350000000402100039000000200300003900000000003204350000024202000041000002420310009c000000000102801900000040011002100000025e011001c70000090400010430000008f6002104210000000102000039000000000001042d0000000002000019000000000001042d000008fb002104230000000102000039000000000001042d0000000002000019000000000001042d00000900002104230000000102000039000000000001042d0000000002000019000000000001042d0000090200000432000009030001042e000009040001043000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000628b636d00000000000000000000000000000000000000000000000000000000628b636e0000000000000000000000000000000000000000000000000000000062f84b240000000000000000000000000000000000000000000000000000000039b34c6e0000000000000000000000000000000000000000000000000000000056079ac8000000000000000000000000000000000000000000000000ffffffffffffffff8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000000000000ffffffff000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001ffffffe0000000000000000000000000000000000000000000000000ffffffffffffff9f02000000000000000000000000000000000000000000000000000000000000008ac84c0e000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff3f000000000000000000000000ffffffffffffffffffffffffffffffffffffffff0100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff7f02000000000000000000000000000000000000c000000000000000000000000027fe8c0b49f49507b9d4fe5968c9f49edfe5c9df277d433a07a0717ede97638d00000000000000000000000000000000ffffffffffffffffffffffffffffffff3a36e47291f4201faf137fab081d92295bce2d53be2c6ca68ba82c7faa9ce24100000000000000000000000000000000000000200000000000000000000000004661696c656420746f206368617267652067617300000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000004f766572666c6f7700000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c792062792074686520626f6f746c6f61646572000000000000000000000000000000000000000064000000800000000000000000000008010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000100a06e6f7420657175616c20746f20636861696e65644c6f677348617368000000007265636f6e7374727563746564436861696e65644c6f677348617368206973200000000000000000000000000000000000000084000000000000000000000000000007ffffffffffffffffffffffffffffffffffffffffffffffffffffffffff72abee45b59e344af8a6e520241c4744aff26ed411f4c4b00f8af09adada43ba6b656363616b3235362072657475726e656420696e76616c69642064617461004861736800000000000000000000000000000000000000000000000000000000206973206e6f7420657175616c20746f20636861696e65644d657373616765737265636f6e7374727563746564436861696e65644d657373616765734861736800000000000000000000000000000000000000a40000000000000000000000000000001f00000000000000000000000000000000000000000000000000000000706f000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000007368612072657475726e656420696e76616c696420646174610000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffff06ffffff000000000000000000000000000000000000000000000000000000007072000000000000000000000000000000000000000000000000000000000000707000000000000000000000000000000000000000000000000000000000000061696e65644c3142797465636f64657352657665616c44617461486173680000657665616c4461746148617368206973206e6f7420657175616c20746f2063687265636f6e7374727563746564436861696e65644c3142797465636f64657352ff0000000000000000000000000000000000000000000000000000000000000069736d61746368000000000000000000000000000000000000000000000000007374617465206469666620636f6d7072657373696f6e2076657273696f6e206d000000000000000000000000000000000000000000000000000000000007ef416006d8b500000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000003ffffffffe00000000000000000000000000000000000000000000000000000000001ffffe064617461206172726179000000000000000000000000000000000000000000004578747261206461746120696e2074686520746f74616c4c32546f4c315075624c31204d657373656e676572207075626461746120697320746f6f206c6f6e674e487b71000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000546f6f206d616e79204c322d3e4c31206c6f67730000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000400000080000000000000000054686973206d6574686f642072657175697265207468652063616c6c657220746f2062652073797374656d20636f6e74726163740000000000000000000000000000000000000000000000000000000000000084000000800000000000000000496e617070726f7072696174652063616c6c65720000000000000000000000000200000000000000000000000000000000000040000000a0000000000000000000000000000000000000000000000000000000000000000000000000ffffffd80200000000000000000000000000000000000020000000000000000000000000480d3c9f727b5e5c1203d4c61fb185d37f08e6b2dc5e9bbf98591b1a7addf57c00000000000000000000000000000000000000000000000000000000000000003bcca2165d1b42f8d351fb1411089dd7f5639a7d6e1ec51538da3ead741d4108", + "deployedBytecode": "0x0002000000000002000e000000000002000100000001035500000000030100190000006005300270000002420050019d0000008004000039000000400040043f00000242035001970000000102200190000000310000c13d000000040230008c000001250000413d000000000201043b000000e002200270000002440620009c000000390000213d000002470420009c000000710000613d000002480220009c000001250000c13d0000000002000416000000000202004b000001250000c13d000000040230008a000000600220008c000001250000413d0000000401100370000000000301043b000000000103004b0000000001000019000000010100c039000000000113004b000001250000c13d0000000002000411000002870120009c000000ec0000413d0000025d01000041000000800010043f0000002001000039000000840010043f0000003401000039000000a40010043f0000028901000041000000c40010043f0000028a01000041000000e40010043f0000028b0100004100000904000104300000000001000416000000000101004b000001250000c13d0000002001000039000001000010044300000120000004430000024301000041000009030001042e000002450620009c000000ae0000613d000002460220009c000001250000c13d0000000002000416000000000202004b000001250000c13d000000040230008a000000200220008c000001250000413d0000000402100370000000000202043b000002490620009c000001250000213d00000023062000390000024a07000041000000000836004b000000000800001900000000080780190000024a06600197000000000906004b00000000070080190000024a0660009c000000000708c019000000000607004b000001250000c13d0000000406200039000000000661034f000000000706043b000002490670009c000001250000213d00000024082000390000000002870019000000000323004b000001250000413d000000000900041400000000030004140000024b0630009c0000014a0000413d00000044014000390000025f0200004100000000002104350000002401400039000000080200003900000000002104350000025d0100004100000000001404350000000401400039000000200200003900000000002104350000024201000041000002420240009c000000000401801900000040014002100000025e011001c700000904000104300000000002000416000000000202004b000001250000c13d000000040230008a000000200220008c000001250000413d0000000002000411000080040220008c000000e20000c13d0000000401100370000000000201043b0000000301000039000d00000001001d000000000101041a000000a00010043f000e00000002001d000000c00020043f0000004001000039000000800010043f000000e001000039000000400010043f00000242010000410000000002000414000002420320009c0000000002018019000000c0012002100000028d011001c70000801002000039090208f80000040f0000000102200190000001250000613d000000000101043b0000000d02000029000000000012041b000000000100041300000242031001970000000e06000029000000e0016002700000ffff0210018f000000050120021000000004041001bf00000000514300a900000000544100d9000000000343004b0000019d0000c13d0000000102200270000000010320003900000007423000c9000000075420011a000000000343004b0000019d0000c13d00000000012100190000028e0210009c000001df0000413d000000400100043d00000044021000390000025f03000041000000000032043500000024021000390000000803000039000005fe0000013d0000000002000416000000000202004b000001250000c13d000000040230008a000000200220008c000001250000413d0000000402100370000000000202043b000002490420009c000001250000213d00000023042000390000024a05000041000000000634004b000000000600001900000000060580190000024a04400197000000000704004b00000000050080190000024a0440009c000000000506c019000000000405004b000001250000c13d0000000404200039000000000541034f000000000505043b000b00000005001d000002490550009c000001250000213d0000002402200039000a00000002001d0000000b02200029000000000232004b000001250000213d0000000002000411000080010220008c000001a30000c13d0000000b02000029000000040220008c000001250000413d0000002002400039000000000221034f000000000402043b000002620240009c0000029b0000413d0000025d01000041000000800010043f0000002001000039000000840010043f0000001401000039000000a40010043f0000028601000041000000e90000013d0000025d01000041000000800010043f0000002001000039000000840010043f0000001401000039000000a40010043f0000028c01000041000000c40010043f00000261010000410000090400010430000e00000003001d000d00000002001d0000025101000041000000800010043f00000242010000410000000002000414000002420320009c0000000002018019000000c00120021000000288011001c70000800b02000039090208f80000040f000000000301001900000060033002700000024203300197000000200430008c000000000403001900000020040080390000001f0540018f00000005064002720000010a0000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b000001020000413d000000000705004b000001190000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000001270000613d0000001f01400039000000600210018f00000080082001bf000000400080043f000000200130008c0000000e05000029000001250000413d000000800100043d0000ffff0310008c000001ab0000a13d00000000010000190000090400010430000000400200043d0000001f0430018f0000000505300272000001340000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000012c0000413d000000000604004b000001430000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f00000000001504350000024201000041000002420420009c000000000201801900000040012002100000006002300210000000000121019f0000090400010430000e00000009001d000d00000007001d000c00000008001d0000024204800197000000000141034f0000000002250049000002420220019700000000012103df000000c0023002100000024c022001970000024d022001c700000000012103af0000801002000039090208fd0000040f0000000003010019000000600330027000000242033001970000000102200190000001ea0000613d0000003f023000390000024e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000002490640009c000001db0000213d0000000105500190000001db0000c13d000000400040043f00000000043204360000001f053000390000000505500272000001780000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b000001700000413d000000000500004b0000017a0000613d0000001f0530018f00000005033002720000000e09000029000001870000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b0000017f0000413d000000000605004b000001960000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f00000000001304350000000001020433000000200110008c000005f80000c13d00000000040404330000000002000414000000000129004b000003ad0000813d000002840100004100000000001004350000001101000039000000040010043f000002850100004100000904000104300000025d01000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f0000026001000041000000e90000013d0000014003200039000000400030043f0000000000080435000000a003200039000b00000003001d00000000005304350000025504000041000000000305004b0000000004006019000000e003200039000e00000003001d0000000d090000290000000000930435000000c003200039000900000003001d000000000013043500000001030003670000002405300370000000000505043b000001200720003900000100022001bf000a00000002001d00000000005204350000004402300370000000000602043b000c00000007001d00000000006704350000000002080433000000f807200210000000400200043d0000002003200039000000000073043500000021072000390000000000470435000000f00110021000000022042000390000000000140435000000600190021000000024042000390000000000140435000000580120003900000000006104350000003801200039000000000051043500000058010000390000000000120435000002560120009c000002050000a13d000002840100004100000000001004350000004101000039000001a00000013d00000028011000390000000002100420000000400100043d000000000202004b000002880000c13d00000044021000390000025c03000041000000000032043500000024021000390000001403000039000005fe0000013d0000001f0430018f0000000502300272000001f50000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000001ee0000413d000000000504004b000002030000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f0000000000120435000000600130021000000904000104300000008001200039000000400010043f0000024201000041000002420430009c000000000301801900000040033002100000000002020433000002420420009c00000000020180190000006002200210000000000232019f0000000003000414000002420430009c0000000003018019000000c001300210000000000121019f00000250011001c70000801002000039000d00000008001d090208f80000040f0000000102200190000001250000613d000000000201043b000000400100043d0000004003100039000000000400041a000000000023043500000020021000390000000000420435000000400300003900000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f0000024203000041000002420420009c000000000203801900000040022002100000000001010433000002420410009c00000000010380190000006001100210000000000121019f0000000002000414000002420420009c0000000002038019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f0000000102200190000001250000613d000000000101043b000000000010041b0000000103000039000000000203041a000000010100008a000800000002001d000000000112004b0000019d0000613d00000008010000290000000101100039000000000013041b0000000d010000290000000001010433000000ff0110018f000000400200043d00000000011204360000000b040000290000000004040433000000000404004b0000000004000019000000010400c0390000000000410435000000090100002900000000010104330000ffff0110018f000000400420003900000000001404350000000e0100002900000000010104330000025401100197000000600420003900000000001404350000000a010000290000000001010433000000800420003900000000001404350000000c010000290000000001010433000000a00420003900000000001404350000024205000041000002420120009c00000000020580190000000001000414000002420410009c00000000010580190000004002200210000000c001100210000000000121019f00000257011001c70000800d020000390000025804000041090208f30000040f0000000101200190000001250000613d00000078010000390000000003100420000000400100043d000002420210009c000002420200004100000000020140190000004002200210000000000303004b000005060000c13d00000044031000390000025c0400004100000000004304350000002403100039000000140400003900000000004304350000025d0300004100000000003104350000000401100039000000200300003900000000003104350000025e012001c70000090400010430000000000061043500000242020000410000000003000414000002420430009c0000000003028019000002420410009c00000000010280190000004001100210000000c002300210000000000112019f0000028f011001c70000800d0200003900000001030000390000029004000041090208f30000040f0000000101200190000001250000613d0000000001000019000009030001042e000000000131034f000600000004001d000000e0064002700000026302000041000000400020043f0000080002000039000700000002001d000000800020043f000000a00200003900000000030000190000000504300210000000000441034f000000000404043b00000000024204360000000103300039000008000430008c000002a50000413d000000040200003900000006010000290000024d0110009c00000000080000190000030a0000813d000000000100041a000000000118004b000003980000c13d000d00000002001d0000000601000029000002670110009c000002c20000213d0000026801000041000000800200043d000000000262004b000003060000a13d0000000502600210000000a0022000390000000000120435000007ff0260008c0000000106600039000002b90000413d000900400000003d000880100000003d0000000701000029000600000001001d000700010010027800000000040000190000000101400210000000800200043d000000000312004b000003060000a13d00000001011001bf000000000212004b000003060000a13d0000000501100210000000a0011000390000000002010433000e00000004001d0000000601400210000000a001100039000c00000001001d0000000003010433000000400100043d0000004004100039000000000024043500000020021000390000000000320435000000090300002900000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f000002420320009c0000024204000041000000000204801900000040022002100000000001010433000002420310009c00000000010480190000006001100210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000000802000029090208f80000040f0000000102200190000001250000613d000000800200043d0000000e04000029000000000242004b000003060000a13d00000005024002100000000c02200069000000000101043b00000000001204350000000104400039000000070140006c000002c80000413d0000000601000029000000030110008c000002c40000213d000000800100043d000000000101004b0000050a0000c13d000002840100004100000000001004350000003201000039000001a00000013d0000000401000039000900590000009200000000070000190000000008000019000800000006001d0000005803100039000d00000003001d0000000b0230006c000001250000213d0000000a0210002900000000010004140000024203200197000000090420006c0000019d0000213d00000058022000390000000004000031000000000524004b0000019d0000413d000c00000008001d000e00000007001d0000000103300367000002420510009c000000a70000213d0000000002240049000002420220019700000000022303df000000c0011002100000024c011001970000024d011001c700000000011203af0000801002000039090208fd0000040f0000000003010019000000600330027000000242033001970000000102200190000004ce0000613d0000003f023000390000024e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000002490640009c000001db0000213d0000000105500190000001db0000c13d000000400040043f00000000043204360000001f0530003900000005055002720000034a0000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b000003420000413d000000000500004b0000034c0000613d0000000505300272000003570000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000034f0000413d0000001f03300190000003660000613d0000000505500210000000000151034f00000000055400190000000303300210000000000605043300000000063601cf000000000636022f000000000101043b0000010003300089000000000131022f00000000013101cf000000000161019f00000000001504350000000001020433000000200110008c0000000e030000290000000c05000029000005f80000c13d000000800100043d000000000131004b000003060000a13d00000000020404330000000501300210000000a0011000390000000000210435000000400100043d000000400310003900000000002304350000004002000039000000000221043600000000005204350000024f0310009c000001db0000213d0000006003100039000000400030043f000002420320009c0000024204000041000000000204801900000040022002100000000001010433000002420310009c00000000010480190000006001100210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f000000010220019000000008060000290000000e07000029000001250000613d000000000801043b0000000107700039000000000167004b0000000d0200002900000000010200190000030f0000413d000002b10000013d000000400100043d00000064021000390000026403000041000000000032043500000044021000390000026503000041000000000032043500000024021000390000003c0300003900000000003204350000025d0200004100000000002104350000000402100039000000200300003900000000003204350000024202000041000002420310009c0000000001028019000000400110021000000266011001c70000090400010430000800000002001d0000000201000039000b00000001001d000000000301041a000000400100043d0000004002100039000a00000004001d0000000000420435000000200210003900000000003204350000004003000039000900000003001d00000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f0000024204000041000002420320009c000000000204801900000040022002100000000001010433000002420310009c00000000010480190000006001100210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f0000000102200190000001250000613d000000000101043b0000000b02000029000000000012041b0000025101000041000000400400043d000b00000004001d00000000001404350000000001000414000002420210009c00000242030000410000000001038019000002420240009c00000000030440190000004002300210000000c001100210000000000121019f00000252011001c70000800b02000039090208f80000040f0000000b0a000029000000000301001900000060033002700000024203300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000003f70000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b000003ef0000413d00000000090a0019000000000705004b000004070000613d0000000506600210000000000761034f00000000066900190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000004e90000613d0000001f01400039000000600110018f0000000002910019000000000112004b00000000010000190000000101004039000700000002001d000002490220009c000001db0000213d0000000101100190000001db0000c13d0000000701000029000000400010043f000000200130008c000001250000413d00000000010904330000ffff0210008c000001250000213d0000000702000029000002530220009c000001db0000213d0000000703000029000000c002300039000000400020043f000000000400041000000254024001970000006005300039000500000005001d000000000025043500000020053000390000000102000039000b00000002001d000300000005001d0000000000250435000000a0023000390000000a07000029000600000002001d000000000072043500000080023000390000000008000411000400000002001d000000000082043500000000000304350000004002300039000200000002001d0000000000120435000000400200043d00000020032000390000000000030435000000210520003900000255060000410000000000650435000000f0011002100000002205200039000000000015043500000060014002100000002404200039000000000014043500000058012000390000000000710435000000580100003900000000001204350000003801200039000100000008001d0000000000810435000002560120009c000001db0000213d0000008001200039000000400010043f0000024201000041000002420430009c000000000301801900000040033002100000000002020433000002420420009c00000000020180190000006002200210000000000232019f0000000003000414000002420430009c0000000003018019000000c001300210000000000121019f00000250011001c70000801002000039090208f80000040f0000000102200190000001250000613d000000000201043b000000400100043d0000004003100039000000000400041a000000000023043500000020021000390000000000420435000000090300002900000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f0000024203000041000002420420009c000000000203801900000040022002100000000001010433000002420410009c00000000010380190000006001100210000000000121019f0000000002000414000002420420009c0000000002038019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f0000000102200190000001250000613d000000000101043b000000000010041b0000000b01000029000000000101041a000000010200008a000000000221004b0000019d0000613d00000001011000390000000b03000029000000000013041b00000007010000290000000001010433000000ff0110018f000000400200043d000000000112043600000003040000290000000004040433000000000404004b0000000004000019000000010400c0390000000000410435000000020100002900000000010104330000ffff0110018f0000004004200039000000000014043500000005010000290000000001010433000002540110019700000060042000390000000000140435000000040100002900000000010104330000008004200039000000000014043500000006010000290000000001010433000000a00420003900000000001404350000024201000041000002420420009c00000000020180190000000005000414000002420450009c00000000050180190000004001200210000000c002500210000000000112019f00000257011001c70000800d020000390000025804000041090208f30000040f00000001012001900000000d01000029000001250000613d0000005c021000390000000001000413000002420310019700000000412300a90000025902200197000002590410019700000000422400d9000000000223004b00000008030000290000019d0000c13d0000000e02300069000000a0031000390000000001230019000000000231004b0000000002000019000000010200403900000001022001900000019d0000c13d0000024b0210009c000006e00000413d000000400400043d000000600000013d0000001f0430018f0000000502300272000004d90000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000004d20000413d000000000504004b000004e70000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000090400010430000000400200043d0000001f0430018f0000000505300272000004f60000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000004ee0000413d000000000604004b000005050000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000001430000013d000000080300002900000000003104350000025b012001c7000009030001042e000000050100008a000800000001001d0000000d0110006b0000019d0000213d0000000d0100002900000004031000390000000b0130006c000001250000213d000000a00100043d000500000001001d0000000d020000290000000a012000290000000101100367000000000101043b0000024d0210009c0000000009000019000005620000813d0000000201000039000400000001001d000000000101041a000000000119004b0000060a0000c13d0000000002030019000000080120006c0000019d0000213d00000004032000390000000b0130006c000001250000213d0000000a012000290000000101100367000000000101043b0000024d0210009c00000000090000190000063d0000813d00000000050300190000000301000039000d00000001001d000000000101041a000000000119004b000006e50000c13d0000000b0150006c000003060000813d0000000a015000290000000102000367000000000312034f000000000303043b0000027a03300197000002550330009c000007380000c13d0000000004050019000000080340006c0000019d0000213d00000004034000390000000b0430006c000001250000213d0000000101100039000000000112034f000000000101043b0000000b0430006c000003060000813d000000e8011002700000000a03300029000000000432034f0000000503500039000c00000031001d0000000c0510006b00000000060000190000000106004039000000000504043b00000001046001900000019d0000c13d0000000c060000290000000b0460006c000001250000213d0000000c040000290000027d0440009c000007720000413d000000400100043d0000004402100039000002830300004100000000003204350000025d0200004100000000002104350000002402100039000000200300003900000000003204350000000402100039000006030000013d000700e00010027800000000080000190000000009000019000000080130006c0000019d0000213d00000004023000390000000b0120006c000001250000213d0000000a033000290000000101000367000000000331034f000000000303043b000000e0053002700000000007250019000000000357004b0000000003000019000000010300403900000001033001900000019d0000c13d0000000b0370006c000001250000213d0000000a04200029000002420340019700000000020004140000000004450019000000000554004b0000000005000019000000010500403900000001055001900000019d0000c13d0000000005000031000000000645004b0000019d0000413d000e00000009001d000c00000008001d000d00000007001d000002420620009c000000a70000213d000000000131034f0000000003450049000002420330019700000000013103df000000c0022002100000024c022001970000024d022001c700000000012103af0000801002000039090208fd0000040f0000000003010019000000600330027000000242033001970000000102200190000006220000613d0000003f023000390000024e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000002490640009c000001db0000213d0000000105500190000001db0000c13d000000400040043f00000000043204360000001f053000390000000505500272000005b20000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b000005aa0000413d000000000500004b000005b40000613d00000005053002720000000e09000029000005c00000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000005b80000413d0000001f03300190000005cf0000613d0000000505500210000000000151034f00000000055400190000000303300210000000000605043300000000063601cf000000000636022f000000000101043b0000010003300089000000000131022f00000000013101cf000000000161019f00000000001504350000000001020433000000200110008c000005f80000c13d0000000002040433000000400100043d0000004003100039000000000023043500000020021000390000000000920435000000090300002900000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f000002420320009c0000024204000041000000000204801900000040022002100000000001010433000002420310009c00000000010480190000006001100210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f00000001022001900000000d030000290000000c08000029000001250000613d000000000901043b0000000108800039000000070180006c000005650000413d0000051b0000013d000000400100043d00000044021000390000026903000041000000000032043500000024021000390000001f0300003900000000003204350000025d0200004100000000002104350000000402100039000000200300003900000000003204350000024202000041000002420310009c000000000102801900000040011002100000025e011001c70000090400010430000000400100043d00000084021000390000026a03000041000000000032043500000064021000390000026b03000041000000000032043500000044021000390000026c0300004100000000003204350000002402100039000000440300003900000000003204350000025d0200004100000000002104350000000402100039000000200300003900000000003204350000024202000041000002420310009c000000000102801900000040011002100000026d011001c700000904000104300000001f0430018f00000005023002720000062d0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000006260000413d000000000504004b0000063b0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000090400010430000600e00010027800000000080000190000000009000019000000080130006c0000019d0000213d00000004023000390000000b0120006c000001250000213d0000000a033000290000000101000367000000000331034f000000000303043b000000e00a30027000000000072a00190000000004a7004b0000000004000019000000010400403900000001044001900000019d0000c13d0000000b0470006c000001250000213d0000026e04300198000007420000c13d000002700430009c000007460000813d00000271033001980000074a0000613d0000000a042000290000024203400197000000000200041400000000044a00190000000005a4004b0000000005000019000000010500403900000001055001900000019d0000c13d0000000005000031000000000645004b0000019d0000413d000d0000000a001d000e00000009001d000700000008001d000c00000007001d000002420620009c000000a70000213d000000000131034f0000000003450049000002420330019700000000013103df000000c0022002100000024c022001970000024d022001c700000000012103af0000000202000039090208fd0000040f0000000003010019000000600330027000000242033001970000000102200190000007510000613d0000003f023000390000024e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000002490640009c000001db0000213d0000000105500190000001db0000c13d000000400040043f00000000043204360000001f0530003900000005055002720000000d0a000029000006950000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b0000068d0000413d000000000500004b000006970000613d00000005053002720000000e09000029000006a30000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000069b0000413d0000001f03300190000006b20000613d0000000505500210000000000151034f00000000055400190000000303300210000000000605043300000000063601cf000000000636022f000000000101043b0000010003300089000000000131022f00000000013101cf000000000161019f0000000000150435000000400100043d0000000002020433000000200220008c0000076c0000c13d00000000020404330000027302200197000000db03a002100000027403300197000000000223019f00000255022001c70000004003100039000000000023043500000020021000390000000000920435000000090300002900000000003104350000024f0310009c000001db0000213d0000006003100039000000400030043f000002420320009c0000024204000041000000000204801900000040022002100000000001010433000002420310009c00000000010480190000006001100210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000801002000039090208f80000040f00000001022001900000000c030000290000000708000029000001250000613d000000000901043b0000000108800039000000060180006c000006400000413d0000052c0000013d0000000002100420000000400100043d000000000202004b000006f20000c13d000001e40000013d000000400100043d00000084021000390000027703000041000000000032043500000064021000390000027803000041000000000032043500000044021000390000027903000041000000000032043500000024021000390000005e03000039000006160000013d000000200200003900000000022104360000000d0500002900000000005204350000001f0350018f00000040021000390000000c0400002900000001044003670000000505500272000007050000613d000000000600001900000005076002100000000008720019000000000774034f000000000707043b00000000007804350000000106600039000000000756004b000006fd0000413d000000000603004b000007140000613d0000000505500210000000000454034f00000000055200190000000303300210000000000605043300000000063601cf000000000636022f000000000404043b0000010003300089000000000434022f00000000033401cf000000000363019f00000000003504350000000d03000029000000000232001900000000000204350000005f02300039000000200300008a000000000232016f0000024204000041000002420310009c00000000010480190000004001100210000002420320009c00000000020480190000006002200210000000000121019f0000000002000414000002420320009c0000000002048019000000c002200210000000000112019f00000250011001c70000800d0200003900000003030000390000025a0400004100000001050000290000000a06000029090208f30000040f0000000101200190000001250000613d000000400100043d0000000a020000290000000000210435000002420210009c000002420100804100000040011002100000025b011001c7000009030001042e000000400100043d00000064021000390000027b03000041000000000032043500000044021000390000027c03000041000000000032043500000024021000390000002703000039000003a10000013d000000400100043d00000044021000390000026f030000410000074d0000013d000000400100043d000000440210003900000276030000410000074d0000013d000000400100043d00000044021000390000027503000041000000000032043500000024021000390000000403000029000005fe0000013d0000001f0430018f00000005023002720000075c0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000007550000413d000000000504004b0000076a0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001204350000006001300210000009040001043000000044021000390000027203000041000000000032043500000024021000390000001903000039000005fe0000013d0000000c0400002900000004064000390000000b0460006c000001250000213d0000000c070000290000000a04700029000000000442034f000000000804043b000000e00780027000000110947000c90000024d0880009c000007810000413d00000000987400d9000001100880008c0000019d0000c13d0000000009640019000900000009001d0000000b0890006c000001250000213d000000f805500270000000400a00043d0000004408a00039000000800900003900000000009804350000002408a0003900000000005804350000027e0500004100000000005a04350000000a066000290000008405a0003900000000004504350000000405a000390000000000750435000000000862034f0000001f0740018f000e0000000a001d000000a406a000390000000509400272000007a20000613d000000000a000019000000050ba00210000000000cb60019000000000bb8034f000000000b0b043b0000000000bc0435000000010aa00039000000000b9a004b0000079a0000413d0000000a03300029000000000a07004b000007b20000613d0000000509900210000000000898034f00000000099600190000000307700210000000000a090433000000000a7a01cf000000000a7a022f000000000808043b0000010007700089000000000878022f00000000077801cf0000000007a7019f0000000000790435000000000746001900000000000704350000001f044000390000027f04400197000000000646001900000000045600490000000e0500002900000064055000390000000000450435000000000432034f0000001f0310018f00000000021604360000000505100272000007c90000613d000000000600001900000005076002100000000008720019000000000774034f000000000707043b00000000007804350000000106600039000000000756004b000007c10000413d000000000603004b000007d80000613d0000000505500210000000000454034f00000000055200190000000303300210000000000605043300000000063601cf000000000636022f000000000404043b0000010003300089000000000434022f00000000033401cf000000000363019f0000000000350435000000000312001900000000000304350000001f0110003900000280011001970000000e04000029000000000141004900000000012100190000024202000041000002420340009c000000000302001900000000030440190000004003300210000002420410009c00000000010280190000006001100210000000000131019f0000000003000414000002420430009c0000000003028019000000c002300210000000000112019f0000800e02000039090208f30000040f000000000301001900000060033002700000024203300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000008010000613d000000000700001900000005087002100000000e09800029000000000881034f000000000808043b00000000008904350000000107700039000000000867004b000007f90000413d000000000705004b000008100000613d0000000506600210000000000761034f0000000e066000290000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000008360000613d0000001f01400039000000600210018f0000000e01200029000000000221004b00000000020000190000000102004039000002490410009c000001db0000213d0000000102200190000001db0000c13d000000400010043f000000200230008c000001250000413d00000009030000290000000b0230006c000008530000c13d0000000e010000290000000001010433000e00000001001d0000000501000029000000000010041d0000000a010000290000000c020000290902085c0000040f0000000102000039000000000012041d00000004010000290000000e03000029000000000031041d000000000000041b000000000002041b000000000001041b0000000d01000029000000000001041b0000000001000019000009030001042e000000400200043d0000001f0430018f0000000505300272000008430000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b0000083b0000413d000000000604004b000008520000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000001430000013d00000064021000390000028103000041000000000032043500000044021000390000028203000041000000000032043500000024021000390000002a03000039000003a10000013d00000000030004140000000004120019000000000224004b0000000005000019000000010500403900000242021001970000000101500190000008b50000c13d0000000001000031000000000541004b000008b50000413d00000001022003670000024b0530009c000008b90000813d0000000001410049000002420110019700000000011203df000000c0023002100000024c022001970000024d022001c700000000012103af0000801002000039090208fd0000040f0000000003010019000000600330027000000242033001970000000102200190000008c00000613d0000003f023000390000024e04200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000002490640009c000008db0000213d0000000105500190000008db0000c13d000000400040043f00000000043204360000001f053000390000000505500272000008930000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b0000088b0000413d000000000500004b000008950000613d0000001f0530018f0000000503300272000008a10000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b000008990000413d000000000605004b000008b00000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f00000000001304350000000001020433000000200110008c000008e10000c13d0000000001040433000000000001042d000002840100004100000000001004350000001101000039000008de0000013d000000400100043d00000044021000390000025f03000041000000000032043500000024021000390000000803000039000008e70000013d0000001f0430018f0000000502300272000008cb0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000008c40000413d000000000504004b000008d90000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000090400010430000002840100004100000000001004350000004101000039000000040010043f00000285010000410000090400010430000000400100043d00000044021000390000026903000041000000000032043500000024021000390000001f0300003900000000003204350000025d0200004100000000002104350000000402100039000000200300003900000000003204350000024202000041000002420310009c000000000102801900000040011002100000025e011001c70000090400010430000008f6002104210000000102000039000000000001042d0000000002000019000000000001042d000008fb002104230000000102000039000000000001042d0000000002000019000000000001042d00000900002104230000000102000039000000000001042d0000000002000019000000000001042d0000090200000432000009030001042e000009040001043000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000628b636d00000000000000000000000000000000000000000000000000000000628b636e0000000000000000000000000000000000000000000000000000000062f84b240000000000000000000000000000000000000000000000000000000039b34c6e0000000000000000000000000000000000000000000000000000000056079ac8000000000000000000000000000000000000000000000000ffffffffffffffff8000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000000000000ffffffff000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001ffffffe0000000000000000000000000000000000000000000000000ffffffffffffff9f02000000000000000000000000000000000000000000000000000000000000008ac84c0e000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff3f000000000000000000000000ffffffffffffffffffffffffffffffffffffffff0100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffff7f02000000000000000000000000000000000000c000000000000000000000000027fe8c0b49f49507b9d4fe5968c9f49edfe5c9df277d433a07a0717ede97638d00000000000000000000000000000000ffffffffffffffffffffffffffffffff3a36e47291f4201faf137fab081d92295bce2d53be2c6ca68ba82c7faa9ce24100000000000000000000000000000000000000200000000000000000000000004661696c656420746f206368617267652067617300000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000004f766572666c6f7700000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c792062792074686520626f6f746c6f61646572000000000000000000000000000000000000000064000000800000000000000000000008010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000100a06e6f7420657175616c20746f20636861696e65644c6f677348617368000000007265636f6e7374727563746564436861696e65644c6f677348617368206973200000000000000000000000000000000000000084000000000000000000000000000007ffffffffffffffffffffffffffffffffffffffffffffffffffffffffff72abee45b59e344af8a6e520241c4744aff26ed411f4c4b00f8af09adada43ba6b656363616b3235362072657475726e656420696e76616c69642064617461004861736800000000000000000000000000000000000000000000000000000000206973206e6f7420657175616c20746f20636861696e65644d657373616765737265636f6e7374727563746564436861696e65644d657373616765734861736800000000000000000000000000000000000000a40000000000000000000000000000001f00000000000000000000000000000000000000000000000000000000706f000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000007368612072657475726e656420696e76616c696420646174610000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffff06ffffff000000000000000000000000000000000000000000000000000000007072000000000000000000000000000000000000000000000000000000000000707000000000000000000000000000000000000000000000000000000000000061696e65644c3142797465636f64657352657665616c44617461486173680000657665616c4461746148617368206973206e6f7420657175616c20746f2063687265636f6e7374727563746564436861696e65644c3142797465636f64657352ff0000000000000000000000000000000000000000000000000000000000000069736d61746368000000000000000000000000000000000000000000000000007374617465206469666620636f6d7072657373696f6e2076657273696f6e206d000000000000000000000000000000000000000000000000000000000007ef416006d8b500000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000003ffffffffe00000000000000000000000000000000000000000000000000000000001ffffe064617461206172726179000000000000000000000000000000000000000000004578747261206461746120696e2074686520746f74616c4c32546f4c315075624c31204d657373656e676572207075626461746120697320746f6f206c6f6e674e487b71000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000024000000000000000000000000546f6f206d616e79204c322d3e4c31206c6f67730000000000000000000000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000400000080000000000000000054686973206d6574686f642072657175697265207468652063616c6c657220746f2062652073797374656d20636f6e74726163740000000000000000000000000000000000000000000000000000000000000084000000800000000000000000496e617070726f7072696174652063616c6c65720000000000000000000000000200000000000000000000000000000000000040000000a0000000000000000000000000000000000000000000000000000000000000000000000000ffffffd80200000000000000000000000000000000000020000000000000000000000000480d3c9f727b5e5c1203d4c61fb185d37f08e6b2dc5e9bbf98591b1a7addf57c00000000000000000000000000000000000000000000000000000000000000003bcca2165d1b42f8d351fb1411089dd7f5639a7d6e1ec51538da3ead741d4108", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/L2EthToken.json b/.test-node-subtree/src/deps/contracts/L2EthToken.json new file mode 100644 index 00000000..45b1bb34 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/L2EthToken.json @@ -0,0 +1,255 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "L2EthToken", + "sourceName": "cache-zk/solpp-generated-contracts/L2EthToken.sol", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "account", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "amount", + "type": "uint256" + } + ], + "name": "Mint", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "from", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "to", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "value", + "type": "uint256" + } + ], + "name": "Transfer", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "_l2Sender", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "_l1Receiver", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "_amount", + "type": "uint256" + } + ], + "name": "Withdrawal", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "_l2Sender", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "_l1Receiver", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "_amount", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "_additionalData", + "type": "bytes" + } + ], + "name": "WithdrawalWithMessage", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_account", + "type": "uint256" + } + ], + "name": "balanceOf", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "decimals", + "outputs": [ + { + "internalType": "uint8", + "name": "", + "type": "uint8" + } + ], + "stateMutability": "pure", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_account", + "type": "address" + }, + { + "internalType": "uint256", + "name": "_amount", + "type": "uint256" + } + ], + "name": "mint", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "pure", + "type": "function" + }, + { + "inputs": [], + "name": "symbol", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "pure", + "type": "function" + }, + { + "inputs": [], + "name": "totalSupply", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_from", + "type": "address" + }, + { + "internalType": "address", + "name": "_to", + "type": "address" + }, + { + "internalType": "uint256", + "name": "_amount", + "type": "uint256" + } + ], + "name": "transferFromTo", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_l1Receiver", + "type": "address" + } + ], + "name": "withdraw", + "outputs": [], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_l1Receiver", + "type": "address" + }, + { + "internalType": "bytes", + "name": "_additionalData", + "type": "bytes" + } + ], + "name": "withdrawWithMessage", + "outputs": [], + "stateMutability": "payable", + "type": "function" + } + ], + "bytecode": "0x00050000000000020000008003000039000000400030043f00000000030100190000006003300270000000d8033001970000000102200190000000240000c13d000000040230008c0000030d0000413d000000000201043b000000e002200270000000da0420009c0000002c0000a13d000000db0420009c000000380000a13d000000dc0420009c000000b20000613d000000dd0420009c000002070000613d000000de0220009c0000030d0000c13d0000000002000416000000000202004b0000030d0000c13d000000040230008a000000200220008c0000030d0000413d0000000401100370000000000101043b000000e6011001970000000000100435000000200000043f0000000001000019035b033f0000040f000000360000013d0000000001000416000000000101004b0000030d0000c13d000000200100003900000100001004430000012000000443000000d9010000410000035c0001042e000000e10420009c0000007a0000213d000000e40120009c000001c30000613d000000e50120009c0000030d0000c13d0000000001000416000000000101004b0000030d0000c13d0000000101000039000000000101041a000002040000013d000000df0420009c000001cc0000613d000000e00220009c0000030d0000c13d0000000002000416000000000202004b0000030d0000c13d000000040230008a000000600220008c0000030d0000413d0000000402100370000000000402043b000000e60240009c0000030d0000213d0000002402100370000000000202043b000000e605200197000000e60220009c0000030d0000213d0000004401100370000000000101043b000400000001001d0000000001000411000080010210008c000000550000613d000080060210008c000000550000613d000080090110008c000002960000c13d0000000000400435000000200000043f000000d8010000410000000002000414000000d80320009c0000000002018019000000c001200210000000ec011001c70000801002000039000500000004001d000300000005001d035b03560000040f000000050300002900000001022001900000030d0000613d000000000101043b000000000201041a000000040120006c000002c50000813d000000400100043d0000004402100039000000f303000041000000000032043500000024021000390000001f030000390000000000320435000000f4020000410000000000210435000000040210003900000020030000390000000000320435000000d802000041000000d80310009c00000000010280190000004001100210000000f5011001c70000035d00010430000000e20420009c000002000000613d000000e30220009c0000030d0000c13d0000000002000416000000000202004b0000030d0000c13d000000040230008a000000400220008c0000030d0000413d0000000402100370000000000402043b000000e60240009c0000030d0000213d0000002401100370000000000501043b0000000001000411000080010110008c0000021c0000c13d0000000101000039000000000301041a0000000002530019000000000332004b000000000300001900000001030040390000000103300190000000ae0000c13d000400000005001d000000000021041b0000000000400435000000200000043f000000d8010000410000000002000414000000d80320009c0000000002018019000000c001200210000000ec011001c70000801002000039000500000004001d035b03560000040f000000050500002900000001022001900000030d0000613d000000000101043b000000000301041a00000004040000290000000002430019000000000332004b000000000300001900000001030040390000000103300190000002f80000613d000000fb0100004100000000001004350000001101000039000001fd0000013d000000040230008a000000400220008c0000030d0000413d0000000402100370000000000802043b000000e60280009c0000030d0000213d0000002402100370000000000402043b000000ea0240009c0000030d0000213d0000002302400039000000eb05000041000000000632004b00000000060000190000000006058019000000eb02200197000000000702004b0000000005008019000000eb0220009c000000000506c019000000000205004b0000030d0000c13d0000000405400039000000000251034f000000000202043b000000ea0620009c000001fa0000213d000000bf06200039000000200900008a000000000696016f000000ea0760009c000001fa0000213d000000400060043f000000800020043f00000000042400190000002404400039000000000334004b0000030d0000213d0000002003500039000000000131034f0000001f0320018f0000000504200272000000e70000613d00000000050000190000000506500210000000000761034f000000000707043b000000a00660003900000000007604350000000105500039000000000645004b000000df0000413d000400000009001d000500000008001d000000000503004b000000f80000613d0000000504400210000000000141034f0000000303300210000000a004400039000000000504043300000000053501cf000000000535022f000000000101043b0000010003300089000000000131022f00000000013101cf000000000151019f0000000000140435000000a00120003900000000000104350000000001000416000300000001001d00000000010004100000000000100435000000200000043f000000d8010000410000000002000414000000d80320009c0000000002018019000000c001200210000000ec011001c70000801002000039035b03560000040f0000000102200190000000050400002900000004070000290000030d0000613d000000000101043b000000000201041a00000003090000290000000002920049000000000021041b0000000101000039000000000201041a0000000002920049000000000021041b000000ed02000041000000400100043d000000200310003900000000002304350000006002400210000000240310003900000000002304350000000008000411000000600280021000000058031000390000000000230435000000380210003900000000009204350000006c03100039000000800200043d000000000402004b0000012d0000613d00000000040000190000000005340019000000a006400039000000000606043300000000006504350000002004400039000000000524004b000001260000413d000000000332001900000000000304350000004c0320003900000000003104350000008b02200039000000000272016f000000000a12001900000000022a004b00000000020000190000000102004039000000ea03a0009c000001fa0000213d0000000102200190000001fa0000c13d000100000008001d0000004000a0043f000000ee0200004100000000002a04350000000402a000390000002003000039000000000032043500000000020104330000002403a0003900000000002304350000004403a00039000000000402004b000001500000613d000000000400001900000000053400190000002004400039000000000614001900000000060604330000000000650435000000000524004b000001490000413d000000000132001900000000000104350000001f01200039000000000171016f000000d802000041000000d803a0009c000000000302001900000000030a401900000040033002100000004401100039000000d80410009c00000000010280190000006001100210000000000131019f0000000003000414000000d80430009c0000000003028019000000c002300210000000000112019f000080080200003900020000000a001d035b03510000040f000000020a00002900000000030100190000006003300270000000d803300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000001790000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b000001710000413d000000000705004b000001880000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f000000000056043500000001022001900000030f0000613d0000001f01400039000000600210018f0000000001a20019000000000221004b00000000020000190000000102004039000000ea0410009c00000005040000290000000305000029000001fa0000213d0000000102200190000001fa0000c13d000000400010043f000000200230008c0000030d0000413d00000020021000390000004003000039000000000032043500000000005104350000004003100039000000800200043d00000000002304350000006003100039000000e606400197000000000402004b000001ac0000613d00000000040000190000000005340019000000a007400039000000000707043300000000007504350000002004400039000000000524004b000001a50000413d000000000332001900000000000304350000007f02200039000000040220017f000000d803000041000000d80410009c00000000010380190000004001100210000000d80420009c00000000020380190000006002200210000000000112019f0000000002000414000000d80420009c0000000002038019000000c002200210000000000112019f000000ef011001c70000800d020000390000000303000039000000f0040000410000000105000029000003080000013d0000000001000416000000000101004b0000030d0000c13d000000c001000039000000400010043f0000000501000039000000800010043f00000100010000410000020f0000013d000000040230008a000000200220008c0000030d0000413d0000000401100370000000000401043b000000e60140009c0000030d0000213d0000000001000416000400000001001d00000000010004100000000000100435000000200000043f000000d8010000410000000002000414000000d80320009c0000000002018019000000c001200210000000ec011001c70000801002000039000500000004001d035b03560000040f000000050400002900000001022001900000030d0000613d000000000101043b000000000201041a00000004050000290000000002520049000000000021041b0000000101000039000000000201041a0000000002520049000000000021041b000000ed02000041000000400100043d000000200310003900000000002304350000006002400210000000240310003900000000002304350000003802100039000000000052043500000038020000390000000000210435000000f90210009c000002260000413d000000fb0100004100000000001004350000004101000039000000040010043f000000fc010000410000035d000104300000000001000416000000000101004b0000030d0000c13d0000001201000039000000800010043f000000e7010000410000035c0001042e0000000001000416000000000101004b0000030d0000c13d000000c001000039000000400010043f0000000301000039000000800010043f000000e801000041000000a00010043f0000002001000039000000c00010043f0000008001000039000000e002000039035b032c0000040f000000c00110008a000000d802000041000000d80310009c00000000010280190000006001100210000000e9011001c70000035c0001042e000000f401000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f000000fd01000041000000c40010043f000000fe010000410000035d000104300000006007100039000000400070043f000000ee020000410000000000270435000000640210003900000020030000390000000000320435000000840310003900000000020104330000000000230435000000a403100039000000000402004b0000023b0000613d000000000400001900000000053400190000002004400039000000000614001900000000060604330000000000650435000000000524004b000002340000413d000000000132001900000000000104350000001f01200039000000200200008a000000000121016f000000d802000041000000d80370009c0000000003020019000000000307401900000040033002100000004401100039000000d80410009c00000000010280190000006001100210000000000131019f0000000003000414000000d80430009c0000000003028019000000c002300210000000000112019f0000800802000039000300000007001d035b03510000040f000000030a00002900000000030100190000006003300270000000d803300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000002650000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b0000025d0000413d000000000705004b000002740000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000002a20000613d0000001f01400039000000600210018f0000000001a20019000000000221004b00000000020000190000000102004039000000ea0410009c00000005050000290000000404000029000001fa0000213d0000000102200190000001fa0000c13d000000400010043f000000200230008c0000030d0000413d0000000000410435000000d8020000410000000003000414000000d80430009c0000000003028019000000d80410009c00000000010280190000004001100210000000c002300210000000000112019f000000f1011001c7000000e6065001970000800d0200003900000003030000390000000005000411000000fa04000041000003080000013d000000f401000041000000800010043f0000002001000039000000840010043f0000003e01000039000000a40010043f000000f601000041000000c40010043f000000f701000041000000e40010043f000000f8010000410000035d00010430000000400200043d0000001f0430018f0000000505300272000002af0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000002a70000413d000000000604004b000002be0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000000d801000041000000d80420009c000000000201801900000040012002100000006002300210000000000121019f0000035d00010430000200000002001d0000000000300435000000200000043f000000d8030000410000000001000414000000d80210009c0000000001038019000000c001100210000000ec011001c70000801002000039035b03560000040f000000030300002900000001022001900000030d0000613d0000000204000029000000040240006a000000000101043b000000000021041b00000000003004350000000001000414000000d80210009c000000d801008041000000c001100210000000ec011001c70000801002000039035b03560000040f0000000306000029000000050500002900000001022001900000030d0000613d000000000101043b000000000201041a00000004030000290000000002320019000000000021041b000000400100043d0000000000310435000000d8020000410000000003000414000000d80430009c0000000003028019000000d80410009c00000000010280190000004001100210000000c002300210000000000112019f000000f1011001c70000800d020000390000000303000039000000f204000041000003080000013d000000000021041b000000400100043d0000000000410435000000d8020000410000000003000414000000d80430009c0000000003028019000000d80410009c00000000010280190000004001100210000000c002300210000000000112019f000000f1011001c70000800d020000390000000203000039000000ff04000041035b03510000040f00000001012001900000030d0000613d00000000010000190000035c0001042e00000000010000190000035d00010430000000400200043d0000001f0430018f00000005053002720000031c0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000003140000413d000000000604004b0000032b0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000002be0000013d00000000030104330000000002320436000000000403004b000003380000613d000000000400001900000000052400190000002004400039000000000614001900000000060604330000000000650435000000000534004b000003310000413d000000000123001900000000000104350000001f01300039000000200300008a000000000131016f0000000001120019000000000001042d000000d802000041000000d80310009c00000000010280190000000003000414000000d80430009c0000000003028019000000c0023002100000004001100210000000000121019f000000ec011001c70000801002000039035b03560000040f00000001022001900000034f0000613d000000000101043b000000000001042d00000000010000190000035d0001043000000354002104210000000102000039000000000001042d0000000002000019000000000001042d00000359002104230000000102000039000000000001042d0000000002000019000000000001042d0000035b000004320000035c0001042e0000035d000104300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff00000002000000000000000000000000000000400000010000000000000000000000000000000000000000000000000000000000000000000000000051cff8d80000000000000000000000000000000000000000000000000000000084bc3eaf0000000000000000000000000000000000000000000000000000000084bc3eb00000000000000000000000000000000000000000000000000000000095d89b41000000000000000000000000000000000000000000000000000000009cc7f7080000000000000000000000000000000000000000000000000000000051cff8d900000000000000000000000000000000000000000000000000000000579952fc00000000000000000000000000000000000000000000000000000000313ce56600000000000000000000000000000000000000000000000000000000313ce5670000000000000000000000000000000000000000000000000000000040c10f190000000000000000000000000000000000000000000000000000000006fdde030000000000000000000000000000000000000000000000000000000018160ddd000000000000000000000000ffffffffffffffffffffffffffffffffffffffff000000000000000000000000000000000000002000000080000000000000000045544800000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000c00000000000000000000000000000000000000000000000000000000000000000ffffffffffffffff800000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000400000000000000000000000006c0960f90000000000000000000000000000000000000000000000000000000062f84b24000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000c405fe8958410bbaf0c73b7a0c3e20859e86ca168a4c9b0def9c54d2555a306b0200000000000000000000000000000000000020000000000000000000000000ddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef5472616e7366657220616d6f756e7420657863656564732062616c616e63650008c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000004f6e6c792073797374656d20636f6e7472616374732077697468207370656369616c206163636573732063616e2063616c6c2074686973206d6574686f6400000000000000000000000000000000000000000084000000800000000000000000000000000000000000000000000000000000000000000000ffffffffffffffa02717ead6b9200dd235aad468c9809ea400fe33ac69b5bfaa6d3e90fc922b63984e487b7100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000000000000000000000043616c6c61626c65206f6e6c792062792074686520626f6f746c6f616465720000000000000000000000000000000000000000640000008000000000000000000f6798a560793a54c3bcfe86a93cde1e73087d944c0ea20544137d412139688545746865720000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000a7bdb77c992270c20fc1aeec0e9de8a46dab1207152ee7b2222c97279865945c", + "deployedBytecode": "0x00050000000000020000008003000039000000400030043f00000000030100190000006003300270000000d8033001970000000102200190000000240000c13d000000040230008c0000030d0000413d000000000201043b000000e002200270000000da0420009c0000002c0000a13d000000db0420009c000000380000a13d000000dc0420009c000000b20000613d000000dd0420009c000002070000613d000000de0220009c0000030d0000c13d0000000002000416000000000202004b0000030d0000c13d000000040230008a000000200220008c0000030d0000413d0000000401100370000000000101043b000000e6011001970000000000100435000000200000043f0000000001000019035b033f0000040f000000360000013d0000000001000416000000000101004b0000030d0000c13d000000200100003900000100001004430000012000000443000000d9010000410000035c0001042e000000e10420009c0000007a0000213d000000e40120009c000001c30000613d000000e50120009c0000030d0000c13d0000000001000416000000000101004b0000030d0000c13d0000000101000039000000000101041a000002040000013d000000df0420009c000001cc0000613d000000e00220009c0000030d0000c13d0000000002000416000000000202004b0000030d0000c13d000000040230008a000000600220008c0000030d0000413d0000000402100370000000000402043b000000e60240009c0000030d0000213d0000002402100370000000000202043b000000e605200197000000e60220009c0000030d0000213d0000004401100370000000000101043b000400000001001d0000000001000411000080010210008c000000550000613d000080060210008c000000550000613d000080090110008c000002960000c13d0000000000400435000000200000043f000000d8010000410000000002000414000000d80320009c0000000002018019000000c001200210000000ec011001c70000801002000039000500000004001d000300000005001d035b03560000040f000000050300002900000001022001900000030d0000613d000000000101043b000000000201041a000000040120006c000002c50000813d000000400100043d0000004402100039000000f303000041000000000032043500000024021000390000001f030000390000000000320435000000f4020000410000000000210435000000040210003900000020030000390000000000320435000000d802000041000000d80310009c00000000010280190000004001100210000000f5011001c70000035d00010430000000e20420009c000002000000613d000000e30220009c0000030d0000c13d0000000002000416000000000202004b0000030d0000c13d000000040230008a000000400220008c0000030d0000413d0000000402100370000000000402043b000000e60240009c0000030d0000213d0000002401100370000000000501043b0000000001000411000080010110008c0000021c0000c13d0000000101000039000000000301041a0000000002530019000000000332004b000000000300001900000001030040390000000103300190000000ae0000c13d000400000005001d000000000021041b0000000000400435000000200000043f000000d8010000410000000002000414000000d80320009c0000000002018019000000c001200210000000ec011001c70000801002000039000500000004001d035b03560000040f000000050500002900000001022001900000030d0000613d000000000101043b000000000301041a00000004040000290000000002430019000000000332004b000000000300001900000001030040390000000103300190000002f80000613d000000fb0100004100000000001004350000001101000039000001fd0000013d000000040230008a000000400220008c0000030d0000413d0000000402100370000000000802043b000000e60280009c0000030d0000213d0000002402100370000000000402043b000000ea0240009c0000030d0000213d0000002302400039000000eb05000041000000000632004b00000000060000190000000006058019000000eb02200197000000000702004b0000000005008019000000eb0220009c000000000506c019000000000205004b0000030d0000c13d0000000405400039000000000251034f000000000202043b000000ea0620009c000001fa0000213d000000bf06200039000000200900008a000000000696016f000000ea0760009c000001fa0000213d000000400060043f000000800020043f00000000042400190000002404400039000000000334004b0000030d0000213d0000002003500039000000000131034f0000001f0320018f0000000504200272000000e70000613d00000000050000190000000506500210000000000761034f000000000707043b000000a00660003900000000007604350000000105500039000000000645004b000000df0000413d000400000009001d000500000008001d000000000503004b000000f80000613d0000000504400210000000000141034f0000000303300210000000a004400039000000000504043300000000053501cf000000000535022f000000000101043b0000010003300089000000000131022f00000000013101cf000000000151019f0000000000140435000000a00120003900000000000104350000000001000416000300000001001d00000000010004100000000000100435000000200000043f000000d8010000410000000002000414000000d80320009c0000000002018019000000c001200210000000ec011001c70000801002000039035b03560000040f0000000102200190000000050400002900000004070000290000030d0000613d000000000101043b000000000201041a00000003090000290000000002920049000000000021041b0000000101000039000000000201041a0000000002920049000000000021041b000000ed02000041000000400100043d000000200310003900000000002304350000006002400210000000240310003900000000002304350000000008000411000000600280021000000058031000390000000000230435000000380210003900000000009204350000006c03100039000000800200043d000000000402004b0000012d0000613d00000000040000190000000005340019000000a006400039000000000606043300000000006504350000002004400039000000000524004b000001260000413d000000000332001900000000000304350000004c0320003900000000003104350000008b02200039000000000272016f000000000a12001900000000022a004b00000000020000190000000102004039000000ea03a0009c000001fa0000213d0000000102200190000001fa0000c13d000100000008001d0000004000a0043f000000ee0200004100000000002a04350000000402a000390000002003000039000000000032043500000000020104330000002403a0003900000000002304350000004403a00039000000000402004b000001500000613d000000000400001900000000053400190000002004400039000000000614001900000000060604330000000000650435000000000524004b000001490000413d000000000132001900000000000104350000001f01200039000000000171016f000000d802000041000000d803a0009c000000000302001900000000030a401900000040033002100000004401100039000000d80410009c00000000010280190000006001100210000000000131019f0000000003000414000000d80430009c0000000003028019000000c002300210000000000112019f000080080200003900020000000a001d035b03510000040f000000020a00002900000000030100190000006003300270000000d803300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000001790000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b000001710000413d000000000705004b000001880000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f000000000056043500000001022001900000030f0000613d0000001f01400039000000600210018f0000000001a20019000000000221004b00000000020000190000000102004039000000ea0410009c00000005040000290000000305000029000001fa0000213d0000000102200190000001fa0000c13d000000400010043f000000200230008c0000030d0000413d00000020021000390000004003000039000000000032043500000000005104350000004003100039000000800200043d00000000002304350000006003100039000000e606400197000000000402004b000001ac0000613d00000000040000190000000005340019000000a007400039000000000707043300000000007504350000002004400039000000000524004b000001a50000413d000000000332001900000000000304350000007f02200039000000040220017f000000d803000041000000d80410009c00000000010380190000004001100210000000d80420009c00000000020380190000006002200210000000000112019f0000000002000414000000d80420009c0000000002038019000000c002200210000000000112019f000000ef011001c70000800d020000390000000303000039000000f0040000410000000105000029000003080000013d0000000001000416000000000101004b0000030d0000c13d000000c001000039000000400010043f0000000501000039000000800010043f00000100010000410000020f0000013d000000040230008a000000200220008c0000030d0000413d0000000401100370000000000401043b000000e60140009c0000030d0000213d0000000001000416000400000001001d00000000010004100000000000100435000000200000043f000000d8010000410000000002000414000000d80320009c0000000002018019000000c001200210000000ec011001c70000801002000039000500000004001d035b03560000040f000000050400002900000001022001900000030d0000613d000000000101043b000000000201041a00000004050000290000000002520049000000000021041b0000000101000039000000000201041a0000000002520049000000000021041b000000ed02000041000000400100043d000000200310003900000000002304350000006002400210000000240310003900000000002304350000003802100039000000000052043500000038020000390000000000210435000000f90210009c000002260000413d000000fb0100004100000000001004350000004101000039000000040010043f000000fc010000410000035d000104300000000001000416000000000101004b0000030d0000c13d0000001201000039000000800010043f000000e7010000410000035c0001042e0000000001000416000000000101004b0000030d0000c13d000000c001000039000000400010043f0000000301000039000000800010043f000000e801000041000000a00010043f0000002001000039000000c00010043f0000008001000039000000e002000039035b032c0000040f000000c00110008a000000d802000041000000d80310009c00000000010280190000006001100210000000e9011001c70000035c0001042e000000f401000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f000000fd01000041000000c40010043f000000fe010000410000035d000104300000006007100039000000400070043f000000ee020000410000000000270435000000640210003900000020030000390000000000320435000000840310003900000000020104330000000000230435000000a403100039000000000402004b0000023b0000613d000000000400001900000000053400190000002004400039000000000614001900000000060604330000000000650435000000000524004b000002340000413d000000000132001900000000000104350000001f01200039000000200200008a000000000121016f000000d802000041000000d80370009c0000000003020019000000000307401900000040033002100000004401100039000000d80410009c00000000010280190000006001100210000000000131019f0000000003000414000000d80430009c0000000003028019000000c002300210000000000112019f0000800802000039000300000007001d035b03510000040f000000030a00002900000000030100190000006003300270000000d803300197000000200430008c000000000403001900000020040080390000001f0540018f0000000506400272000002650000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b0000025d0000413d000000000705004b000002740000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f00000000005604350000000102200190000002a20000613d0000001f01400039000000600210018f0000000001a20019000000000221004b00000000020000190000000102004039000000ea0410009c00000005050000290000000404000029000001fa0000213d0000000102200190000001fa0000c13d000000400010043f000000200230008c0000030d0000413d0000000000410435000000d8020000410000000003000414000000d80430009c0000000003028019000000d80410009c00000000010280190000004001100210000000c002300210000000000112019f000000f1011001c7000000e6065001970000800d0200003900000003030000390000000005000411000000fa04000041000003080000013d000000f401000041000000800010043f0000002001000039000000840010043f0000003e01000039000000a40010043f000000f601000041000000c40010043f000000f701000041000000e40010043f000000f8010000410000035d00010430000000400200043d0000001f0430018f0000000505300272000002af0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000002a70000413d000000000604004b000002be0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000000d801000041000000d80420009c000000000201801900000040012002100000006002300210000000000121019f0000035d00010430000200000002001d0000000000300435000000200000043f000000d8030000410000000001000414000000d80210009c0000000001038019000000c001100210000000ec011001c70000801002000039035b03560000040f000000030300002900000001022001900000030d0000613d0000000204000029000000040240006a000000000101043b000000000021041b00000000003004350000000001000414000000d80210009c000000d801008041000000c001100210000000ec011001c70000801002000039035b03560000040f0000000306000029000000050500002900000001022001900000030d0000613d000000000101043b000000000201041a00000004030000290000000002320019000000000021041b000000400100043d0000000000310435000000d8020000410000000003000414000000d80430009c0000000003028019000000d80410009c00000000010280190000004001100210000000c002300210000000000112019f000000f1011001c70000800d020000390000000303000039000000f204000041000003080000013d000000000021041b000000400100043d0000000000410435000000d8020000410000000003000414000000d80430009c0000000003028019000000d80410009c00000000010280190000004001100210000000c002300210000000000112019f000000f1011001c70000800d020000390000000203000039000000ff04000041035b03510000040f00000001012001900000030d0000613d00000000010000190000035c0001042e00000000010000190000035d00010430000000400200043d0000001f0430018f00000005053002720000031c0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000003140000413d000000000604004b0000032b0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000002be0000013d00000000030104330000000002320436000000000403004b000003380000613d000000000400001900000000052400190000002004400039000000000614001900000000060604330000000000650435000000000534004b000003310000413d000000000123001900000000000104350000001f01300039000000200300008a000000000131016f0000000001120019000000000001042d000000d802000041000000d80310009c00000000010280190000000003000414000000d80430009c0000000003028019000000c0023002100000004001100210000000000121019f000000ec011001c70000801002000039035b03560000040f00000001022001900000034f0000613d000000000101043b000000000001042d00000000010000190000035d0001043000000354002104210000000102000039000000000001042d0000000002000019000000000001042d00000359002104230000000102000039000000000001042d0000000002000019000000000001042d0000035b000004320000035c0001042e0000035d000104300000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff00000002000000000000000000000000000000400000010000000000000000000000000000000000000000000000000000000000000000000000000051cff8d80000000000000000000000000000000000000000000000000000000084bc3eaf0000000000000000000000000000000000000000000000000000000084bc3eb00000000000000000000000000000000000000000000000000000000095d89b41000000000000000000000000000000000000000000000000000000009cc7f7080000000000000000000000000000000000000000000000000000000051cff8d900000000000000000000000000000000000000000000000000000000579952fc00000000000000000000000000000000000000000000000000000000313ce56600000000000000000000000000000000000000000000000000000000313ce5670000000000000000000000000000000000000000000000000000000040c10f190000000000000000000000000000000000000000000000000000000006fdde030000000000000000000000000000000000000000000000000000000018160ddd000000000000000000000000ffffffffffffffffffffffffffffffffffffffff000000000000000000000000000000000000002000000080000000000000000045544800000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000c00000000000000000000000000000000000000000000000000000000000000000ffffffffffffffff800000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000400000000000000000000000006c0960f90000000000000000000000000000000000000000000000000000000062f84b24000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000c405fe8958410bbaf0c73b7a0c3e20859e86ca168a4c9b0def9c54d2555a306b0200000000000000000000000000000000000020000000000000000000000000ddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef5472616e7366657220616d6f756e7420657863656564732062616c616e63650008c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000004f6e6c792073797374656d20636f6e7472616374732077697468207370656369616c206163636573732063616e2063616c6c2074686973206d6574686f6400000000000000000000000000000000000000000084000000800000000000000000000000000000000000000000000000000000000000000000ffffffffffffffa02717ead6b9200dd235aad468c9809ea400fe33ac69b5bfaa6d3e90fc922b63984e487b7100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000000000000000000000043616c6c61626c65206f6e6c792062792074686520626f6f746c6f616465720000000000000000000000000000000000000000640000008000000000000000000f6798a560793a54c3bcfe86a93cde1e73087d944c0ea20544137d412139688545746865720000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000a7bdb77c992270c20fc1aeec0e9de8a46dab1207152ee7b2222c97279865945c", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/ModExp.yul.zbin b/.test-node-subtree/src/deps/contracts/ModExp.yul.zbin new file mode 100644 index 00000000..84702c5d Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/ModExp.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/MsgValueSimulator.json b/.test-node-subtree/src/deps/contracts/MsgValueSimulator.json new file mode 100644 index 00000000..d4d55f67 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/MsgValueSimulator.json @@ -0,0 +1,16 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "MsgValueSimulator", + "sourceName": "cache-zk/solpp-generated-contracts/MsgValueSimulator.sol", + "abi": [ + { + "stateMutability": "nonpayable", + "type": "fallback" + } + ], + "bytecode": "0x000200000000000200060000000000020001000000010355000000000601001900000060066002700000004b0060019d0000008007000039000000400070043f0000004b09600197000000000800041600000001072001900000001f0000c13d000000000708004b000000690000c13d0000000202200190000000260000c13d00000000020004110000004d0220009c000000260000413d0000005a01000041000000800010043f0000002001000039000000840010043f0000002401000039000000a40010043f0000005e01000041000000c40010043f0000005f01000041000000e40010043f00000060010000410000012a00010430000000000108004b000000690000c13d0000002001000039000001000010044300000120000004430000004c01000041000001290001042e0000004e024001970000000004000410000000000442004b000000340000c13d0000005a01000041000000800010043f0000002001000039000000840010043f0000001e01000039000000a40010043f0000005c01000041000000c40010043f0000005d010000410000012a00010430000000000403004b00000000080004110000000007090019000000400000c13d00000000000304170000000003000414000000000497004b0000006b0000813d000000570100004100000000001004350000001101000039000000ff0000013d000300000009001d000500000005001d000600000006001d0000004f01000041000000a00010043f000100000008001d0000004e01800197000000a40010043f000200000002001d000000c40020043f000400000003001d000000e40030043f0000006401000039000000800010043f0000012001000039000000400010043f0000004b0100004100000000020004140000004b0320009c0000000002018019000000c00120021000000050011001c70000800a020000390128011d0000040f000000000301001900000060033002700000004b053001980000007f0000c13d00000001012001900000000606000029000000050500002900000004030000290000000309000029000000690000613d000000530130009c000000020200002900000001080000290000006d0000213d00000001010003670000000007000031000000380000013d00000000010000190000012a000104300000004b0430009c000000a80000a13d000000400100043d0000004402100039000000590300004100000000003204350000002402100039000000080300003900000000003204350000005a0200004100000000002104350000000402100039000000200300003900000000003204350000004b020000410000004b0310009c000000000102801900000040011002100000005b011001c70000012a000104300000003f035000390000005103300197000000400400043d0000000003340019000000000643004b00000000060000190000000106004039000000520730009c000000fc0000213d0000000106600190000000fc0000c13d000000400030043f0000001f0350018f00000000045404360000000505500272000000980000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000000900000413d000000000603004b0000005c0000613d0000000505500210000000000151034f00000000045400190000000303300210000000000504043300000000053501cf000000000535022f000000000101043b0000010003300089000000000131022f00000000013101cf000000000151019f00000000001404350000005c0000013d000000010450019000000054040000410000005505000041000000000504c019000000c0033002100000005603300197000000000353019f00000000046700490000004b0440019700000000014103df00000000013103af0000004e0d800197012801220000040f000000000301001900000060033002700000004b033001970000000102200190000001020000613d0000003f023000390000005104200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000000520640009c000000fc0000213d0000000105500190000000fc0000c13d000000400040043f00000000043204360000001f053000390000000505500272000000d50000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b000000cd0000413d000000000500004b000000d70000613d0000001f0530018f0000000503300272000000e30000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b000000db0000413d000000000605004b000000f20000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f000000000013043500000000010204330000004b020000410000004b0310009c00000000010280190000004b0340009c000000000402801900000040024002100000006001100210000000000121019f000001290001042e000000570100004100000000001004350000004101000039000000040010043f00000058010000410000012a000104300000001f0430018f00000005023002720000010d0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000001060000413d000000000504004b0000011b0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000012a0001043000000120002104210000000102000039000000000001042d0000000002000019000000000001042d000000000f0d001900000126002104290000000102000039000000000001042d0000000002000019000000000001042d0000012800000432000001290001042e0000012a00010430000000000000000000000000000000000000000000000000000000000000000000000000ffffffff00000002000000000000000000000000000000400000010000000000000000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff579952fc000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000064000000a0000000000000000000000000000000000000000000000000000000000000000000000001ffffffe0000000000000000000000000000000000000000000000000ffffffffffffffff00000000000000000000000000000000ffffffffffffffffffffffffffffffff0100000100000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000ffffffff0000000000000000000000000000000000000000000000004e487b710000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000240000000000000000000000004f766572666c6f7700000000000000000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000004d736756616c756553696d756c61746f722063616c6c7320697473656c660000000000000000000000000000000000000000006400000080000000000000000054686973206d6574686f6420726571756972652073797374656d2063616c6c20666c61670000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000840000008000000000000000000000000000000000000000000000000000000000000000000000000000000000b22b444cb6e0e33b30622f1ac981dd65b148ea73de4659871019667337963e8f", + "deployedBytecode": "0x000200000000000200060000000000020001000000010355000000000601001900000060066002700000004b0060019d0000008007000039000000400070043f0000004b09600197000000000800041600000001072001900000001f0000c13d000000000708004b000000690000c13d0000000202200190000000260000c13d00000000020004110000004d0220009c000000260000413d0000005a01000041000000800010043f0000002001000039000000840010043f0000002401000039000000a40010043f0000005e01000041000000c40010043f0000005f01000041000000e40010043f00000060010000410000012a00010430000000000108004b000000690000c13d0000002001000039000001000010044300000120000004430000004c01000041000001290001042e0000004e024001970000000004000410000000000442004b000000340000c13d0000005a01000041000000800010043f0000002001000039000000840010043f0000001e01000039000000a40010043f0000005c01000041000000c40010043f0000005d010000410000012a00010430000000000403004b00000000080004110000000007090019000000400000c13d00000000000304170000000003000414000000000497004b0000006b0000813d000000570100004100000000001004350000001101000039000000ff0000013d000300000009001d000500000005001d000600000006001d0000004f01000041000000a00010043f000100000008001d0000004e01800197000000a40010043f000200000002001d000000c40020043f000400000003001d000000e40030043f0000006401000039000000800010043f0000012001000039000000400010043f0000004b0100004100000000020004140000004b0320009c0000000002018019000000c00120021000000050011001c70000800a020000390128011d0000040f000000000301001900000060033002700000004b053001980000007f0000c13d00000001012001900000000606000029000000050500002900000004030000290000000309000029000000690000613d000000530130009c000000020200002900000001080000290000006d0000213d00000001010003670000000007000031000000380000013d00000000010000190000012a000104300000004b0430009c000000a80000a13d000000400100043d0000004402100039000000590300004100000000003204350000002402100039000000080300003900000000003204350000005a0200004100000000002104350000000402100039000000200300003900000000003204350000004b020000410000004b0310009c000000000102801900000040011002100000005b011001c70000012a000104300000003f035000390000005103300197000000400400043d0000000003340019000000000643004b00000000060000190000000106004039000000520730009c000000fc0000213d0000000106600190000000fc0000c13d000000400030043f0000001f0350018f00000000045404360000000505500272000000980000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000000900000413d000000000603004b0000005c0000613d0000000505500210000000000151034f00000000045400190000000303300210000000000504043300000000053501cf000000000535022f000000000101043b0000010003300089000000000131022f00000000013101cf000000000151019f00000000001404350000005c0000013d000000010450019000000054040000410000005505000041000000000504c019000000c0033002100000005603300197000000000353019f00000000046700490000004b0440019700000000014103df00000000013103af0000004e0d800197012801220000040f000000000301001900000060033002700000004b033001970000000102200190000001020000613d0000003f023000390000005104200197000000400200043d0000000004420019000000000524004b00000000050000190000000105004039000000520640009c000000fc0000213d0000000105500190000000fc0000c13d000000400040043f00000000043204360000001f053000390000000505500272000000d50000613d00000000060000310000000106600367000000000700001900000005087002100000000009840019000000000886034f000000000808043b00000000008904350000000107700039000000000857004b000000cd0000413d000000000500004b000000d70000613d0000001f0530018f0000000503300272000000e30000613d000000000600001900000005076002100000000008740019000000000771034f000000000707043b00000000007804350000000106600039000000000736004b000000db0000413d000000000605004b000000f20000613d0000000503300210000000000131034f00000000033400190000000305500210000000000603043300000000065601cf000000000656022f000000000101043b0000010005500089000000000151022f00000000015101cf000000000161019f000000000013043500000000010204330000004b020000410000004b0310009c00000000010280190000004b0340009c000000000402801900000040024002100000006001100210000000000121019f000001290001042e000000570100004100000000001004350000004101000039000000040010043f00000058010000410000012a000104300000001f0430018f00000005023002720000010d0000613d00000000050000190000000506500210000000000761034f000000000707043b00000000007604350000000105500039000000000625004b000001060000413d000000000504004b0000011b0000613d00000003044002100000000502200210000000000502043300000000054501cf000000000545022f000000000121034f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f000000000012043500000060013002100000012a0001043000000120002104210000000102000039000000000001042d0000000002000019000000000001042d000000000f0d001900000126002104290000000102000039000000000001042d0000000002000019000000000001042d0000012800000432000001290001042e0000012a00010430000000000000000000000000000000000000000000000000000000000000000000000000ffffffff00000002000000000000000000000000000000400000010000000000000000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff579952fc000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000064000000a0000000000000000000000000000000000000000000000000000000000000000000000001ffffffe0000000000000000000000000000000000000000000000000ffffffffffffffff00000000000000000000000000000000ffffffffffffffffffffffffffffffff0100000100000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000ffffffff0000000000000000000000000000000000000000000000004e487b710000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000240000000000000000000000004f766572666c6f7700000000000000000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000004d736756616c756553696d756c61746f722063616c6c7320697473656c660000000000000000000000000000000000000000006400000080000000000000000054686973206d6574686f6420726571756972652073797374656d2063616c6c20666c61670000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000840000008000000000000000000000000000000000000000000000000000000000000000000000000000000000b22b444cb6e0e33b30622f1ac981dd65b148ea73de4659871019667337963e8f", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/NonceHolder.json b/.test-node-subtree/src/deps/contracts/NonceHolder.json new file mode 100644 index 00000000..3d30c311 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/NonceHolder.json @@ -0,0 +1,229 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "NonceHolder", + "sourceName": "cache-zk/solpp-generated-contracts/NonceHolder.sol", + "abi": [ + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "accountAddress", + "type": "address" + }, + { + "indexed": true, + "internalType": "uint256", + "name": "key", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "value", + "type": "uint256" + } + ], + "name": "ValueSetUnderNonce", + "type": "event" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + } + ], + "name": "getDeploymentNonce", + "outputs": [ + { + "internalType": "uint256", + "name": "deploymentNonce", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + } + ], + "name": "getMinNonce", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + } + ], + "name": "getRawNonce", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_key", + "type": "uint256" + } + ], + "name": "getValueUnderNonce", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_value", + "type": "uint256" + } + ], + "name": "increaseMinNonce", + "outputs": [ + { + "internalType": "uint256", + "name": "oldMinNonce", + "type": "uint256" + } + ], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + } + ], + "name": "incrementDeploymentNonce", + "outputs": [ + { + "internalType": "uint256", + "name": "prevDeploymentNonce", + "type": "uint256" + } + ], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_expectedNonce", + "type": "uint256" + } + ], + "name": "incrementMinNonceIfEquals", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + }, + { + "internalType": "uint256", + "name": "_nonce", + "type": "uint256" + } + ], + "name": "isNonceUsed", + "outputs": [ + { + "internalType": "bool", + "name": "", + "type": "bool" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_key", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "_value", + "type": "uint256" + } + ], + "name": "setValueUnderNonce", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_address", + "type": "address" + }, + { + "internalType": "uint256", + "name": "_key", + "type": "uint256" + }, + { + "internalType": "bool", + "name": "_shouldBeUsed", + "type": "bool" + } + ], + "name": "validateNonceUsage", + "outputs": [], + "stateMutability": "view", + "type": "function" + } + ], + "bytecode": "0x00010000000000020005000000000002000000000601034f00000000000603550000008001000039000000400010043f00000000010600190000006001100270000000bb011001970000000103200190000000260000c13d000000040310008c0000026b0000413d000000000306043b000000e003300270000000bd0430009c0000002e0000213d000000c40430009c000000470000a13d000000c50430009c000001000000613d000000c60230009c000001190000613d000000c70230009c0000026b0000c13d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d0000000401600370000000000101043b000000ca0210009c0000026b0000213d0000000000100435000000200000043f0000012b0000013d0000000001000416000000000101004b0000026b0000c13d000000200100003900000100001004430000012000000443000000bc01000041000002e70001042e000000be0430009c000000630000a13d000000bf0430009c000001310000613d000000c00430009c000001420000613d000000c10230009c0000026b0000c13d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d0000000401600370000000000101043b000000ca0210009c0000026b0000213d0000000000100435000000200000043f000000000100001902e602ca0000040f000000000101041a00000080011002700000012e0000013d000000c80430009c000000730000613d000000c90230009c0000026b0000c13d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d0000000401600370000000000101043b000000ca0210009c0000026b0000213d0000000002000411000080060220008c000001b20000c13d000500000001001d02e6026d0000040f000000000101041a000400000001001d000000050100002902e6026d0000040f0000000403000029000000da02300041000000000021041b0000008001300270000001870000013d000000c20230009c000000cf0000613d000000c30230009c0000026b0000c13d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d0000000401600370000000000101043b000000ca0210009c0000026b0000213d02e6027d0000040f000001870000013d0000000003000416000000000303004b0000026b0000c13d000000040110008a000000400110008c0000026b0000413d00000000030004110000002401600370000000000501043b0000000401600370000000000401043b0000000201200190000000820000c13d000000db0130009c0000014d0000813d000500000005001d000400000004001d000000dc01000041000000800010043f000300000003001d000000ca01300197000200000001001d000000840010043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000dd011001c7000080060200003902e602e10000040f00000000030100190000006003300270000000bb03300197000000400430008c000000000403001900000040040080390000001f0540018f0000000506400272000000a40000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b0000009c0000413d000000000705004b000000b30000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f000000000056043500000001022001900000018f0000613d0000001f01400039000000e00110018f0000008002100039000000400020043f000000400330008c0000026b0000413d000000c003100039000000400030043f000000800300043d000000010430008c0000026b0000213d0000000000320435000000a00200043d000000010320008c0000026b0000213d000000a0011000390000000000210435000000050100006b000001f50000c13d000000400100043d0000004402100039000000e103000041000000000032043500000024021000390000001e03000039000001c20000013d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000600110008c0000026b0000413d0000000401600370000000000301043b000000ca0130009c0000026b0000213d0000004401600370000000000201043b000000000102004b0000000001000019000000010100c039000500000002001d000000000112004b0000026b0000c13d0000002401600370000000000101043b000300000001001d0000000000300435000000200000043f000000bb010000410000000002000414000400000003001d000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f000000040300002900000001022001900000026b0000613d000000000101043b000000000101041a000000cd01100197000000030110006c000001ce0000a13d000000050100006b0000023f0000c13d000000400100043d0000004402100039000000d303000041000000000032043500000024021000390000001c03000039000001c20000013d0000000003000416000000000303004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d0000000401600370000000000301043b00000002012001900000010d0000c13d00000000010004110000ffff0110008c0000014d0000213d000000d40130009c000001780000413d000000cf01000041000000800010043f0000002001000039000000840010043f0000003001000039000000a40010043f000000d501000041000000c40010043f000000d601000041000001560000013d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d000000000100041100000000001004350000000101000039000000200010043f0000000001000019000500000006035302e602ca0000040f000000050200035f0000000402200370000000000202043b0000000000200435000000200010043f000000000100001902e602ca0000040f000000000101041a000000800010043f000000cb01000041000002e70001042e0000000002000416000000000202004b0000026b0000c13d000000040110008a000000400110008c0000026b0000413d0000000401600370000000000101043b000000ca0210009c0000026b0000213d0000002402600370000000000202043b02e602900000040f000000000101004b0000000001000019000000010100c039000001870000013d0000000003000416000000000303004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d00000000030004110000000201200190000001590000c13d0000ffff0130008c000001590000a13d000000cf01000041000000800010043f0000002001000039000000840010043f0000002401000039000000a40010043f000000e201000041000000c40010043f000000e301000041000000e40010043f000000d701000041000002e800010430000500000003001d0000000000300435000000200000043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d00000004020000390000000002200367000000000202043b000000000101043b000000000101041a000000cd03100197000000000223004b000001bc0000c13d00000005020000290000000000200435000000200000043f000500010010003d000000000100001902e602ca0000040f0000000502000029000000000021041b0000000001000019000002e70001042e0000000001000411000400000001001d0000000000100435000000200000043f0000000001000019000500000003001d02e602ca0000040f000000000101041a000300000001001d000000040100002902e6026d0000040f00000003030000290000000502300029000000000021041b000000cd01300197000000400200043d0000000000120435000000bb01000041000000bb0320009c00000000020180190000004001200210000000d1011001c7000002e70001042e000000400200043d0000001f0430018f00000005053002720000019c0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000001940000413d000000000604004b000001ab0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000000bb01000041000000bb0420009c000000000201801900000040012002100000006002300210000000000121019f000002e800010430000000cf01000041000000800010043f0000002001000039000000840010043f0000003d01000039000000a40010043f000000d801000041000000c40010043f000000d901000041000001560000013d000000400100043d0000004402100039000000ce03000041000000000032043500000024021000390000000f030000390000000000320435000000cf020000410000000000210435000000040210003900000020030000390000000000320435000000bb02000041000000bb0310009c00000000010280190000004001100210000000d0011001c7000002e80001043000000000003004350000000101000039000000200010043f000000bb030000410000000001000414000000bb0210009c0000000001038019000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b00000003020000290000000000200435000000200010043f0000000001000414000000bb0210009c000000bb01008041000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b000000000101041a000000000101004b000000f70000c13d000000050100006b0000023f0000613d000000400100043d0000004402100039000000d203000041000000000032043500000024021000390000001d03000039000001c20000013d000000000102004b0000020d0000c13d000000040100006b0000020d0000613d00000002010000290000000000100435000000200000043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d00000004020000290001000100200092000000000101043b000000000101041a000000cd01100197000000010110006c000002410000a13d000000030100002900000000001004350000000101000039000000200010043f000000bb030000410000000001000414000000bb0210009c0000000001038019000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b00000004020000290000000000200435000000200010043f0000000001000414000000bb0210009c000000bb01008041000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b0000000502000029000000000021041b000000400100043d0000000000210435000000bb020000410000000003000414000000bb0430009c0000000003028019000000bb0410009c00000000010280190000004001100210000000c002300210000000000112019f000000df011001c70000800d020000390000000303000039000000e0040000410000000305000029000000040600002902e602dc0000040f00000001012001900000026b0000613d0000000001000019000002e70001042e000000020100002900000000001004350000000101000039000000200010043f000000bb030000410000000001000414000000bb0210009c0000000001038019000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b00000001020000290000000000200435000000200010043f0000000001000414000000bb0210009c000000bb01008041000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b000000000101041a000000000101004b0000020d0000c13d000000400100043d0000004402100039000000de030000410000000000320435000000cf0200004100000000002104350000002402100039000000200300003900000000003204350000000402100039000001c70000013d0000000001000019000002e8000104300000000000100435000000200000043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f00000001022001900000027b0000613d000000000101043b000000000001042d0000000001000019000002e800010430000000ca011001970000000000100435000000200000043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f00000001022001900000028e0000613d000000000101043b000000000101041a000000cd01100197000000000001042d0000000001000019000002e8000104300002000000000002000200000002001d000000ca01100197000100000001001d0000000000100435000000200000043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f0000000102200190000002c80000613d0000000102000039000000000101043b000000000101041a000000cd01100197000000020110006c000002c60000213d000000010100002900000000001004350000000101000039000000200010043f000000bb040000410000000001000414000000bb0210009c0000000001048019000000c001100210000000cc011001c7000080100200003902e602e10000040f0000000102200190000002c80000613d000000000101043b00000002020000290000000000200435000000200010043f0000000001000414000000bb0210009c000000bb01008041000000c001100210000000cc011001c7000080100200003902e602e10000040f0000000102200190000002c80000613d000000000101043b000000000101041a000000000101004b0000000002000019000000010200c039000000010120018f000000000001042d0000000001000019000002e800010430000000bb02000041000000bb0310009c00000000010280190000000003000414000000bb0430009c0000000003028019000000c0023002100000004001100210000000000121019f000000cc011001c7000080100200003902e602e10000040f0000000102200190000002da0000613d000000000101043b000000000001042d0000000001000019000002e800010430000002df002104210000000102000039000000000001042d0000000002000019000000000001042d000002e4002104230000000102000039000000000001042d0000000002000019000000000001042d000002e600000432000002e70001042e000002e80001043000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000000000000000000000000000000000000000000000000000000000006ee1dc1f00000000000000000000000000000000000000000000000000000000cab7e8ea00000000000000000000000000000000000000000000000000000000cab7e8eb00000000000000000000000000000000000000000000000000000000e1239cd800000000000000000000000000000000000000000000000000000000fb1a9a57000000000000000000000000000000000000000000000000000000006ee1dc2000000000000000000000000000000000000000000000000000000000896909dc0000000000000000000000000000000000000000000000000000000038a780910000000000000000000000000000000000000000000000000000000038a780920000000000000000000000000000000000000000000000000000000055d35d18000000000000000000000000000000000000000000000000000000005aa9b6b500000000000000000000000000000000000000000000000000000000155fd27a00000000000000000000000000000000000000000000000000000000306395c6000000000000000000000000ffffffffffffffffffffffffffffffffffffffff0000000000000000000000000000000000000020000000800000000000000000020000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffff496e636f7272656374206e6f6e6365000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000000000000000000000000000000000000000000020000000000000000000000000546865206e6f6e636520776173206e6f7420736574206173207573656400000052657573696e67207468652073616d65206e6f6e63652074776963650000000000000000000000000000000000000000000000000000000000000001000000015468652076616c756520666f7220696e6372656d656e74696e6720746865206e6f6e636520697320746f6f20686967680000000000000000000000000000000000000000000000000000000000000000000000840000008000000000000000004f6e6c792074686520636f6e7472616374206465706c6f7965722063616e20696e6372656d656e7420746865206465706c6f796d656e74206e6f6e6365000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000100007b510fe800000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000080000000000000000050726576696f7573206e6f6e636520686173206e6f74206265656e20757365640200000000000000000000000000000000000020000000000000000000000000da2b716e5a5d5f602b9a5842bcd89c215b125258dfea271a03e5e0e801d93a8c4e6f6e63652076616c75652063616e6e6f742062652073657420746f2030000054686973206d6574686f6420726571756972652073797374656d2063616c6c20666c616700000000000000000000000000000000000000000000000000000000632daf73d815dc516be846d11c1d2e43343946d34c2ab50d6c6df1fc1404454a", + "deployedBytecode": "0x00010000000000020005000000000002000000000601034f00000000000603550000008001000039000000400010043f00000000010600190000006001100270000000bb011001970000000103200190000000260000c13d000000040310008c0000026b0000413d000000000306043b000000e003300270000000bd0430009c0000002e0000213d000000c40430009c000000470000a13d000000c50430009c000001000000613d000000c60230009c000001190000613d000000c70230009c0000026b0000c13d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d0000000401600370000000000101043b000000ca0210009c0000026b0000213d0000000000100435000000200000043f0000012b0000013d0000000001000416000000000101004b0000026b0000c13d000000200100003900000100001004430000012000000443000000bc01000041000002e70001042e000000be0430009c000000630000a13d000000bf0430009c000001310000613d000000c00430009c000001420000613d000000c10230009c0000026b0000c13d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d0000000401600370000000000101043b000000ca0210009c0000026b0000213d0000000000100435000000200000043f000000000100001902e602ca0000040f000000000101041a00000080011002700000012e0000013d000000c80430009c000000730000613d000000c90230009c0000026b0000c13d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d0000000401600370000000000101043b000000ca0210009c0000026b0000213d0000000002000411000080060220008c000001b20000c13d000500000001001d02e6026d0000040f000000000101041a000400000001001d000000050100002902e6026d0000040f0000000403000029000000da02300041000000000021041b0000008001300270000001870000013d000000c20230009c000000cf0000613d000000c30230009c0000026b0000c13d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d0000000401600370000000000101043b000000ca0210009c0000026b0000213d02e6027d0000040f000001870000013d0000000003000416000000000303004b0000026b0000c13d000000040110008a000000400110008c0000026b0000413d00000000030004110000002401600370000000000501043b0000000401600370000000000401043b0000000201200190000000820000c13d000000db0130009c0000014d0000813d000500000005001d000400000004001d000000dc01000041000000800010043f000300000003001d000000ca01300197000200000001001d000000840010043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000dd011001c7000080060200003902e602e10000040f00000000030100190000006003300270000000bb03300197000000400430008c000000000403001900000040040080390000001f0540018f0000000506400272000000a40000613d00000000070000190000000508700210000000000981034f000000000909043b000000800880003900000000009804350000000107700039000000000867004b0000009c0000413d000000000705004b000000b30000613d0000000506600210000000000761034f00000003055002100000008006600039000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f000000000056043500000001022001900000018f0000613d0000001f01400039000000e00110018f0000008002100039000000400020043f000000400330008c0000026b0000413d000000c003100039000000400030043f000000800300043d000000010430008c0000026b0000213d0000000000320435000000a00200043d000000010320008c0000026b0000213d000000a0011000390000000000210435000000050100006b000001f50000c13d000000400100043d0000004402100039000000e103000041000000000032043500000024021000390000001e03000039000001c20000013d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000600110008c0000026b0000413d0000000401600370000000000301043b000000ca0130009c0000026b0000213d0000004401600370000000000201043b000000000102004b0000000001000019000000010100c039000500000002001d000000000112004b0000026b0000c13d0000002401600370000000000101043b000300000001001d0000000000300435000000200000043f000000bb010000410000000002000414000400000003001d000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f000000040300002900000001022001900000026b0000613d000000000101043b000000000101041a000000cd01100197000000030110006c000001ce0000a13d000000050100006b0000023f0000c13d000000400100043d0000004402100039000000d303000041000000000032043500000024021000390000001c03000039000001c20000013d0000000003000416000000000303004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d0000000401600370000000000301043b00000002012001900000010d0000c13d00000000010004110000ffff0110008c0000014d0000213d000000d40130009c000001780000413d000000cf01000041000000800010043f0000002001000039000000840010043f0000003001000039000000a40010043f000000d501000041000000c40010043f000000d601000041000001560000013d0000000002000416000000000202004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d000000000100041100000000001004350000000101000039000000200010043f0000000001000019000500000006035302e602ca0000040f000000050200035f0000000402200370000000000202043b0000000000200435000000200010043f000000000100001902e602ca0000040f000000000101041a000000800010043f000000cb01000041000002e70001042e0000000002000416000000000202004b0000026b0000c13d000000040110008a000000400110008c0000026b0000413d0000000401600370000000000101043b000000ca0210009c0000026b0000213d0000002402600370000000000202043b02e602900000040f000000000101004b0000000001000019000000010100c039000001870000013d0000000003000416000000000303004b0000026b0000c13d000000040110008a000000200110008c0000026b0000413d00000000030004110000000201200190000001590000c13d0000ffff0130008c000001590000a13d000000cf01000041000000800010043f0000002001000039000000840010043f0000002401000039000000a40010043f000000e201000041000000c40010043f000000e301000041000000e40010043f000000d701000041000002e800010430000500000003001d0000000000300435000000200000043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d00000004020000390000000002200367000000000202043b000000000101043b000000000101041a000000cd03100197000000000223004b000001bc0000c13d00000005020000290000000000200435000000200000043f000500010010003d000000000100001902e602ca0000040f0000000502000029000000000021041b0000000001000019000002e70001042e0000000001000411000400000001001d0000000000100435000000200000043f0000000001000019000500000003001d02e602ca0000040f000000000101041a000300000001001d000000040100002902e6026d0000040f00000003030000290000000502300029000000000021041b000000cd01300197000000400200043d0000000000120435000000bb01000041000000bb0320009c00000000020180190000004001200210000000d1011001c7000002e70001042e000000400200043d0000001f0430018f00000005053002720000019c0000613d000000000600001900000005076002100000000008720019000000000771034f000000000707043b00000000007804350000000106600039000000000756004b000001940000413d000000000604004b000001ab0000613d0000000505500210000000000151034f00000000055200190000000304400210000000000605043300000000064601cf000000000646022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000161019f0000000000150435000000bb01000041000000bb0420009c000000000201801900000040012002100000006002300210000000000121019f000002e800010430000000cf01000041000000800010043f0000002001000039000000840010043f0000003d01000039000000a40010043f000000d801000041000000c40010043f000000d901000041000001560000013d000000400100043d0000004402100039000000ce03000041000000000032043500000024021000390000000f030000390000000000320435000000cf020000410000000000210435000000040210003900000020030000390000000000320435000000bb02000041000000bb0310009c00000000010280190000004001100210000000d0011001c7000002e80001043000000000003004350000000101000039000000200010043f000000bb030000410000000001000414000000bb0210009c0000000001038019000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b00000003020000290000000000200435000000200010043f0000000001000414000000bb0210009c000000bb01008041000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b000000000101041a000000000101004b000000f70000c13d000000050100006b0000023f0000613d000000400100043d0000004402100039000000d203000041000000000032043500000024021000390000001d03000039000001c20000013d000000000102004b0000020d0000c13d000000040100006b0000020d0000613d00000002010000290000000000100435000000200000043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d00000004020000290001000100200092000000000101043b000000000101041a000000cd01100197000000010110006c000002410000a13d000000030100002900000000001004350000000101000039000000200010043f000000bb030000410000000001000414000000bb0210009c0000000001038019000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b00000004020000290000000000200435000000200010043f0000000001000414000000bb0210009c000000bb01008041000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b0000000502000029000000000021041b000000400100043d0000000000210435000000bb020000410000000003000414000000bb0430009c0000000003028019000000bb0410009c00000000010280190000004001100210000000c002300210000000000112019f000000df011001c70000800d020000390000000303000039000000e0040000410000000305000029000000040600002902e602dc0000040f00000001012001900000026b0000613d0000000001000019000002e70001042e000000020100002900000000001004350000000101000039000000200010043f000000bb030000410000000001000414000000bb0210009c0000000001038019000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b00000001020000290000000000200435000000200010043f0000000001000414000000bb0210009c000000bb01008041000000c001100210000000cc011001c7000080100200003902e602e10000040f00000001022001900000026b0000613d000000000101043b000000000101041a000000000101004b0000020d0000c13d000000400100043d0000004402100039000000de030000410000000000320435000000cf0200004100000000002104350000002402100039000000200300003900000000003204350000000402100039000001c70000013d0000000001000019000002e8000104300000000000100435000000200000043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f00000001022001900000027b0000613d000000000101043b000000000001042d0000000001000019000002e800010430000000ca011001970000000000100435000000200000043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f00000001022001900000028e0000613d000000000101043b000000000101041a000000cd01100197000000000001042d0000000001000019000002e8000104300002000000000002000200000002001d000000ca01100197000100000001001d0000000000100435000000200000043f000000bb010000410000000002000414000000bb0320009c0000000002018019000000c001200210000000cc011001c7000080100200003902e602e10000040f0000000102200190000002c80000613d0000000102000039000000000101043b000000000101041a000000cd01100197000000020110006c000002c60000213d000000010100002900000000001004350000000101000039000000200010043f000000bb040000410000000001000414000000bb0210009c0000000001048019000000c001100210000000cc011001c7000080100200003902e602e10000040f0000000102200190000002c80000613d000000000101043b00000002020000290000000000200435000000200010043f0000000001000414000000bb0210009c000000bb01008041000000c001100210000000cc011001c7000080100200003902e602e10000040f0000000102200190000002c80000613d000000000101043b000000000101041a000000000101004b0000000002000019000000010200c039000000010120018f000000000001042d0000000001000019000002e800010430000000bb02000041000000bb0310009c00000000010280190000000003000414000000bb0430009c0000000003028019000000c0023002100000004001100210000000000121019f000000cc011001c7000080100200003902e602e10000040f0000000102200190000002da0000613d000000000101043b000000000001042d0000000001000019000002e800010430000002df002104210000000102000039000000000001042d0000000002000019000000000001042d000002e4002104230000000102000039000000000001042d0000000002000019000000000001042d000002e600000432000002e70001042e000002e80001043000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000200000000000000000000000000000040000001000000000000000000000000000000000000000000000000000000000000000000000000006ee1dc1f00000000000000000000000000000000000000000000000000000000cab7e8ea00000000000000000000000000000000000000000000000000000000cab7e8eb00000000000000000000000000000000000000000000000000000000e1239cd800000000000000000000000000000000000000000000000000000000fb1a9a57000000000000000000000000000000000000000000000000000000006ee1dc2000000000000000000000000000000000000000000000000000000000896909dc0000000000000000000000000000000000000000000000000000000038a780910000000000000000000000000000000000000000000000000000000038a780920000000000000000000000000000000000000000000000000000000055d35d18000000000000000000000000000000000000000000000000000000005aa9b6b500000000000000000000000000000000000000000000000000000000155fd27a00000000000000000000000000000000000000000000000000000000306395c6000000000000000000000000ffffffffffffffffffffffffffffffffffffffff0000000000000000000000000000000000000020000000800000000000000000020000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffff496e636f7272656374206e6f6e6365000000000000000000000000000000000008c379a00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000640000000000000000000000000000000000000000000000000000000000000020000000000000000000000000546865206e6f6e636520776173206e6f7420736574206173207573656400000052657573696e67207468652073616d65206e6f6e63652074776963650000000000000000000000000000000000000000000000000000000000000001000000015468652076616c756520666f7220696e6372656d656e74696e6720746865206e6f6e636520697320746f6f20686967680000000000000000000000000000000000000000000000000000000000000000000000840000008000000000000000004f6e6c792074686520636f6e7472616374206465706c6f7965722063616e20696e6372656d656e7420746865206465706c6f796d656e74206e6f6e6365000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000100007b510fe800000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000080000000000000000050726576696f7573206e6f6e636520686173206e6f74206265656e20757365640200000000000000000000000000000000000020000000000000000000000000da2b716e5a5d5f602b9a5842bcd89c215b125258dfea271a03e5e0e801d93a8c4e6f6e63652076616c75652063616e6e6f742062652073657420746f2030000054686973206d6574686f6420726571756972652073797374656d2063616c6c20666c616700000000000000000000000000000000000000000000000000000000632daf73d815dc516be846d11c1d2e43343946d34c2ab50d6c6df1fc1404454a", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/P256VERIFY.yul.zbin b/.test-node-subtree/src/deps/contracts/P256VERIFY.yul.zbin new file mode 100644 index 00000000..8d1fec9a Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/P256VERIFY.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/SHA256.yul.zbin b/.test-node-subtree/src/deps/contracts/SHA256.yul.zbin new file mode 100644 index 00000000..81eea3d7 Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/SHA256.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/SystemContext.json b/.test-node-subtree/src/deps/contracts/SystemContext.json new file mode 100644 index 00000000..5027c3c1 --- /dev/null +++ b/.test-node-subtree/src/deps/contracts/SystemContext.json @@ -0,0 +1,410 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "SystemContext", + "sourceName": "cache-zk/solpp-generated-contracts/SystemContext.sol", + "abi": [ + { + "inputs": [ + { + "internalType": "bytes32", + "name": "_txHash", + "type": "bytes32" + } + ], + "name": "appendTransactionToCurrentL2Block", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "baseFee", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "blockGasLimit", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_blockNumber", + "type": "uint256" + } + ], + "name": "blockHash", + "outputs": [ + { + "internalType": "bytes32", + "name": "hash", + "type": "bytes32" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "chainId", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "coinbase", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "currentBlockInfo", + "outputs": [ + { + "internalType": "uint256", + "name": "blockInfo", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "difficulty", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "gasPrice", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_batchNumber", + "type": "uint256" + } + ], + "name": "getBatchHash", + "outputs": [ + { + "internalType": "bytes32", + "name": "hash", + "type": "bytes32" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getBatchNumberAndTimestamp", + "outputs": [ + { + "internalType": "uint128", + "name": "batchNumber", + "type": "uint128" + }, + { + "internalType": "uint128", + "name": "batchTimestamp", + "type": "uint128" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_block", + "type": "uint256" + } + ], + "name": "getBlockHashEVM", + "outputs": [ + { + "internalType": "bytes32", + "name": "hash", + "type": "bytes32" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getBlockNumber", + "outputs": [ + { + "internalType": "uint128", + "name": "", + "type": "uint128" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getBlockNumberAndTimestamp", + "outputs": [ + { + "internalType": "uint256", + "name": "blockNumber", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "blockTimestamp", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getBlockTimestamp", + "outputs": [ + { + "internalType": "uint128", + "name": "", + "type": "uint128" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getL2BlockNumberAndTimestamp", + "outputs": [ + { + "internalType": "uint128", + "name": "blockNumber", + "type": "uint128" + }, + { + "internalType": "uint128", + "name": "blockTimestamp", + "type": "uint128" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "incrementTxNumberInBatch", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "origin", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "publishTimestampDataToL1", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "resetTxNumberInBatch", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_gasPrice", + "type": "uint256" + } + ], + "name": "setGasPrice", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint128", + "name": "_l2BlockNumber", + "type": "uint128" + }, + { + "internalType": "uint128", + "name": "_l2BlockTimestamp", + "type": "uint128" + }, + { + "internalType": "bytes32", + "name": "_expectedPrevL2BlockHash", + "type": "bytes32" + }, + { + "internalType": "bool", + "name": "_isFirstInBatch", + "type": "bool" + }, + { + "internalType": "uint128", + "name": "_maxVirtualBlocksToCreate", + "type": "uint128" + } + ], + "name": "setL2Block", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes32", + "name": "_prevBatchHash", + "type": "bytes32" + }, + { + "internalType": "uint128", + "name": "_newTimestamp", + "type": "uint128" + }, + { + "internalType": "uint128", + "name": "_expectedNewNumber", + "type": "uint128" + }, + { + "internalType": "uint256", + "name": "_baseFee", + "type": "uint256" + } + ], + "name": "setNewBatch", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "_newOrigin", + "type": "address" + } + ], + "name": "setTxOrigin", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "txNumberInBlock", + "outputs": [ + { + "internalType": "uint16", + "name": "", + "type": "uint16" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "_newTimestamp", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "_number", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "_baseFee", + "type": "uint256" + } + ], + "name": "unsafeOverrideBatch", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + } + ], + "bytecode": "0x0001000000000002000600000000000200000000000103550000008004000039000000400040043f0000000003010019000000600330027000000118033001970000000102200190000000210000c13d000000040230008c000003960000413d000000000201043b000000e0022002700000011c0520009c000000340000213d0000012e0520009c000000430000a13d0000012f0420009c0000007b0000a13d000001300420009c000000c80000213d000001330120009c000001100000613d000001340120009c000003960000c13d0000000001000416000000000101004b000003960000c13d0000010c01000039000000000101041a0000014001100197000001f10000013d0000000001000416000000000101004b000003960000c13d00000118010000410000000302000039000000000012041b0000000401000039000000000201041a000001190220019700008001022001bf000000000021041b0000011a010000410000000502000039000000000012041b0000002001000039000001000010044300000120000004430000011b010000410000045a0001042e0000011d0420009c000000630000a13d0000011e0420009c000000860000a13d0000011f0420009c000000f80000213d000001220120009c0000003e0000613d000001230120009c000003960000c13d0000000001000416000000000101004b000003960000c13d045904180000040f0000006f0000013d000001380520009c0000009c0000213d0000013c0520009c000001150000613d0000013d0520009c000001570000613d0000013e0220009c000003960000c13d0000000002000416000000000202004b000003960000c13d000000040230008a000000200220008c000003960000413d0000000002000411000080010220008c000002160000c13d0000000a02000039000600000002001d000000000202041a000000a00020043f0000000401100370000000000101043b000000c00010043f0000004002000039000000800020043f000000e001000039000000400010043f000000a0010000390459043e0000040f0000000602000029000001e30000013d000001270420009c000000b30000213d0000012b0420009c000001010000613d0000012c0120009c0000018f0000613d0000012d0120009c000003960000c13d0000000001000416000000000101004b000003960000c13d0459042b0000040f0000014002200197000000400300043d00000020043000390000000000240435000001400110019700000000001304350000011801000041000001180230009c0000000003018019000000400130021000000141011001c70000045a0001042e000001350120009c000001960000613d000001360120009c000001a20000613d000001370120009c000003960000c13d0000000001000416000000000101004b000003960000c13d0000000601000039000001c70000013d000001240420009c000001a90000613d000001250420009c000001ae0000613d000001260120009c000003960000c13d0000000001000416000000000101004b000003960000c13d000000040130008a000000200110008c000003960000413d0000000001000411000080010110008c00000000010000190000000101006039045903f80000040f00000004010000390000000001100367000000000101043b0000000202000039000001e30000013d000001390120009c000001c30000613d0000013a0120009c000001c90000613d0000013b0120009c000003960000c13d0000000001000416000000000101004b000003960000c13d0000000001000411000080010110008c000002160000c13d0000010e01000039000000000201041a0000ffff0320018f0000ffff0430008c000002200000c13d0000017b0100004100000000001004350000001101000039000000040010043f0000017c010000410000045b00010430000001280120009c000001e60000613d000001290120009c000001ed0000613d0000012a0120009c000003960000c13d0000000001000416000000000101004b000003960000c13d045904180000040f00000140022001970000008001100210000000000121019f000000400200043d00000000001204350000011801000041000001180320009c0000000002018019000000400120021000000143011001c70000045a0001042e000001310420009c000001f40000613d000001320220009c000003960000c13d0000000002000416000000000202004b000003960000c13d000000040230008a000000200220008c000003960000413d0000000401100370000000000101043b0000010c02000039000000000202041a000000c003000039000000400030043f00000080062002700000010d02000039000000000302041a0000014005300197000000800050043f0000008002300270000000a00020043f000000000416004b0000000004000019000002440000a13d0000000004160049000001010440008c0000000004000019000002440000813d000000000451004b000002260000813d00000000001004350000000801000039000000200010043f00000118010000410000000002000414000001180320009c0000000002018019000000c00120021000000146011001c70000801002000039045904540000040f0000000102200190000003960000613d000000000101043b000000000401041a000002440000013d000001200420009c000001010000613d000001210120009c000003960000c13d0000000001000416000000000101004b000003960000c13d0000000201000039000001c70000013d0000000002000416000000000202004b000003960000c13d000000040230008a000000200220008c000003960000413d0000000401100370000000000101043b00000000001004350000000801000039000000200010043f000000400200003900000000010000190459043e0000040f000001c70000013d0000000001000416000000000101004b000003960000c13d0000000301000039000001c70000013d0000000002000416000000000202004b000003960000c13d000000040230008a000000800220008c000003960000413d0000000402100370000000000302043b0000002402100370000000000402043b000001400240009c000003960000213d0000004401100370000000000501043b000001400150009c000003960000213d0000000001000411000080010110008c000002160000c13d000000c001000039000000400010043f0000000706000039000000000106041a0000014002100197000000800020043f0000008001100270000000a00010043f000000000224004b0000024c0000a13d000001400210009c000000ad0000613d0000000102100039000000000252004b000002550000c13d000300000006001d000400000005001d000600000003001d0000000902000039000000000202041a0000014002200197000500000004001d000000000224004b000002610000a13d00000000001004350000000801000039000000200010043f00000118010000410000000002000414000001180320009c0000000002018019000000c00120021000000146011001c70000801002000039045904540000040f00000001022001900000000602000029000003960000613d000000000101043b000000000021041b000000400100043d0000015e0210009c000003110000a13d0000017b0100004100000000001004350000004101000039000000b00000013d0000000002000416000000000202004b000003960000c13d000000040230008a000000a00220008c000003960000413d0000000402100370000000000602043b000001400260009c000003960000213d0000002402100370000000000502043b000001400250009c000003960000213d0000004402100370000000000702043b0000006402100370000000000202043b000000000302004b0000000003000019000000010300c039000000000332004b000003960000c13d0000008401100370000000000301043b000001400130009c000003960000213d0000000001000411000080010110008c000002160000c13d000000000102004b000600000003001d000400000007001d0000027e0000613d0000000701000039000000000101041a00000140011001970000000003050019000000000115004b0000026f0000813d0000014701000041000000800010043f0000002001000039000000840010043f0000006101000039000000a40010043f0000014f01000041000000c40010043f0000015001000041000000e40010043f0000015101000041000001040010043f0000015201000041000001240010043f00000153010000410000045b000104300000000001000416000000000101004b000003960000c13d0000010e01000039000000000101041a0000ffff0110018f000001f10000013d0000000001000416000000000101004b000003960000c13d0000000001000411000080010110008c00000000010000190000000101006039045903f80000040f0000010e01000039000000000201041a0000014b02200197000002230000013d0000000001000416000000000101004b000003960000c13d0000010c01000039000000000101041a0000008001100270000001f10000013d0000000001000416000000000101004b000003960000c13d0000000401000039000001ea0000013d0000000002000416000000000202004b000003960000c13d000000040230008a000000200220008c000003960000413d0000000401100370000000000201043b000001420120009c000003960000213d0000000001000411000080010110008c00000000010000190000000101006039000600000002001d045903f80000040f0000000101000039000000000201041a000001190220019700000006022001af000002230000013d0000000001000416000000000101004b000003960000c13d0000000501000039000000000101041a000001f10000013d0000000001000416000000000101004b000003960000c13d000000040130008a000000600110008c000003960000413d0000000001000411000080010110008c00000000010000190000000101006039045903f80000040f000000400100043d0459040d0000040f00000000010003670000002402100370000000000202043b00000080022002100000000403100370000000000303043b0000014003300197000000000223019f0000000703000039000000000023041b0000004401100370000000000101043b0000000602000039000000000012041b00000000010000190000045a0001042e0000000001000416000000000101004b000003960000c13d0000000101000039000000000101041a0000014201100197000001f10000013d0000000001000416000000000101004b000003960000c13d000000000100041a000000800010043f0000013f010000410000045a0001042e0000000001000416000000000101004b000003960000c13d0000000001000411000080010110008c000002160000c13d0000000701000039000000000301041a0000014001300197000000800010043f0000008002300270000000a00020043f0000010002000039000000400020043f0000000902000039000000000402041a0000014002400197000000c00020043f0000008004400270000000e00040043f000001400330009c0000022e0000213d0000014701000041000001000010043f0000002001000039000001040010043f0000002f01000039000001240010043f0000014801000041000001440010043f0000014901000041000001640010043f0000014a010000410000045b000104300000014701000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f0000017201000041000000c40010043f00000173010000410000045b000104300000014b022001970000000103300039000000000223019f000000000021041b00000000010000190000045a0001042e000001440330009c000002340000413d000000000221004b000002340000413d000001012110011a0000000b01200039000000000401041a000002440000013d0000008001100210000000000112019f0000000302000039000000000012041c00000000010000190000045a0001042e000000e00010043f0000002001000039000000c00010043f0000010001000039000000400010043f00000118010000410000000002000414000001180320009c0000000002018019000000c00120021000000145011001c70000801002000039045904540000040f0000000102200190000003960000613d000000000401043b000000400100043d00000000004104350000011802000041000001180310009c0000000001028019000000400110021000000143011001c70000045a0001042e0000014701000041000000c00010043f0000002001000039000000c40010043f000000e40010043f0000017401000041000001040010043f00000155010000410000045b000104300000014701000041000000c00010043f0000002001000039000000c40010043f0000002801000039000000e40010043f0000017501000041000001040010043f0000017601000041000001240010043f00000161010000410000045b000104300000014701000041000000c00010043f0000002001000039000000c40010043f0000005301000039000000e40010043f0000017701000041000001040010043f0000017801000041000001240010043f0000017901000041000001440010043f0000017a010000410000045b00010430000000060100006b00000000050300190000027e0000c13d0000014701000041000000800010043f0000002001000039000000840010043f0000003f01000039000000a40010043f0000014c01000041000000c40010043f0000014d01000041000000e40010043f0000014e010000410000045b00010430000200000005001d000000c001000039000000400010043f0000000901000039000100000001001d000000000301041a0000014005300197000000800050043f0000008001300270000000a00010043f000001400330009c000500000006001d000300000005001d0000029a0000213d000000000305004b0000029f0000c13d000000000102004b000002fd0000c13d0000014701000041000000c00010043f0000002001000039000000c40010043f0000002101000039000000e40010043f0000017001000041000001040010043f00000171010000410000025e0000013d000000000361004b000002a10000613d000001400210009c000000ad0000613d000002bc0000013d000000050310006c000002bc0000c13d000000000102004b000002f30000c13d0000000302000029000000020120006c000003270000c13d0000000501000029000000010110008a000001400210009c000000ad0000213d0000014001100197000001012110011a0000000b01200039000000000101041a000000040110006b000003980000c13d000000060100006b000003640000613d0000014701000041000000c00010043f0000002001000039000000c40010043f0000003c01000039000000e40010043f0000016601000041000001040010043f00000167010000410000025e0000013d0000000102100039000000050220006c000003090000c13d000000010210008a000001400320009c000000ad0000213d0000000a03000039000000000303041a0000014002200197000001015220011a0000000b02500039000000000202041a000000e00010043f0000000301000029000001000010043f000001200020043f000001400030043f000000c00040043f0000016001000039000000400010043f00000118010000410000000002000414000001180320009c0000000002018019000000c00120021000000156011001c70000801002000039045904540000040f00000001022001900000000403000029000003960000613d000000400200043d000000000101043b000000000113004b000003a20000c13d0000000303000029000000020130006b000003c50000a13d0000015e0120009c000001530000213d0000004001200039000000400010043f000000200120003900000005040000290000000000410435000000020300002900000000003204350000008001400210000000000113019f0000000102000029000000000012041b000000010140008a000001400210009c000000ad0000213d0000035d0000013d0000014701000041000000c00010043f0000002001000039000000c40010043f0000003501000039000000e40010043f0000015f01000041000001040010043f00000160010000410000025e0000013d000000050100006b000003310000c13d0000014701000041000000c00010043f0000002001000039000000c40010043f0000002c01000039000000e40010043f0000016e01000041000001040010043f0000016f010000410000025e0000013d0000014701000041000000c00010043f0000002001000039000000c40010043f0000001b01000039000000e40010043f0000015401000041000002520000013d0000004002100039000000400020043f0000002002100039000000040300002900000000003204350000000502000029000000000021043500000080013002100000014002200197000000000112019f0000000302000029000000000012041b00000064010000390000000001100367000000000101043b0000000602000039000000000012041b00000004010000390000000602000029000000000021041c00000000010000190000045a0001042e0000014701000041000000c00010043f0000002001000039000000c40010043f0000002f01000039000000e40010043f0000016201000041000001040010043f00000163010000410000025e0000013d00000005010000290000014001100041000300000001001d000000e001100210000000e00010043f0000000401000039000000c00010043f0000010001000039000000400010043f00000118010000410000000002000414000001180320009c0000000002018019000000c00120021000000168011001c70000801002000039045904540000040f00000001022001900000000403000029000003960000613d000000400200043d000000000101043b000000000131004b000003ab0000c13d00000003010000290000014001100197000001013110011a0000000b013000390000000403000029000000000031041b0000015e0120009c000001530000213d0000004001200039000000400010043f000000200120003900000005040000290000000000410435000000020300002900000000003204350000008001400210000000000113019f0000000102000029000000000012041b000000010140008a0000014001100197000001012110011a0000000b012000390000000402000029000000000021041b0000000a01000039000000000001041b0000010d01000039000000000201041a000001440320009c000003bf0000813d000000400300043d0000015e0430009c000001530000213d0000004004300039000000400040043f0000010c04000039000000000604041a0000014004600197000000000443043600000080056002700000000000540435000001400660009c000003dc0000213d00000000060304330000014006600198000003dc0000c13d0000000705000039000000000505041a000000800550027000000000005404350000016b02200197000000000225019f000000000021041b000000060600006b000003df0000c13d000000400100043d00000064021000390000016c03000041000000000032043500000044021000390000016d030000410000000000320435000000240210003900000028030000390000000000320435000001470200004100000000002104350000000402100039000000200300003900000000003204350000011802000041000001180310009c0000000001028019000000400110021000000159011001c70000045b0001043000000000010000190000045b000104300000014701000041000000c00010043f0000002001000039000000c40010043f0000003301000039000000e40010043f0000016401000041000001040010043f00000165010000410000025e0000013d00000064012000390000015703000041000000000031043500000044012000390000015803000041000000000031043500000024012000390000002603000039000003b30000013d00000064012000390000016903000041000000000031043500000044012000390000016a030000410000000000310435000000240120003900000027030000390000000000310435000001470100004100000000001204350000000401200039000000200300003900000000003104350000011801000041000001180320009c0000000002018019000000400120021000000159011001c70000045b000104300000000101000029000000000101041a0000010c02000039000000000012041b00000000010000190000045a0001042e00000084012000390000015a03000041000000000031043500000064012000390000015b03000041000000000031043500000044012000390000015c03000041000000000031043500000024012000390000005d030000390000000000310435000001470100004100000000001204350000000401200039000000200300003900000000003104350000011801000041000001180320009c000000000201801900000040012002100000015d011001c70000045b00010430000000060600006b000003e10000c13d000003c30000013d000000060600002900060001006000920000000605500029000001400650009c000000ad0000213d00000000005404350000000205000029000000000053043500000000050404330000014006500197000000050660006c000003ed0000813d0000008005500210000003f40000013d00000005060000290000008005600210000000000252019f000000000021041b00000000006404350000000001030433000200000001001d00000002010000290000014001100197000000000151019f000003c10000013d000000000101004b000003fb0000613d000000000001042d000000400100043d00000044021000390000017203000041000000000032043500000024021000390000001f030000390000000000320435000001470200004100000000002104350000000402100039000000200300003900000000003204350000011802000041000001180310009c000000000102801900000040011002100000017d011001c70000045b000104300000017e0210009c000004120000813d0000004001100039000000400010043f000000000001042d0000017b0100004100000000001004350000004101000039000000040010043f0000017c010000410000045b00010430000000400300043d0000017e0130009c000004250000813d0000004001300039000000400010043f0000000701000039000000000201041a00000020043000390000008001200270000000000014043500000140022001970000000000230435000000000001042d0000017b0100004100000000001004350000004101000039000000040010043f0000017c010000410000045b00010430000000400300043d0000017e0130009c000004380000813d0000004001300039000000400010043f0000000901000039000000000201041a00000020043000390000008001200270000000000014043500000140022001970000000000230435000000000001042d0000017b0100004100000000001004350000004101000039000000040010043f0000017c010000410000045b000104300000011803000041000001180410009c00000000010380190000004001100210000001180420009c00000000020380190000006002200210000000000112019f0000000002000414000001180420009c0000000002038019000000c002200210000000000112019f0000017f011001c70000801002000039045904540000040f0000000102200190000004520000613d000000000101043b000000000001042d00000000010000190000045b0001043000000457002104230000000102000039000000000001042d0000000002000019000000000001042d00000459000004320000045a0001042e0000045b00010430000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffff00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000008e1bc9bf0400000000002000000000000000000000000000000400000010000000000000000000000000000000000000000000000000000000000000000000000000085df51fc00000000000000000000000000000000000000000000000000000000a6ae0aab00000000000000000000000000000000000000000000000000000000d0f2c66200000000000000000000000000000000000000000000000000000000ddeaa8e500000000000000000000000000000000000000000000000000000000ddeaa8e600000000000000000000000000000000000000000000000000000000fe173b9700000000000000000000000000000000000000000000000000000000d0f2c66300000000000000000000000000000000000000000000000000000000d4a4ca0d00000000000000000000000000000000000000000000000000000000a6ae0aac00000000000000000000000000000000000000000000000000000000a851ae7800000000000000000000000000000000000000000000000000000000bf1fe42000000000000000000000000000000000000000000000000000000000938b5f3100000000000000000000000000000000000000000000000000000000938b5f32000000000000000000000000000000000000000000000000000000009a8a059200000000000000000000000000000000000000000000000000000000a0803ef70000000000000000000000000000000000000000000000000000000085df51fd000000000000000000000000000000000000000000000000000000008ac84c0e000000000000000000000000000000000000000000000000000000008e8acf87000000000000000000000000000000000000000000000000000000003635f3e5000000000000000000000000000000000000000000000000000000007877a796000000000000000000000000000000000000000000000000000000007c9bd1f2000000000000000000000000000000000000000000000000000000007c9bd1f30000000000000000000000000000000000000000000000000000000080b41246000000000000000000000000000000000000000000000000000000007877a79700000000000000000000000000000000000000000000000000000000796b89b9000000000000000000000000000000000000000000000000000000003635f3e60000000000000000000000000000000000000000000000000000000042cbb15c000000000000000000000000000000000000000000000000000000006ef25c3a0000000000000000000000000000000000000000000000000000000019cae4610000000000000000000000000000000000000000000000000000000019cae4620000000000000000000000000000000000000000000000000000000029f172ad0000000000000000000000000000000000000000000000000000000030e5ccbd0000000000000000000000000000000000000000000000000000000002fa57790000000000000000000000000000000000000000000000000000000006bed0360000000000000000000000000000000000000000000000000000000006e7517b000000000000000000000000000000000000002000000080000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffff0000000000000000000000000000000000000040000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000200000000000000000000000000000000000020000000e00000000000000000020000000000000000000000000000000000004000000000000000000000000008c379a0000000000000000000000000000000000000000000000000000000005468652063757272656e74206261746368206e756d626572206d7573742062652067726561746572207468616e203000000000000000000000000000000000000000000000000000000000000000000000000084000001000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00005468657265206d7573742062652061207669727475616c20626c6f636b206372656174656420617420746865207374617274206f66207468652062617463680000000000000000000000000000000000000000840000008000000000000000005468652074696d657374616d70206f6620746865204c3220626c6f636b206d7573742062652067726561746572207468616e206f7220657175616c20746f207468652074696d657374616d70206f66207468652063757272656e742062617463680000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000c4000000800000000000000000496e76616c6964206e6577204c3220626c6f636b206e756d62657200000000000000000000000000000000000000000000000064000000c000000000000000000200000000000000000000000000000000000080000000e000000000000000006f727265637400000000000000000000000000000000000000000000000000005468652063757272656e74204c3220626c6f636b206861736820697320696e63000000000000000000000000000000000000008400000000000000000000000074616d70206f66207468652070726576696f7573204c3220626c6f636b0000006b206d7573742062652067726561746572207468616e207468652074696d65735468652074696d657374616d70206f6620746865206e6577204c3220626c6f6300000000000000000000000000000000000000a4000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffbf43616e206e6f74207265757365204c3220626c6f636b206e756d6265722066726f6d207468652070726576696f757320626174636800000000000000000000000000000000000000000000000000000000000084000000c000000000000000005468652074696d657374616d70206f66207468652073616d65204c3220626c6f636b206d7573742062652073616d6500000000000000000000000000000000005468652070726576696f75732068617368206f66207468652073616d65204c3220626c6f636b206d7573742062652073616d650000000000000000000000000043616e206e6f7420637265617465207669727475616c20626c6f636b7320696e20746865206d6964646c65206f6620746865206d696e69626c6f636b000000000200000000000000000000000000000000000004000000e00000000000000000636f7272656374000000000000000000000000000000000000000000000000005468652070726576696f7573204c3220626c6f636b206861736820697320696effffffffffffffffffffffffffffffff00000000000000000000000000000000616c20626c6f636b00000000000000000000000000000000000000000000000043616e277420696e697469616c697a65207468652066697273742076697274754c3220626c6f636b206e756d626572206973206e6576657220657870656374656420746f206265207a65726f000000000000000000000000000000000000000055706772616465207472616e73616374696f6e206d7573742062652066697273740000000000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c792062792074686520626f6f746c6f6164657200000000000000000000000000000000000000006400000080000000000000000054696d657374616d70732073686f756c6420626520696e6372656d656e74616c5468652070726f766964656420626c6f636b206e756d626572206973206e6f7420636f72726563740000000000000000000000000000000000000000000000005468652074696d657374616d70206f6620746865206261746368206d7573742062652067726561746572207468616e207468652074696d657374616d70206f66207468652070726576696f757320626c6f636b0000000000000000000000000000000000000000000000000000000000000000a4000000c000000000000000004e487b710000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000240000000000000000000000000000000000000000000000000000000000000064000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffc00200000000000000000000000000000000000000000000000000000000000000d027bdd27752595955b3394e4e92eb3bd90dc369879cc1209636f3bc179f19bf", + "deployedBytecode": "0x0001000000000002000600000000000200000000000103550000008004000039000000400040043f0000000003010019000000600330027000000118033001970000000102200190000000210000c13d000000040230008c000003960000413d000000000201043b000000e0022002700000011c0520009c000000340000213d0000012e0520009c000000430000a13d0000012f0420009c0000007b0000a13d000001300420009c000000c80000213d000001330120009c000001100000613d000001340120009c000003960000c13d0000000001000416000000000101004b000003960000c13d0000010c01000039000000000101041a0000014001100197000001f10000013d0000000001000416000000000101004b000003960000c13d00000118010000410000000302000039000000000012041b0000000401000039000000000201041a000001190220019700008001022001bf000000000021041b0000011a010000410000000502000039000000000012041b0000002001000039000001000010044300000120000004430000011b010000410000045a0001042e0000011d0420009c000000630000a13d0000011e0420009c000000860000a13d0000011f0420009c000000f80000213d000001220120009c0000003e0000613d000001230120009c000003960000c13d0000000001000416000000000101004b000003960000c13d045904180000040f0000006f0000013d000001380520009c0000009c0000213d0000013c0520009c000001150000613d0000013d0520009c000001570000613d0000013e0220009c000003960000c13d0000000002000416000000000202004b000003960000c13d000000040230008a000000200220008c000003960000413d0000000002000411000080010220008c000002160000c13d0000000a02000039000600000002001d000000000202041a000000a00020043f0000000401100370000000000101043b000000c00010043f0000004002000039000000800020043f000000e001000039000000400010043f000000a0010000390459043e0000040f0000000602000029000001e30000013d000001270420009c000000b30000213d0000012b0420009c000001010000613d0000012c0120009c0000018f0000613d0000012d0120009c000003960000c13d0000000001000416000000000101004b000003960000c13d0459042b0000040f0000014002200197000000400300043d00000020043000390000000000240435000001400110019700000000001304350000011801000041000001180230009c0000000003018019000000400130021000000141011001c70000045a0001042e000001350120009c000001960000613d000001360120009c000001a20000613d000001370120009c000003960000c13d0000000001000416000000000101004b000003960000c13d0000000601000039000001c70000013d000001240420009c000001a90000613d000001250420009c000001ae0000613d000001260120009c000003960000c13d0000000001000416000000000101004b000003960000c13d000000040130008a000000200110008c000003960000413d0000000001000411000080010110008c00000000010000190000000101006039045903f80000040f00000004010000390000000001100367000000000101043b0000000202000039000001e30000013d000001390120009c000001c30000613d0000013a0120009c000001c90000613d0000013b0120009c000003960000c13d0000000001000416000000000101004b000003960000c13d0000000001000411000080010110008c000002160000c13d0000010e01000039000000000201041a0000ffff0320018f0000ffff0430008c000002200000c13d0000017b0100004100000000001004350000001101000039000000040010043f0000017c010000410000045b00010430000001280120009c000001e60000613d000001290120009c000001ed0000613d0000012a0120009c000003960000c13d0000000001000416000000000101004b000003960000c13d045904180000040f00000140022001970000008001100210000000000121019f000000400200043d00000000001204350000011801000041000001180320009c0000000002018019000000400120021000000143011001c70000045a0001042e000001310420009c000001f40000613d000001320220009c000003960000c13d0000000002000416000000000202004b000003960000c13d000000040230008a000000200220008c000003960000413d0000000401100370000000000101043b0000010c02000039000000000202041a000000c003000039000000400030043f00000080062002700000010d02000039000000000302041a0000014005300197000000800050043f0000008002300270000000a00020043f000000000416004b0000000004000019000002440000a13d0000000004160049000001010440008c0000000004000019000002440000813d000000000451004b000002260000813d00000000001004350000000801000039000000200010043f00000118010000410000000002000414000001180320009c0000000002018019000000c00120021000000146011001c70000801002000039045904540000040f0000000102200190000003960000613d000000000101043b000000000401041a000002440000013d000001200420009c000001010000613d000001210120009c000003960000c13d0000000001000416000000000101004b000003960000c13d0000000201000039000001c70000013d0000000002000416000000000202004b000003960000c13d000000040230008a000000200220008c000003960000413d0000000401100370000000000101043b00000000001004350000000801000039000000200010043f000000400200003900000000010000190459043e0000040f000001c70000013d0000000001000416000000000101004b000003960000c13d0000000301000039000001c70000013d0000000002000416000000000202004b000003960000c13d000000040230008a000000800220008c000003960000413d0000000402100370000000000302043b0000002402100370000000000402043b000001400240009c000003960000213d0000004401100370000000000501043b000001400150009c000003960000213d0000000001000411000080010110008c000002160000c13d000000c001000039000000400010043f0000000706000039000000000106041a0000014002100197000000800020043f0000008001100270000000a00010043f000000000224004b0000024c0000a13d000001400210009c000000ad0000613d0000000102100039000000000252004b000002550000c13d000300000006001d000400000005001d000600000003001d0000000902000039000000000202041a0000014002200197000500000004001d000000000224004b000002610000a13d00000000001004350000000801000039000000200010043f00000118010000410000000002000414000001180320009c0000000002018019000000c00120021000000146011001c70000801002000039045904540000040f00000001022001900000000602000029000003960000613d000000000101043b000000000021041b000000400100043d0000015e0210009c000003110000a13d0000017b0100004100000000001004350000004101000039000000b00000013d0000000002000416000000000202004b000003960000c13d000000040230008a000000a00220008c000003960000413d0000000402100370000000000602043b000001400260009c000003960000213d0000002402100370000000000502043b000001400250009c000003960000213d0000004402100370000000000702043b0000006402100370000000000202043b000000000302004b0000000003000019000000010300c039000000000332004b000003960000c13d0000008401100370000000000301043b000001400130009c000003960000213d0000000001000411000080010110008c000002160000c13d000000000102004b000600000003001d000400000007001d0000027e0000613d0000000701000039000000000101041a00000140011001970000000003050019000000000115004b0000026f0000813d0000014701000041000000800010043f0000002001000039000000840010043f0000006101000039000000a40010043f0000014f01000041000000c40010043f0000015001000041000000e40010043f0000015101000041000001040010043f0000015201000041000001240010043f00000153010000410000045b000104300000000001000416000000000101004b000003960000c13d0000010e01000039000000000101041a0000ffff0110018f000001f10000013d0000000001000416000000000101004b000003960000c13d0000000001000411000080010110008c00000000010000190000000101006039045903f80000040f0000010e01000039000000000201041a0000014b02200197000002230000013d0000000001000416000000000101004b000003960000c13d0000010c01000039000000000101041a0000008001100270000001f10000013d0000000001000416000000000101004b000003960000c13d0000000401000039000001ea0000013d0000000002000416000000000202004b000003960000c13d000000040230008a000000200220008c000003960000413d0000000401100370000000000201043b000001420120009c000003960000213d0000000001000411000080010110008c00000000010000190000000101006039000600000002001d045903f80000040f0000000101000039000000000201041a000001190220019700000006022001af000002230000013d0000000001000416000000000101004b000003960000c13d0000000501000039000000000101041a000001f10000013d0000000001000416000000000101004b000003960000c13d000000040130008a000000600110008c000003960000413d0000000001000411000080010110008c00000000010000190000000101006039045903f80000040f000000400100043d0459040d0000040f00000000010003670000002402100370000000000202043b00000080022002100000000403100370000000000303043b0000014003300197000000000223019f0000000703000039000000000023041b0000004401100370000000000101043b0000000602000039000000000012041b00000000010000190000045a0001042e0000000001000416000000000101004b000003960000c13d0000000101000039000000000101041a0000014201100197000001f10000013d0000000001000416000000000101004b000003960000c13d000000000100041a000000800010043f0000013f010000410000045a0001042e0000000001000416000000000101004b000003960000c13d0000000001000411000080010110008c000002160000c13d0000000701000039000000000301041a0000014001300197000000800010043f0000008002300270000000a00020043f0000010002000039000000400020043f0000000902000039000000000402041a0000014002400197000000c00020043f0000008004400270000000e00040043f000001400330009c0000022e0000213d0000014701000041000001000010043f0000002001000039000001040010043f0000002f01000039000001240010043f0000014801000041000001440010043f0000014901000041000001640010043f0000014a010000410000045b000104300000014701000041000000800010043f0000002001000039000000840010043f0000001f01000039000000a40010043f0000017201000041000000c40010043f00000173010000410000045b000104300000014b022001970000000103300039000000000223019f000000000021041b00000000010000190000045a0001042e000001440330009c000002340000413d000000000221004b000002340000413d000001012110011a0000000b01200039000000000401041a000002440000013d0000008001100210000000000112019f0000000302000039000000000012041c00000000010000190000045a0001042e000000e00010043f0000002001000039000000c00010043f0000010001000039000000400010043f00000118010000410000000002000414000001180320009c0000000002018019000000c00120021000000145011001c70000801002000039045904540000040f0000000102200190000003960000613d000000000401043b000000400100043d00000000004104350000011802000041000001180310009c0000000001028019000000400110021000000143011001c70000045a0001042e0000014701000041000000c00010043f0000002001000039000000c40010043f000000e40010043f0000017401000041000001040010043f00000155010000410000045b000104300000014701000041000000c00010043f0000002001000039000000c40010043f0000002801000039000000e40010043f0000017501000041000001040010043f0000017601000041000001240010043f00000161010000410000045b000104300000014701000041000000c00010043f0000002001000039000000c40010043f0000005301000039000000e40010043f0000017701000041000001040010043f0000017801000041000001240010043f0000017901000041000001440010043f0000017a010000410000045b00010430000000060100006b00000000050300190000027e0000c13d0000014701000041000000800010043f0000002001000039000000840010043f0000003f01000039000000a40010043f0000014c01000041000000c40010043f0000014d01000041000000e40010043f0000014e010000410000045b00010430000200000005001d000000c001000039000000400010043f0000000901000039000100000001001d000000000301041a0000014005300197000000800050043f0000008001300270000000a00010043f000001400330009c000500000006001d000300000005001d0000029a0000213d000000000305004b0000029f0000c13d000000000102004b000002fd0000c13d0000014701000041000000c00010043f0000002001000039000000c40010043f0000002101000039000000e40010043f0000017001000041000001040010043f00000171010000410000025e0000013d000000000361004b000002a10000613d000001400210009c000000ad0000613d000002bc0000013d000000050310006c000002bc0000c13d000000000102004b000002f30000c13d0000000302000029000000020120006c000003270000c13d0000000501000029000000010110008a000001400210009c000000ad0000213d0000014001100197000001012110011a0000000b01200039000000000101041a000000040110006b000003980000c13d000000060100006b000003640000613d0000014701000041000000c00010043f0000002001000039000000c40010043f0000003c01000039000000e40010043f0000016601000041000001040010043f00000167010000410000025e0000013d0000000102100039000000050220006c000003090000c13d000000010210008a000001400320009c000000ad0000213d0000000a03000039000000000303041a0000014002200197000001015220011a0000000b02500039000000000202041a000000e00010043f0000000301000029000001000010043f000001200020043f000001400030043f000000c00040043f0000016001000039000000400010043f00000118010000410000000002000414000001180320009c0000000002018019000000c00120021000000156011001c70000801002000039045904540000040f00000001022001900000000403000029000003960000613d000000400200043d000000000101043b000000000113004b000003a20000c13d0000000303000029000000020130006b000003c50000a13d0000015e0120009c000001530000213d0000004001200039000000400010043f000000200120003900000005040000290000000000410435000000020300002900000000003204350000008001400210000000000113019f0000000102000029000000000012041b000000010140008a000001400210009c000000ad0000213d0000035d0000013d0000014701000041000000c00010043f0000002001000039000000c40010043f0000003501000039000000e40010043f0000015f01000041000001040010043f00000160010000410000025e0000013d000000050100006b000003310000c13d0000014701000041000000c00010043f0000002001000039000000c40010043f0000002c01000039000000e40010043f0000016e01000041000001040010043f0000016f010000410000025e0000013d0000014701000041000000c00010043f0000002001000039000000c40010043f0000001b01000039000000e40010043f0000015401000041000002520000013d0000004002100039000000400020043f0000002002100039000000040300002900000000003204350000000502000029000000000021043500000080013002100000014002200197000000000112019f0000000302000029000000000012041b00000064010000390000000001100367000000000101043b0000000602000039000000000012041b00000004010000390000000602000029000000000021041c00000000010000190000045a0001042e0000014701000041000000c00010043f0000002001000039000000c40010043f0000002f01000039000000e40010043f0000016201000041000001040010043f00000163010000410000025e0000013d00000005010000290000014001100041000300000001001d000000e001100210000000e00010043f0000000401000039000000c00010043f0000010001000039000000400010043f00000118010000410000000002000414000001180320009c0000000002018019000000c00120021000000168011001c70000801002000039045904540000040f00000001022001900000000403000029000003960000613d000000400200043d000000000101043b000000000131004b000003ab0000c13d00000003010000290000014001100197000001013110011a0000000b013000390000000403000029000000000031041b0000015e0120009c000001530000213d0000004001200039000000400010043f000000200120003900000005040000290000000000410435000000020300002900000000003204350000008001400210000000000113019f0000000102000029000000000012041b000000010140008a0000014001100197000001012110011a0000000b012000390000000402000029000000000021041b0000000a01000039000000000001041b0000010d01000039000000000201041a000001440320009c000003bf0000813d000000400300043d0000015e0430009c000001530000213d0000004004300039000000400040043f0000010c04000039000000000604041a0000014004600197000000000443043600000080056002700000000000540435000001400660009c000003dc0000213d00000000060304330000014006600198000003dc0000c13d0000000705000039000000000505041a000000800550027000000000005404350000016b02200197000000000225019f000000000021041b000000060600006b000003df0000c13d000000400100043d00000064021000390000016c03000041000000000032043500000044021000390000016d030000410000000000320435000000240210003900000028030000390000000000320435000001470200004100000000002104350000000402100039000000200300003900000000003204350000011802000041000001180310009c0000000001028019000000400110021000000159011001c70000045b0001043000000000010000190000045b000104300000014701000041000000c00010043f0000002001000039000000c40010043f0000003301000039000000e40010043f0000016401000041000001040010043f00000165010000410000025e0000013d00000064012000390000015703000041000000000031043500000044012000390000015803000041000000000031043500000024012000390000002603000039000003b30000013d00000064012000390000016903000041000000000031043500000044012000390000016a030000410000000000310435000000240120003900000027030000390000000000310435000001470100004100000000001204350000000401200039000000200300003900000000003104350000011801000041000001180320009c0000000002018019000000400120021000000159011001c70000045b000104300000000101000029000000000101041a0000010c02000039000000000012041b00000000010000190000045a0001042e00000084012000390000015a03000041000000000031043500000064012000390000015b03000041000000000031043500000044012000390000015c03000041000000000031043500000024012000390000005d030000390000000000310435000001470100004100000000001204350000000401200039000000200300003900000000003104350000011801000041000001180320009c000000000201801900000040012002100000015d011001c70000045b00010430000000060600006b000003e10000c13d000003c30000013d000000060600002900060001006000920000000605500029000001400650009c000000ad0000213d00000000005404350000000205000029000000000053043500000000050404330000014006500197000000050660006c000003ed0000813d0000008005500210000003f40000013d00000005060000290000008005600210000000000252019f000000000021041b00000000006404350000000001030433000200000001001d00000002010000290000014001100197000000000151019f000003c10000013d000000000101004b000003fb0000613d000000000001042d000000400100043d00000044021000390000017203000041000000000032043500000024021000390000001f030000390000000000320435000001470200004100000000002104350000000402100039000000200300003900000000003204350000011802000041000001180310009c000000000102801900000040011002100000017d011001c70000045b000104300000017e0210009c000004120000813d0000004001100039000000400010043f000000000001042d0000017b0100004100000000001004350000004101000039000000040010043f0000017c010000410000045b00010430000000400300043d0000017e0130009c000004250000813d0000004001300039000000400010043f0000000701000039000000000201041a00000020043000390000008001200270000000000014043500000140022001970000000000230435000000000001042d0000017b0100004100000000001004350000004101000039000000040010043f0000017c010000410000045b00010430000000400300043d0000017e0130009c000004380000813d0000004001300039000000400010043f0000000901000039000000000201041a00000020043000390000008001200270000000000014043500000140022001970000000000230435000000000001042d0000017b0100004100000000001004350000004101000039000000040010043f0000017c010000410000045b000104300000011803000041000001180410009c00000000010380190000004001100210000001180420009c00000000020380190000006002200210000000000112019f0000000002000414000001180420009c0000000002038019000000c002200210000000000112019f0000017f011001c70000801002000039045904540000040f0000000102200190000004520000613d000000000101043b000000000001042d00000000010000190000045b0001043000000457002104230000000102000039000000000001042d0000000002000019000000000001042d00000459000004320000045a0001042e0000045b00010430000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffff00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000008e1bc9bf0400000000002000000000000000000000000000000400000010000000000000000000000000000000000000000000000000000000000000000000000000085df51fc00000000000000000000000000000000000000000000000000000000a6ae0aab00000000000000000000000000000000000000000000000000000000d0f2c66200000000000000000000000000000000000000000000000000000000ddeaa8e500000000000000000000000000000000000000000000000000000000ddeaa8e600000000000000000000000000000000000000000000000000000000fe173b9700000000000000000000000000000000000000000000000000000000d0f2c66300000000000000000000000000000000000000000000000000000000d4a4ca0d00000000000000000000000000000000000000000000000000000000a6ae0aac00000000000000000000000000000000000000000000000000000000a851ae7800000000000000000000000000000000000000000000000000000000bf1fe42000000000000000000000000000000000000000000000000000000000938b5f3100000000000000000000000000000000000000000000000000000000938b5f32000000000000000000000000000000000000000000000000000000009a8a059200000000000000000000000000000000000000000000000000000000a0803ef70000000000000000000000000000000000000000000000000000000085df51fd000000000000000000000000000000000000000000000000000000008ac84c0e000000000000000000000000000000000000000000000000000000008e8acf87000000000000000000000000000000000000000000000000000000003635f3e5000000000000000000000000000000000000000000000000000000007877a796000000000000000000000000000000000000000000000000000000007c9bd1f2000000000000000000000000000000000000000000000000000000007c9bd1f30000000000000000000000000000000000000000000000000000000080b41246000000000000000000000000000000000000000000000000000000007877a79700000000000000000000000000000000000000000000000000000000796b89b9000000000000000000000000000000000000000000000000000000003635f3e60000000000000000000000000000000000000000000000000000000042cbb15c000000000000000000000000000000000000000000000000000000006ef25c3a0000000000000000000000000000000000000000000000000000000019cae4610000000000000000000000000000000000000000000000000000000019cae4620000000000000000000000000000000000000000000000000000000029f172ad0000000000000000000000000000000000000000000000000000000030e5ccbd0000000000000000000000000000000000000000000000000000000002fa57790000000000000000000000000000000000000000000000000000000006bed0360000000000000000000000000000000000000000000000000000000006e7517b000000000000000000000000000000000000002000000080000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffff0000000000000000000000000000000000000040000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffff000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000200000000000000000000000000000000000020000000e00000000000000000020000000000000000000000000000000000004000000000000000000000000008c379a0000000000000000000000000000000000000000000000000000000005468652063757272656e74206261746368206e756d626572206d7573742062652067726561746572207468616e203000000000000000000000000000000000000000000000000000000000000000000000000084000001000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00005468657265206d7573742062652061207669727475616c20626c6f636b206372656174656420617420746865207374617274206f66207468652062617463680000000000000000000000000000000000000000840000008000000000000000005468652074696d657374616d70206f6620746865204c3220626c6f636b206d7573742062652067726561746572207468616e206f7220657175616c20746f207468652074696d657374616d70206f66207468652063757272656e742062617463680000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000c4000000800000000000000000496e76616c6964206e6577204c3220626c6f636b206e756d62657200000000000000000000000000000000000000000000000064000000c000000000000000000200000000000000000000000000000000000080000000e000000000000000006f727265637400000000000000000000000000000000000000000000000000005468652063757272656e74204c3220626c6f636b206861736820697320696e63000000000000000000000000000000000000008400000000000000000000000074616d70206f66207468652070726576696f7573204c3220626c6f636b0000006b206d7573742062652067726561746572207468616e207468652074696d65735468652074696d657374616d70206f6620746865206e6577204c3220626c6f6300000000000000000000000000000000000000a4000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffbf43616e206e6f74207265757365204c3220626c6f636b206e756d6265722066726f6d207468652070726576696f757320626174636800000000000000000000000000000000000000000000000000000000000084000000c000000000000000005468652074696d657374616d70206f66207468652073616d65204c3220626c6f636b206d7573742062652073616d6500000000000000000000000000000000005468652070726576696f75732068617368206f66207468652073616d65204c3220626c6f636b206d7573742062652073616d650000000000000000000000000043616e206e6f7420637265617465207669727475616c20626c6f636b7320696e20746865206d6964646c65206f6620746865206d696e69626c6f636b000000000200000000000000000000000000000000000004000000e00000000000000000636f7272656374000000000000000000000000000000000000000000000000005468652070726576696f7573204c3220626c6f636b206861736820697320696effffffffffffffffffffffffffffffff00000000000000000000000000000000616c20626c6f636b00000000000000000000000000000000000000000000000043616e277420696e697469616c697a65207468652066697273742076697274754c3220626c6f636b206e756d626572206973206e6576657220657870656374656420746f206265207a65726f000000000000000000000000000000000000000055706772616465207472616e73616374696f6e206d7573742062652066697273740000000000000000000000000000000000000000000000000000000000000043616c6c61626c65206f6e6c792062792074686520626f6f746c6f6164657200000000000000000000000000000000000000006400000080000000000000000054696d657374616d70732073686f756c6420626520696e6372656d656e74616c5468652070726f766964656420626c6f636b206e756d626572206973206e6f7420636f72726563740000000000000000000000000000000000000000000000005468652074696d657374616d70206f6620746865206261746368206d7573742062652067726561746572207468616e207468652074696d657374616d70206f66207468652070726576696f757320626c6f636b0000000000000000000000000000000000000000000000000000000000000000a4000000c000000000000000004e487b710000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000240000000000000000000000000000000000000000000000000000000000000064000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffc00200000000000000000000000000000000000000000000000000000000000000d027bdd27752595955b3394e4e92eb3bd90dc369879cc1209636f3bc179f19bf", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/contracts/fee_estimate.yul.zbin b/.test-node-subtree/src/deps/contracts/fee_estimate.yul.zbin new file mode 100644 index 00000000..837793d3 Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/fee_estimate.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/fee_estimate_impersonating.yul.zbin b/.test-node-subtree/src/deps/contracts/fee_estimate_impersonating.yul.zbin new file mode 100644 index 00000000..d64c6933 Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/fee_estimate_impersonating.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/gas_test.yul.zbin b/.test-node-subtree/src/deps/contracts/gas_test.yul.zbin new file mode 100644 index 00000000..2f66731b Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/gas_test.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/playground_batch.yul.zbin b/.test-node-subtree/src/deps/contracts/playground_batch.yul.zbin new file mode 100644 index 00000000..bdaf4f66 Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/playground_batch.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/proved_batch.yul.zbin b/.test-node-subtree/src/deps/contracts/proved_batch.yul.zbin new file mode 100644 index 00000000..9d68bf2e Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/proved_batch.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/proved_batch_impersonating.yul.zbin b/.test-node-subtree/src/deps/contracts/proved_batch_impersonating.yul.zbin new file mode 100644 index 00000000..b90c9b81 Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/proved_batch_impersonating.yul.zbin differ diff --git a/.test-node-subtree/src/deps/contracts/secp256k1VERIFY.yul.zbin b/.test-node-subtree/src/deps/contracts/secp256k1VERIFY.yul.zbin new file mode 100644 index 00000000..9d9ec8ec Binary files /dev/null and b/.test-node-subtree/src/deps/contracts/secp256k1VERIFY.yul.zbin differ diff --git a/.test-node-subtree/src/deps/mod.rs b/.test-node-subtree/src/deps/mod.rs new file mode 100644 index 00000000..0ce904a5 --- /dev/null +++ b/.test-node-subtree/src/deps/mod.rs @@ -0,0 +1,95 @@ +use std::collections::HashMap; +pub mod system_contracts; +use zksync_types::{ + get_code_key, get_system_context_init_logs, L2ChainId, StorageKey, StorageLog, StorageLogKind, + StorageValue, H256, +}; +pub mod storage_view; +use zksync_state::ReadStorage; + +/// In-memory storage. +#[derive(Debug, Default, Clone, PartialEq)] +pub struct InMemoryStorage { + pub(crate) state: HashMap, + pub(crate) factory_deps: HashMap>, +} + +impl InMemoryStorage { + /// Constructs a storage that contains system smart contracts (with a given chain id). + pub fn with_system_contracts_and_chain_id( + chain_id: L2ChainId, + bytecode_hasher: impl Fn(&[u8]) -> H256, + system_contracts_options: &crate::system_contracts::Options, + ) -> Self { + let contracts = crate::system_contracts::get_deployed_contracts(system_contracts_options); + + let system_context_init_log = get_system_context_init_logs(chain_id); + + let state = contracts + .iter() + .map(|contract| { + let deployer_code_key = get_code_key(contract.account_id.address()); + StorageLog::new_write_log(deployer_code_key, bytecode_hasher(&contract.bytecode)) + }) + .chain(system_context_init_log) + .filter_map(|log| (log.kind == StorageLogKind::Write).then_some((log.key, log.value))) + .collect(); + + let factory_deps = contracts + .into_iter() + .map(|contract| (bytecode_hasher(&contract.bytecode), contract.bytecode)) + .collect(); + Self { + state, + factory_deps, + } + } + + /// Sets the storage `value` at the specified `key`. + pub fn set_value(&mut self, key: StorageKey, value: StorageValue) { + self.state.insert(key, value); + } + + /// Stores a factory dependency with the specified `hash` and `bytecode`. + pub fn store_factory_dep(&mut self, hash: H256, bytecode: Vec) { + self.factory_deps.insert(hash, bytecode); + } +} + +impl ReadStorage for &InMemoryStorage { + fn read_value(&mut self, key: &StorageKey) -> StorageValue { + self.state.get(key).copied().unwrap_or_default() + } + + fn is_write_initial(&mut self, key: &StorageKey) -> bool { + !self.state.contains_key(key) + } + + fn load_factory_dep(&mut self, hash: H256) -> Option> { + self.factory_deps.get(&hash).cloned() + } + + fn get_enumeration_index(&mut self, _key: &StorageKey) -> Option { + // TODO: Update this file to use proper enumeration index value once it's exposed for forks via API + // This should happen as the migration of Boojum completes + Some(0_u64) + } +} + +impl ReadStorage for InMemoryStorage { + fn read_value(&mut self, key: &StorageKey) -> StorageValue { + (&*self).read_value(key) + } + + fn is_write_initial(&mut self, key: &StorageKey) -> bool { + (&*self).is_write_initial(key) + } + + fn load_factory_dep(&mut self, hash: H256) -> Option> { + (&*self).load_factory_dep(hash) + } + + fn get_enumeration_index(&mut self, key: &StorageKey) -> Option { + (&*self).get_enumeration_index(key) + } +} diff --git a/.test-node-subtree/src/deps/storage_view.rs b/.test-node-subtree/src/deps/storage_view.rs new file mode 100644 index 00000000..feb341e0 --- /dev/null +++ b/.test-node-subtree/src/deps/storage_view.rs @@ -0,0 +1,164 @@ +use std::{cell::RefCell, collections::HashMap, fmt, rc::Rc}; + +use zksync_state::{ReadStorage, WriteStorage}; +use zksync_types::{StorageKey, StorageValue, H256}; + +/// `StorageView` is a buffer for `StorageLog`s between storage and transaction execution code. +/// In order to commit transactions logs should be submitted to the underlying storage +/// after a transaction is executed. +/// +/// When executing transactions as a part of miniblock / L1 batch creation, +/// a single `StorageView` is used for the entire L1 batch. +/// One `StorageView` must not be used for multiple L1 batches; +/// otherwise, [`Self::is_write_initial()`] will return incorrect values because of the caching. +/// +/// When executing transactions in the API sandbox, a dedicated view is used for each transaction; +/// the only shared part is the read storage keys cache. +#[derive(Debug)] +pub struct StorageView { + pub storage_handle: S, + // Used for caching and to get the list/count of modified keys + pub modified_storage_keys: HashMap, + // Used purely for caching + read_storage_keys: HashMap, + // Cache for `contains_key()` checks. The cache is only valid within one L1 batch execution. + initial_writes_cache: HashMap, +} + +impl StorageView { + /// Creates a new storage view based on the underlying storage. + pub fn new(storage_handle: S) -> Self { + Self { + storage_handle, + modified_storage_keys: HashMap::new(), + read_storage_keys: HashMap::new(), + initial_writes_cache: HashMap::new(), + } + } + + #[allow(dead_code)] + pub fn clean_cache(&mut self) { + self.modified_storage_keys = Default::default(); + self.read_storage_keys = Default::default(); + self.initial_writes_cache = Default::default(); + } + + fn get_value_no_log(&mut self, key: &StorageKey) -> StorageValue { + let cached_value = self + .modified_storage_keys + .get(key) + .or_else(|| self.read_storage_keys.get(key)); + cached_value.copied().unwrap_or_else(|| { + let value = self.storage_handle.read_value(key); + self.read_storage_keys.insert(*key, value); + value + }) + } + /// Make a Rc RefCell ptr to the storage + pub fn into_rc_ptr(self) -> Rc> { + Rc::new(RefCell::new(self)) + } +} + +impl ReadStorage for StorageView { + fn read_value(&mut self, key: &StorageKey) -> StorageValue { + let value = self.get_value_no_log(key); + + tracing::trace!( + "read value {:?} {:?} ({:?}/{:?})", + key.hashed_key().0, + value.0, + key.address(), + key.key() + ); + + value + } + + /// Only keys contained in the underlying storage will return `false`. If a key was + /// inserted using [`Self::set_value()`], it will still return `true`. + fn is_write_initial(&mut self, key: &StorageKey) -> bool { + if let Some(&is_write_initial) = self.initial_writes_cache.get(key) { + is_write_initial + } else { + let is_write_initial = self.storage_handle.is_write_initial(key); + self.initial_writes_cache.insert(*key, is_write_initial); + is_write_initial + } + } + + fn load_factory_dep(&mut self, hash: H256) -> Option> { + self.storage_handle.load_factory_dep(hash) + } + + fn get_enumeration_index(&mut self, key: &StorageKey) -> Option { + self.storage_handle.get_enumeration_index(key) + } +} + +impl WriteStorage for StorageView { + fn set_value(&mut self, key: StorageKey, value: StorageValue) -> StorageValue { + let original = self.get_value_no_log(&key); + + tracing::trace!( + "write value {:?} value: {:?} original value: {:?} ({:?}/{:?})", + key.hashed_key().0, + value, + original, + key.address(), + key.key() + ); + self.modified_storage_keys.insert(key, value); + + original + } + + fn modified_storage_keys(&self) -> &HashMap { + &self.modified_storage_keys + } + + fn missed_storage_invocations(&self) -> usize { + 0 + } +} + +#[cfg(test)] +mod test { + use super::*; + use crate::deps::InMemoryStorage; + use zksync_types::{AccountTreeId, Address, H256}; + + #[test] + fn test_storage_access() { + let account: AccountTreeId = AccountTreeId::new(Address::from([0xfe; 20])); + let key = H256::from_low_u64_be(61); + let value = H256::from_low_u64_be(73); + let key = StorageKey::new(account, key); + + let mut raw_storage = InMemoryStorage::default(); + let mut storage_view = StorageView::new(&raw_storage); + + let default_value = storage_view.read_value(&key); + assert_eq!(default_value, H256::zero()); + + let prev_value = storage_view.set_value(key, value); + assert_eq!(prev_value, H256::zero()); + assert_eq!(storage_view.read_value(&key), value); + assert!(storage_view.is_write_initial(&key)); // key was inserted during the view lifetime + + raw_storage.set_value(key, value); + let mut storage_view = StorageView::new(&raw_storage); + + assert_eq!(storage_view.read_value(&key), value); + assert!(!storage_view.is_write_initial(&key)); // `key` is present in `raw_storage` + + let new_value = H256::from_low_u64_be(74); + storage_view.set_value(key, new_value); + assert_eq!(storage_view.read_value(&key), new_value); + + let new_key = StorageKey::new(account, H256::from_low_u64_be(62)); + storage_view.set_value(new_key, new_value); + assert_eq!(storage_view.read_value(&new_key), new_value); + assert!(storage_view.is_write_initial(&new_key)); + } +} diff --git a/.test-node-subtree/src/deps/system_contracts.rs b/.test-node-subtree/src/deps/system_contracts.rs new file mode 100644 index 00000000..0dddd2d6 --- /dev/null +++ b/.test-node-subtree/src/deps/system_contracts.rs @@ -0,0 +1,200 @@ +use once_cell::sync::Lazy; +use serde_json::Value; +use zksync_basic_types::{AccountTreeId, Address, H160}; +use zksync_types::{ + block::DeployedContract, ACCOUNT_CODE_STORAGE_ADDRESS, BOOTLOADER_ADDRESS, + BOOTLOADER_UTILITIES_ADDRESS, COMPRESSOR_ADDRESS, CONTRACT_DEPLOYER_ADDRESS, + ECRECOVER_PRECOMPILE_ADDRESS, EVENT_WRITER_ADDRESS, IMMUTABLE_SIMULATOR_STORAGE_ADDRESS, + KECCAK256_PRECOMPILE_ADDRESS, KNOWN_CODES_STORAGE_ADDRESS, L1_MESSENGER_ADDRESS, + L2_ETH_TOKEN_ADDRESS, MSG_VALUE_SIMULATOR_ADDRESS, NONCE_HOLDER_ADDRESS, + SHA256_PRECOMPILE_ADDRESS, SYSTEM_CONTEXT_ADDRESS, +}; + +/// The `ecAdd` system contract address. +pub const ECADD_PRECOMPILE_ADDRESS: Address = H160([ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x06, +]); + +/// The `ecMul` system contract address. +pub const ECMUL_PRECOMPILE_ADDRESS: Address = H160([ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x07, +]); + +/// The `ecPairing` system contract address. +pub const ECPAIRING_PRECOMPILE_ADDRESS: Address = H160([ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x08, +]); + +/// The `p256Verify` system contract address. +pub const P256VERIFY_PRECOMPILE_ADDRESS: Address = H160([ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x19, +]); + +/// The `secp256k1VERIFY` system contract address. +pub const SECP256K1VERIFY_PRECOMPILE_ADDRESS: Address = H160([ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x20, +]); + +/// The `modexp` system contract address. +pub const MODEXP_PRECOMPILE_ADDRESS: Address = H160([ + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x05, +]); + + +pub fn bytecode_from_slice(artifact_name: &str, contents: &[u8]) -> Vec { + let artifact: Value = serde_json::from_slice(contents).expect(artifact_name); + let bytecode = artifact["bytecode"] + .as_str() + .unwrap_or_else(|| panic!("Bytecode not found in {:?}", artifact_name)) + .strip_prefix("0x") + .unwrap_or_else(|| panic!("Bytecode in {:?} is not hex", artifact_name)); + + hex::decode(bytecode) + .unwrap_or_else(|err| panic!("Can't decode bytecode in {:?}: {}", artifact_name, err)) +} + +pub static COMPILED_IN_SYSTEM_CONTRACTS: Lazy> = Lazy::new(|| { + let mut deployed_system_contracts = [ + ( + "AccountCodeStorage", + ACCOUNT_CODE_STORAGE_ADDRESS, + include_bytes!("contracts/AccountCodeStorage.json").to_vec(), + ), + ( + "NonceHolder", + NONCE_HOLDER_ADDRESS, + include_bytes!("contracts/NonceHolder.json").to_vec(), + ), + ( + "KnownCodesStorage", + KNOWN_CODES_STORAGE_ADDRESS, + include_bytes!("contracts/KnownCodesStorage.json").to_vec(), + ), + ( + "ImmutableSimulator", + IMMUTABLE_SIMULATOR_STORAGE_ADDRESS, + include_bytes!("contracts/ImmutableSimulator.json").to_vec(), + ), + ( + "ContractDeployer", + CONTRACT_DEPLOYER_ADDRESS, + include_bytes!("contracts/ContractDeployer.json").to_vec(), + ), + ( + "L1Messenger", + L1_MESSENGER_ADDRESS, + include_bytes!("contracts/L1Messenger.json").to_vec(), + ), + ( + "MsgValueSimulator", + MSG_VALUE_SIMULATOR_ADDRESS, + include_bytes!("contracts/MsgValueSimulator.json").to_vec(), + ), + ( + "L2EthToken", + L2_ETH_TOKEN_ADDRESS, + include_bytes!("contracts/L2EthToken.json").to_vec(), + ), + ( + "SystemContext", + SYSTEM_CONTEXT_ADDRESS, + include_bytes!("contracts/SystemContext.json").to_vec(), + ), + ( + "BootloaderUtilities", + BOOTLOADER_UTILITIES_ADDRESS, + include_bytes!("contracts/BootloaderUtilities.json").to_vec(), + ), + ( + "Compressor", + COMPRESSOR_ADDRESS, + include_bytes!("contracts/Compressor.json").to_vec(), + ), + ] + .map(|(pname, address, contents)| DeployedContract { + account_id: AccountTreeId::new(address), + + bytecode: bytecode_from_slice(pname, &contents), + }) + .to_vec(); + + let yul_contracts = [ + ( + "Keccak256", + KECCAK256_PRECOMPILE_ADDRESS, + include_bytes!("contracts/Keccak256.yul.zbin").to_vec(), + ), + ( + "SHA256", + SHA256_PRECOMPILE_ADDRESS, + include_bytes!("contracts/SHA256.yul.zbin").to_vec(), + ), + ( + "Ecrecover", + ECRECOVER_PRECOMPILE_ADDRESS, + include_bytes!("contracts/Ecrecover.yul.zbin").to_vec(), + ), + ( + "EventWriter", + EVENT_WRITER_ADDRESS, + include_bytes!("contracts/EventWriter.yul.zbin").to_vec(), + ), + ( + "ECADD_PRECOMPILE_ADDRESS", + ECADD_PRECOMPILE_ADDRESS, + include_bytes!("contracts/EcAdd.yul.zbin").to_vec(), + ), + ( + "ECMUL_PRECOMPILE_ADDRESS", + ECMUL_PRECOMPILE_ADDRESS, + include_bytes!("contracts/EcMul.yul.zbin").to_vec(), + ), + ( + "ECPAIRING_PRECOMPILE_ADDRESS", + ECPAIRING_PRECOMPILE_ADDRESS, + include_bytes!("contracts/EcPairing.yul.zbin").to_vec(), + ), + ( + "P256VERIFY_PRECOMPILE_ADDRESS", + P256VERIFY_PRECOMPILE_ADDRESS, + include_bytes!("contracts/P256VERIFY.yul.zbin").to_vec(), + ), + ( + "secp256k1VERIFY_PRECOMPILE_ADDRESS", + SECP256K1VERIFY_PRECOMPILE_ADDRESS, + include_bytes!("contracts/secp256k1VERIFY.yul.zbin").to_vec(), + ), + ( + "MODEXP_PRECOMPILE_ADDRESS", + MODEXP_PRECOMPILE_ADDRESS, + include_bytes!("contracts/ModExp.yul.zbin").to_vec(), + ), + ] + .map(|(_pname, address, contents)| DeployedContract { + account_id: AccountTreeId::new(address), + bytecode: contents, + }); + + deployed_system_contracts.extend(yul_contracts); + + let empty_bytecode = bytecode_from_slice( + "EmptyContract", + include_bytes!("contracts/EmptyContract.json"), + ); + // For now, only zero address and the bootloader address have empty bytecode at the init + // In the future, we might want to set all of the system contracts this way. + let empty_system_contracts = + [Address::zero(), BOOTLOADER_ADDRESS].map(|address| DeployedContract { + account_id: AccountTreeId::new(address), + bytecode: empty_bytecode.clone(), + }); + + deployed_system_contracts.extend(empty_system_contracts); + deployed_system_contracts +}); diff --git a/.test-node-subtree/src/deps/test-contracts/Primary.json b/.test-node-subtree/src/deps/test-contracts/Primary.json new file mode 100644 index 00000000..d9c096e8 --- /dev/null +++ b/.test-node-subtree/src/deps/test-contracts/Primary.json @@ -0,0 +1,68 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "Primary", + "sourceName": "cache-zk/solpp-generated-contracts/tracing/Primary.sol", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_secondary", + "type": "address" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + } + ], + "name": "calculate", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "pure", + "type": "function" + }, + { + "inputs": [], + "name": "shouldRevert", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + } + ], + "bytecode": "0x00030000000000020001000000000002000200000001035500000060011002700000006d0010019d000100000000001f00000001012001900000004b0000c13d0000008001000039000000400010043f0000000001000031000000040110008c000000c30000413d0000000201000367000000000101043b000000e001100270000000730210009c000000b20000613d000000740210009c0000008f0000613d000000750110009c000000c30000c13d0000000001000416000000000101004b000000c30000c13d000000040100008a00000000011000310000006f02000041000000000301004b000000000300001900000000030240190000006f01100197000000000401004b000000000200a0190000006f0110009c00000000010300190000000001026019000000000101004b000000c30000c13d000000c001000039000000400010043f0000000701000039000000800010043f0000007d01000041000000a00010043f0000002002000039000000400100043d0000000003210436000000800200043d00000000002304350000004003100039000000000402004b0000003d0000613d00000000040000190000000005340019000000a006400039000000000606043300000000006504350000002004400039000000000524004b000000360000413d000000000332001900000000000304350000005f02200039000000200300008a000000000232016f0000006d030000410000006d0420009c00000000020380190000006d0410009c000000000103801900000040011002100000006002200210000000000112019f000001ae0001042e0000000001000416000000000101004b000000c30000c13d00000000010000310000009f02100039000000200300008a000000000232016f0000006e0320009c0000005a0000413d0000007c0100004100000000001004350000004101000039000000040010043f0000007b01000041000001af00010430000000400020043f0000001f0210018f00000002030003670000000504100272000000680000613d00000000050000190000000506500210000000000763034f000000000707043b000000800660003900000000007604350000000105500039000000000645004b000000600000413d000000000502004b000000770000613d0000000504400210000000000343034f00000003022002100000008004400039000000000504043300000000052501cf000000000525022f000000000303043b0000010002200089000000000323022f00000000022301cf000000000252019f00000000002404350000006f02000041000000200310008c000000000300001900000000030240190000006f01100197000000000401004b000000000200a0190000006f0110009c00000000010300190000000001026019000000000101004b000000c30000c13d000000800100043d000000700210009c000000c30000213d000000000200041a0000007102200197000000000112019f000000000010041b0000002001000039000001000010044300000120000004430000007201000041000001ae0001042e0000000001000416000000000101004b000000c30000c13d000000040100008a00000000011000310000006f02000041000000200310008c000000000300001900000000030240190000006f01100197000000000401004b000000000200a0190000006f0110009c00000000010300190000000001026019000000000101004b000000c30000c13d000000000200041a000000400a00043d0000007a0100004100000000001a043500000004010000390000000201100367000000000101043b0000000403a00039000000000013043500000000010004140000007002200197000000040320008c000000d20000c13d0000000103000031000000200130008c00000020040000390000000004034019000001020000013d0000000001000416000000000101004b000000c30000c13d000000040100008a00000000011000310000006f02000041000000000301004b000000000300001900000000030240190000006f01100197000000000401004b000000000200a0190000006f0110009c00000000010300190000000001026019000000000101004b000000c50000613d0000000001000019000001af00010430000000000200041a000000400a00043d000000760100004100000000001a043500000000010004140000007002200197000000040320008c000001170000c13d0000000103000031000000200130008c00000020040000390000000004034019000001470000013d0000006d030000410000006d0410009c00000000010380190000006d04a0009c00000000030a40190000004003300210000000c001100210000000000131019f0000007b011001c700010000000a001d01ad01a80000040f000000010a000029000000000301001900000060033002700000006d03300197000000200430008c000000200400003900000000040340190000001f0540018f0000000506400272000000f00000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b000000e80000413d000000000705004b000000ff0000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f00000001022001900000015c0000613d0000001f01400039000000600210018f0000000001a20019000000000221004b00000000020000190000000102004039000000780410009c000000540000213d0000000102200190000000540000c13d000000400010043f000000200230008c000000c30000413d00000000020a043300000000002104350000006d020000410000006d0310009c0000000001028019000000400110021000000079011001c7000001ae0001042e0000006d030000410000006d0410009c00000000010380190000006d04a0009c00000000030a40190000004003300210000000c001100210000000000131019f00000077011001c700010000000a001d01ad01a80000040f000000010a000029000000000301001900000060033002700000006d03300197000000200430008c000000200400003900000000040340190000001f0540018f0000000506400272000001350000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b0000012d0000413d000000000705004b000001440000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f0000000102200190000001820000613d0000001f01400039000000600210018f0000000001a20019000000000221004b00000000020000190000000102004039000000780410009c000000540000213d0000000102200190000000540000c13d000000400010043f000000200230008c000000c30000413d00000000020a043300000000002104350000006d020000410000006d0310009c0000000001028019000000400110021000000079011001c7000001ae0001042e000000400200043d0000001f0430018f0000000503300272000001690000613d000000000500001900000005065002100000000007620019000000000661034f000000000606043b00000000006704350000000105500039000000000635004b000001610000413d000000000504004b000001780000613d0000000503300210000000000131034f00000000033200190000000304400210000000000503043300000000054501cf000000000545022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001304350000006d0100004100000001030000310000006d0430009c00000000030180190000006d0420009c000000000102401900000040011002100000006002300210000000000112019f000001af00010430000000400200043d0000001f0430018f00000005033002720000018f0000613d000000000500001900000005065002100000000007620019000000000661034f000000000606043b00000000006704350000000105500039000000000635004b000001870000413d000000000504004b0000019e0000613d0000000503300210000000000131034f00000000033200190000000304400210000000000503043300000000054501cf000000000545022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001304350000006d0100004100000001030000310000006d0430009c00000000030180190000006d0420009c000000000102401900000040011002100000006002300210000000000112019f000001af00010430000001ab002104230000000102000039000000000001042d0000000002000019000000000001042d000001ad00000432000001ae0001042e000001af00010430000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff00000000000000000000000000000000000000000000000100000000000000008000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000000000000000000000000000000000000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000d3072d8200000000000000000000000000000000000000000000000000000000b9d92de80000000000000000000000000000000000000000000000000000000006fdde03d3072d82000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffff0000000000000000000000000000000000000020000000000000000000000000c6888fa10000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000240000000000000000000000004e487b71000000000000000000000000000000000000000000000000000000005072696d617279000000000000000000000000000000000000000000000000009c917ca34a24c60aac10aab9022e5996487bc34dbb282973dfb468de4a087199", + "deployedBytecode": "0x00030000000000020001000000000002000200000001035500000060011002700000006d0010019d000100000000001f00000001012001900000004b0000c13d0000008001000039000000400010043f0000000001000031000000040110008c000000c30000413d0000000201000367000000000101043b000000e001100270000000730210009c000000b20000613d000000740210009c0000008f0000613d000000750110009c000000c30000c13d0000000001000416000000000101004b000000c30000c13d000000040100008a00000000011000310000006f02000041000000000301004b000000000300001900000000030240190000006f01100197000000000401004b000000000200a0190000006f0110009c00000000010300190000000001026019000000000101004b000000c30000c13d000000c001000039000000400010043f0000000701000039000000800010043f0000007d01000041000000a00010043f0000002002000039000000400100043d0000000003210436000000800200043d00000000002304350000004003100039000000000402004b0000003d0000613d00000000040000190000000005340019000000a006400039000000000606043300000000006504350000002004400039000000000524004b000000360000413d000000000332001900000000000304350000005f02200039000000200300008a000000000232016f0000006d030000410000006d0420009c00000000020380190000006d0410009c000000000103801900000040011002100000006002200210000000000112019f000001ae0001042e0000000001000416000000000101004b000000c30000c13d00000000010000310000009f02100039000000200300008a000000000232016f0000006e0320009c0000005a0000413d0000007c0100004100000000001004350000004101000039000000040010043f0000007b01000041000001af00010430000000400020043f0000001f0210018f00000002030003670000000504100272000000680000613d00000000050000190000000506500210000000000763034f000000000707043b000000800660003900000000007604350000000105500039000000000645004b000000600000413d000000000502004b000000770000613d0000000504400210000000000343034f00000003022002100000008004400039000000000504043300000000052501cf000000000525022f000000000303043b0000010002200089000000000323022f00000000022301cf000000000252019f00000000002404350000006f02000041000000200310008c000000000300001900000000030240190000006f01100197000000000401004b000000000200a0190000006f0110009c00000000010300190000000001026019000000000101004b000000c30000c13d000000800100043d000000700210009c000000c30000213d000000000200041a0000007102200197000000000112019f000000000010041b0000002001000039000001000010044300000120000004430000007201000041000001ae0001042e0000000001000416000000000101004b000000c30000c13d000000040100008a00000000011000310000006f02000041000000200310008c000000000300001900000000030240190000006f01100197000000000401004b000000000200a0190000006f0110009c00000000010300190000000001026019000000000101004b000000c30000c13d000000000200041a000000400a00043d0000007a0100004100000000001a043500000004010000390000000201100367000000000101043b0000000403a00039000000000013043500000000010004140000007002200197000000040320008c000000d20000c13d0000000103000031000000200130008c00000020040000390000000004034019000001020000013d0000000001000416000000000101004b000000c30000c13d000000040100008a00000000011000310000006f02000041000000000301004b000000000300001900000000030240190000006f01100197000000000401004b000000000200a0190000006f0110009c00000000010300190000000001026019000000000101004b000000c50000613d0000000001000019000001af00010430000000000200041a000000400a00043d000000760100004100000000001a043500000000010004140000007002200197000000040320008c000001170000c13d0000000103000031000000200130008c00000020040000390000000004034019000001470000013d0000006d030000410000006d0410009c00000000010380190000006d04a0009c00000000030a40190000004003300210000000c001100210000000000131019f0000007b011001c700010000000a001d01ad01a80000040f000000010a000029000000000301001900000060033002700000006d03300197000000200430008c000000200400003900000000040340190000001f0540018f0000000506400272000000f00000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b000000e80000413d000000000705004b000000ff0000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f00000001022001900000015c0000613d0000001f01400039000000600210018f0000000001a20019000000000221004b00000000020000190000000102004039000000780410009c000000540000213d0000000102200190000000540000c13d000000400010043f000000200230008c000000c30000413d00000000020a043300000000002104350000006d020000410000006d0310009c0000000001028019000000400110021000000079011001c7000001ae0001042e0000006d030000410000006d0410009c00000000010380190000006d04a0009c00000000030a40190000004003300210000000c001100210000000000131019f00000077011001c700010000000a001d01ad01a80000040f000000010a000029000000000301001900000060033002700000006d03300197000000200430008c000000200400003900000000040340190000001f0540018f0000000506400272000001350000613d0000000007000019000000050870021000000000098a0019000000000881034f000000000808043b00000000008904350000000107700039000000000867004b0000012d0000413d000000000705004b000001440000613d0000000506600210000000000761034f00000000066a00190000000305500210000000000806043300000000085801cf000000000858022f000000000707043b0000010005500089000000000757022f00000000055701cf000000000585019f0000000000560435000100000003001f0000000102200190000001820000613d0000001f01400039000000600210018f0000000001a20019000000000221004b00000000020000190000000102004039000000780410009c000000540000213d0000000102200190000000540000c13d000000400010043f000000200230008c000000c30000413d00000000020a043300000000002104350000006d020000410000006d0310009c0000000001028019000000400110021000000079011001c7000001ae0001042e000000400200043d0000001f0430018f0000000503300272000001690000613d000000000500001900000005065002100000000007620019000000000661034f000000000606043b00000000006704350000000105500039000000000635004b000001610000413d000000000504004b000001780000613d0000000503300210000000000131034f00000000033200190000000304400210000000000503043300000000054501cf000000000545022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001304350000006d0100004100000001030000310000006d0430009c00000000030180190000006d0420009c000000000102401900000040011002100000006002300210000000000112019f000001af00010430000000400200043d0000001f0430018f00000005033002720000018f0000613d000000000500001900000005065002100000000007620019000000000661034f000000000606043b00000000006704350000000105500039000000000635004b000001870000413d000000000504004b0000019e0000613d0000000503300210000000000131034f00000000033200190000000304400210000000000503043300000000054501cf000000000545022f000000000101043b0000010004400089000000000141022f00000000014101cf000000000151019f00000000001304350000006d0100004100000001030000310000006d0430009c00000000030180190000006d0420009c000000000102401900000040011002100000006002300210000000000112019f000001af00010430000001ab002104230000000102000039000000000001042d0000000002000019000000000001042d000001ad00000432000001ae0001042e000001af00010430000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff00000000000000000000000000000000000000000000000100000000000000008000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0000000000000000000000000000000000000000000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000000000000000000000000000d3072d8200000000000000000000000000000000000000000000000000000000b9d92de80000000000000000000000000000000000000000000000000000000006fdde03d3072d82000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffff0000000000000000000000000000000000000020000000000000000000000000c6888fa10000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000240000000000000000000000004e487b71000000000000000000000000000000000000000000000000000000005072696d617279000000000000000000000000000000000000000000000000009c917ca34a24c60aac10aab9022e5996487bc34dbb282973dfb468de4a087199", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/deps/test-contracts/Secondary.json b/.test-node-subtree/src/deps/test-contracts/Secondary.json new file mode 100644 index 00000000..e39f0fa7 --- /dev/null +++ b/.test-node-subtree/src/deps/test-contracts/Secondary.json @@ -0,0 +1,68 @@ +{ + "_format": "hh-zksolc-artifact-1", + "contractName": "Secondary", + "sourceName": "cache-zk/solpp-generated-contracts/tracing/Secondary.sol", + "abi": [ + { + "inputs": [ + { + "internalType": "uint256", + "name": "_data", + "type": "uint256" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "value", + "type": "uint256" + } + ], + "name": "multiply", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "name", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "pure", + "type": "function" + }, + { + "inputs": [], + "name": "shouldRevert", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "pure", + "type": "function" + } + ], + "bytecode": "0x000200000000000200010000000103550000006001100270000000370010019d0000000101200190000000490000c13d0000008001000039000000400010043f0000000001000031000000040110008c000000bc0000413d0000000101000367000000000101043b000000e0011002700000003d0210009c000000880000613d0000003e0210009c000000ab0000613d0000003f0110009c000000bc0000c13d0000000001000416000000000101004b000000bc0000c13d000000040100008a00000000011000310000003902000041000000000301004b000000000300001900000000030240190000003901100197000000000401004b000000000200a019000000390110009c00000000010300190000000001026019000000000101004b000000bc0000c13d000000c001000039000000400010043f0000000901000039000000800010043f0000004401000041000000a00010043f0000002002000039000000400100043d0000000003210436000000800200043d00000000002304350000004003100039000000000402004b0000003b0000613d00000000040000190000000005340019000000a006400039000000000606043300000000006504350000002004400039000000000524004b000000340000413d000000000332001900000000000304350000005f02200039000000200300008a000000000232016f0000003703000041000000370420009c0000000002038019000000370410009c000000000103801900000040011002100000006002200210000000000112019f000000d70001042e0000000001000416000000000101004b000000bc0000c13d00000000010000310000009f02100039000000200300008a000000000232016f000000380320009c000000580000413d0000003b0100004100000000001004350000004101000039000000040010043f0000003c01000041000000d800010430000000400020043f0000001f0210018f00000001030003670000000504100272000000660000613d00000000050000190000000506500210000000000763034f000000000707043b000000800660003900000000007604350000000105500039000000000645004b0000005e0000413d000000000502004b000000750000613d0000000504400210000000000343034f00000003022002100000008004400039000000000504043300000000052501cf000000000525022f000000000303043b0000010002200089000000000323022f00000000022301cf000000000252019f00000000002404350000003902000041000000200310008c000000000300001900000000030240190000003901100197000000000401004b000000000200a019000000390110009c00000000010300190000000001026019000000000101004b000000bc0000c13d000000800100043d000000000010041b0000002001000039000001000010044300000120000004430000003a01000041000000d70001042e0000000001000416000000000101004b000000bc0000c13d000000040100008a00000000011000310000003902000041000000000301004b000000000300001900000000030240190000003901100197000000000401004b000000000200a019000000390110009c00000000010300190000000001026019000000000101004b000000bc0000c13d000000400100043d000000440210003900000040030000410000000000320435000000240210003900000012030000390000000000320435000000410200004100000000002104350000000402100039000000200300003900000000003204350000003702000041000000370310009c0000000001028019000000400110021000000042011001c7000000d8000104300000000001000416000000000101004b000000bc0000c13d000000040100008a00000000011000310000003902000041000000200310008c000000000300001900000000030240190000003901100197000000000401004b000000000200a019000000390110009c00000000010300190000000001026019000000000101004b000000be0000613d0000000001000019000000d80001043000000004010000390000000101100367000000000201043b000000000300041a00000000412300a9000000000403004b000000c80000613d00000000433100d9000000000232004b000000d00000c13d000000400200043d00000000001204350000003701000041000000370320009c0000000001024019000000400110021000000043011001c7000000d70001042e0000003b0100004100000000001004350000001101000039000000040010043f0000003c01000041000000d800010430000000d600000432000000d70001042e000000d80001043000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000000000000000000000000000000000000000000010000000000000000800000000000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000400000010000000000000000004e487b7100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000000000000000000000000000000000000000000000000000000000000000000000000000000d3072d8200000000000000000000000000000000000000000000000000000000c6888fa10000000000000000000000000000000000000000000000000000000006fdde03546869732073686f756c6420726576657274000000000000000000000000000008c379a000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000006400000000000000000000000000000000000000000000000000000000000000200000000000000000000000005365636f6e64617279000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004ea1fe6554dbdbb43038724153cb8d87eb9015df7df422ef539f7d7c715e3c99", + "deployedBytecode": "0x000200000000000200010000000103550000006001100270000000370010019d0000000101200190000000490000c13d0000008001000039000000400010043f0000000001000031000000040110008c000000bc0000413d0000000101000367000000000101043b000000e0011002700000003d0210009c000000880000613d0000003e0210009c000000ab0000613d0000003f0110009c000000bc0000c13d0000000001000416000000000101004b000000bc0000c13d000000040100008a00000000011000310000003902000041000000000301004b000000000300001900000000030240190000003901100197000000000401004b000000000200a019000000390110009c00000000010300190000000001026019000000000101004b000000bc0000c13d000000c001000039000000400010043f0000000901000039000000800010043f0000004401000041000000a00010043f0000002002000039000000400100043d0000000003210436000000800200043d00000000002304350000004003100039000000000402004b0000003b0000613d00000000040000190000000005340019000000a006400039000000000606043300000000006504350000002004400039000000000524004b000000340000413d000000000332001900000000000304350000005f02200039000000200300008a000000000232016f0000003703000041000000370420009c0000000002038019000000370410009c000000000103801900000040011002100000006002200210000000000112019f000000d70001042e0000000001000416000000000101004b000000bc0000c13d00000000010000310000009f02100039000000200300008a000000000232016f000000380320009c000000580000413d0000003b0100004100000000001004350000004101000039000000040010043f0000003c01000041000000d800010430000000400020043f0000001f0210018f00000001030003670000000504100272000000660000613d00000000050000190000000506500210000000000763034f000000000707043b000000800660003900000000007604350000000105500039000000000645004b0000005e0000413d000000000502004b000000750000613d0000000504400210000000000343034f00000003022002100000008004400039000000000504043300000000052501cf000000000525022f000000000303043b0000010002200089000000000323022f00000000022301cf000000000252019f00000000002404350000003902000041000000200310008c000000000300001900000000030240190000003901100197000000000401004b000000000200a019000000390110009c00000000010300190000000001026019000000000101004b000000bc0000c13d000000800100043d000000000010041b0000002001000039000001000010044300000120000004430000003a01000041000000d70001042e0000000001000416000000000101004b000000bc0000c13d000000040100008a00000000011000310000003902000041000000000301004b000000000300001900000000030240190000003901100197000000000401004b000000000200a019000000390110009c00000000010300190000000001026019000000000101004b000000bc0000c13d000000400100043d000000440210003900000040030000410000000000320435000000240210003900000012030000390000000000320435000000410200004100000000002104350000000402100039000000200300003900000000003204350000003702000041000000370310009c0000000001028019000000400110021000000042011001c7000000d8000104300000000001000416000000000101004b000000bc0000c13d000000040100008a00000000011000310000003902000041000000200310008c000000000300001900000000030240190000003901100197000000000401004b000000000200a019000000390110009c00000000010300190000000001026019000000000101004b000000be0000613d0000000001000019000000d80001043000000004010000390000000101100367000000000201043b000000000300041a00000000412300a9000000000403004b000000c80000613d00000000433100d9000000000232004b000000d00000c13d000000400200043d00000000001204350000003701000041000000370320009c0000000001024019000000400110021000000043011001c7000000d70001042e0000003b0100004100000000001004350000001101000039000000040010043f0000003c01000041000000d800010430000000d600000432000000d70001042e000000d80001043000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffff0000000000000000000000000000000000000000000000010000000000000000800000000000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000400000010000000000000000004e487b7100000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000002400000000000000000000000000000000000000000000000000000000000000000000000000000000d3072d8200000000000000000000000000000000000000000000000000000000c6888fa10000000000000000000000000000000000000000000000000000000006fdde03546869732073686f756c6420726576657274000000000000000000000000000008c379a000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000006400000000000000000000000000000000000000000000000000000000000000200000000000000000000000005365636f6e64617279000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000004ea1fe6554dbdbb43038724153cb8d87eb9015df7df422ef539f7d7c715e3c99", + "linkReferences": {}, + "deployedLinkReferences": {}, + "factoryDeps": {} +} diff --git a/.test-node-subtree/src/filters.rs b/.test-node-subtree/src/filters.rs new file mode 100644 index 00000000..8d4214dd --- /dev/null +++ b/.test-node-subtree/src/filters.rs @@ -0,0 +1,1122 @@ +use std::collections::{HashMap, HashSet}; + +use zksync_basic_types::{H160, H256, U256, U64}; +use zksync_types::api::{BlockNumber, Log}; +use zksync_web3_decl::types::FilterChanges; + +use crate::utils; + +/// Specifies a filter type +#[derive(Debug, Clone, PartialEq)] +pub enum FilterType { + /// A filter for block information + Block(BlockFilter), + /// A filter for log information. + /// This is [Box] to ensure the enum invariants are similar size. + Log(Box), + /// A filter for pending transaction information + PendingTransaction(PendingTransactionFilter), +} + +/// Specifies a filter that keeps track of new blocks +#[derive(Debug, Default, Clone, PartialEq)] +pub struct BlockFilter { + updates: Vec, +} + +/// Specifies a filter that keeps track of new logs +#[derive(Debug, Clone, PartialEq)] +pub struct LogFilter { + from_block: BlockNumber, + to_block: BlockNumber, + addresses: Vec, + topics: [Option>; 4], + updates: Vec, +} + +impl LogFilter { + pub fn new( + from_block: BlockNumber, + to_block: BlockNumber, + addresses: Vec, + topics: [Option>; 4], + ) -> Self { + Self { + from_block, + to_block, + addresses, + topics, + updates: Default::default(), + } + } + + pub fn matches(&self, log: &Log, latest_block_number: U64) -> bool { + let from = utils::to_real_block_number(self.from_block, latest_block_number); + let to = utils::to_real_block_number(self.to_block, latest_block_number); + + let n = log.block_number.expect("block number must exist"); + if n < from || n > to { + return false; + } + + if !self.addresses.is_empty() + && self.addresses.iter().all(|address| address != &log.address) + { + return false; + } + + let mut matched_topic = [true; 4]; + for (i, topic) in log.topics.iter().take(4).enumerate() { + if let Some(topic_set) = &self.topics[i] { + if !topic_set.is_empty() && !topic_set.contains(topic) { + matched_topic[i] = false; + } + } + } + + matched_topic.iter().all(|m| *m) + } +} + +/// Specifies a filter that keeps track of new pending transactions +#[derive(Debug, Default, Clone, PartialEq)] +pub struct PendingTransactionFilter { + updates: Vec, +} + +type Result = std::result::Result; + +/// Keeps track of installed filters and their respective updates. +#[derive(Debug, Default, Clone, PartialEq)] +pub struct EthFilters { + id_counter: U256, + filters: HashMap, +} + +impl EthFilters { + /// Adds a block filter to keep track of new block hashes. Returns the filter id. + pub fn add_block_filter(&mut self) -> Result { + self.id_counter = self + .id_counter + .checked_add(U256::from(1)) + .ok_or("overflow")?; + self.filters.insert( + self.id_counter, + FilterType::Block(BlockFilter { + updates: Default::default(), + }), + ); + + tracing::info!("created block filter '{:#x}'", self.id_counter); + Ok(self.id_counter) + } + + /// Adds a log filter to keep track of new transaction logs. Returns the filter id. + pub fn add_log_filter( + &mut self, + from_block: BlockNumber, + to_block: BlockNumber, + addresses: Vec, + topics: [Option>; 4], + ) -> Result { + self.id_counter = self + .id_counter + .checked_add(U256::from(1)) + .ok_or("overflow")?; + self.filters.insert( + self.id_counter, + FilterType::Log(Box::new(LogFilter { + from_block, + to_block, + addresses, + topics, + updates: Default::default(), + })), + ); + + tracing::info!("created log filter '{:#x}'", self.id_counter); + Ok(self.id_counter) + } + + /// Adds a filter to keep track of new pending transaction hashes. Returns the filter id. + pub fn add_pending_transaction_filter(&mut self) -> Result { + self.id_counter = self + .id_counter + .checked_add(U256::from(1)) + .ok_or("overflow")?; + self.filters.insert( + self.id_counter, + FilterType::PendingTransaction(PendingTransactionFilter { + updates: Default::default(), + }), + ); + + tracing::info!( + "created pending transaction filter '{:#x}'", + self.id_counter + ); + Ok(self.id_counter) + } + + /// Removes the filter with the given id. Returns true if the filter existed, false otherwise. + pub fn remove_filter(&mut self, id: U256) -> bool { + tracing::info!("removing filter '{id:#x}'"); + self.filters.remove(&id).is_some() + } + + /// Retrieves the filter updates with the given id. The updates are reset after this call. + pub fn get_new_changes(&mut self, id: U256) -> Result { + let filter = self.filters.get_mut(&id).ok_or("invalid filter")?; + let changes = match filter { + FilterType::Block(f) => { + if f.updates.is_empty() { + FilterChanges::Empty(Default::default()) + } else { + let updates = f.updates.clone(); + f.updates.clear(); + FilterChanges::Hashes(updates) + } + } + FilterType::Log(f) => { + if f.updates.is_empty() { + FilterChanges::Empty(Default::default()) + } else { + let updates = f.updates.clone(); + f.updates.clear(); + FilterChanges::Logs(updates) + } + } + FilterType::PendingTransaction(f) => { + if f.updates.is_empty() { + FilterChanges::Empty(Default::default()) + } else { + let updates = f.updates.clone(); + f.updates.clear(); + FilterChanges::Hashes(updates) + } + } + }; + + Ok(changes) + } + + pub fn get_filter(&self, id: U256) -> Option<&FilterType> { + self.filters.get(&id) + } + + /// Notify available filters of a newly produced block + pub fn notify_new_block(&mut self, hash: H256) { + self.filters.iter_mut().for_each(|(_, filter)| { + if let FilterType::Block(f) = filter { + f.updates.push(hash) + } + }) + } + + /// Notify available filters of a new pending transaction + pub fn notify_new_pending_transaction(&mut self, hash: H256) { + self.filters.iter_mut().for_each(|(_, filter)| { + if let FilterType::PendingTransaction(f) = filter { + f.updates.push(hash) + } + }) + } + + /// Notify available filters of a new transaction log + pub fn notify_new_log(&mut self, log: &Log, latest_block_number: U64) { + self.filters.iter_mut().for_each(|(_, filter)| { + if let FilterType::Log(f) = filter { + if f.matches(log, latest_block_number) { + f.updates.push(log.clone()); + } + } + }) + } +} + +#[cfg(test)] +mod tests { + use crate::testing::LogBuilder; + + use super::*; + + use maplit::{hashmap, hashset}; + + #[test] + fn test_add_block_filter() { + let mut filters = EthFilters::default(); + let id = filters.add_block_filter().expect("failed adding filter"); + + assert_eq!(U256::from(1), id); + assert_eq!( + hashmap! { + U256::from(1) => FilterType::Block(BlockFilter { updates: vec![] }) + }, + filters.filters + ); + } + + #[test] + fn test_add_log_filter() { + let mut filters = EthFilters::default(); + let id = filters + .add_log_filter( + BlockNumber::Latest, + BlockNumber::Number(U64::from(10)), + vec![H160::repeat_byte(0x1)], + [ + Some(hashset! { H256::repeat_byte(0x2) }), + Some(hashset! { H256::repeat_byte(0x3), H256::repeat_byte(0x4) }), + None, + Some(hashset! {}), + ], + ) + .expect("failed adding filter"); + + assert_eq!(U256::from(1), id); + assert_eq!( + hashmap! { + U256::from(1) => FilterType::Log(Box::new(LogFilter { + from_block: BlockNumber::Latest, + to_block: BlockNumber::Number(U64::from(10)), + addresses: vec![H160::repeat_byte(0x1)], + topics: [ + Some(hashset! { H256::repeat_byte(0x2) }), + Some(hashset! { H256::repeat_byte(0x3), H256::repeat_byte(0x4) }), + None, + Some(hashset! {}), + ], + updates:vec![], + })) + }, + filters.filters + ); + } + + #[test] + fn test_add_pending_transaction_filter() { + let mut filters = EthFilters::default(); + let id = filters + .add_pending_transaction_filter() + .expect("failed adding filter"); + + assert_eq!(U256::from(1), id); + assert_eq!( + hashmap! { + U256::from(1) => FilterType::PendingTransaction(PendingTransactionFilter { updates: vec![] }) + }, + filters.filters + ); + } + + #[test] + fn test_different_filters_share_incremental_identifiers() { + let mut filters = EthFilters::default(); + + let block_filter_id = filters.add_block_filter().expect("failed adding filter"); + let log_filter_id = filters + .add_log_filter( + BlockNumber::Earliest, + BlockNumber::Latest, + Default::default(), + Default::default(), + ) + .expect("failed adding filter"); + let pending_transaction_filter_id = filters + .add_pending_transaction_filter() + .expect("failed adding filter"); + + assert_eq!(U256::from(1), block_filter_id); + assert_eq!(U256::from(2), log_filter_id); + assert_eq!(U256::from(3), pending_transaction_filter_id); + } + + #[test] + fn test_remove_filter() { + let mut filters = EthFilters::default(); + let block_filter_id = filters.add_block_filter().expect("failed adding filter"); + let log_filter_id = filters + .add_log_filter( + BlockNumber::Earliest, + BlockNumber::Latest, + Default::default(), + Default::default(), + ) + .expect("failed adding filter"); + let pending_transaction_filter_id = filters + .add_pending_transaction_filter() + .expect("failed adding filter"); + + filters.remove_filter(log_filter_id); + + assert!( + filters.filters.contains_key(&block_filter_id), + "filter was erroneously removed" + ); + assert!( + filters.filters.contains_key(&pending_transaction_filter_id), + "filter was erroneously removed" + ); + assert!( + !filters.filters.contains_key(&log_filter_id), + "filter was not removed" + ); + } + + #[test] + fn test_notify_new_block_appends_updates() { + let mut filters = EthFilters::default(); + let id = filters.add_block_filter().expect("failed adding filter"); + + filters.notify_new_block(H256::repeat_byte(0x1)); + + match filters.filters.get(&id).unwrap() { + FilterType::Block(f) => { + assert_eq!(vec![H256::repeat_byte(0x1)], f.updates); + } + _ => panic!("invalid filter"), + } + } + + #[test] + fn test_notify_new_log_appends_matching_updates() { + let mut filters = EthFilters::default(); + let match_address = H160::repeat_byte(0x1); + let id = filters + .add_log_filter( + BlockNumber::Earliest, + BlockNumber::Latest, + vec![match_address], + Default::default(), + ) + .expect("failed adding filter"); + + let log = LogBuilder::new() + .set_address(match_address) + .set_block(U64::from(1)) + .build(); + filters.notify_new_log(&log, U64::from(1)); + + match filters.filters.get(&id).unwrap() { + FilterType::Log(f) => { + assert_eq!(vec![log], f.updates); + } + _ => panic!("invalid filter"), + } + } + + #[test] + fn test_notify_new_pending_transaction_appends_updates() { + let mut filters = EthFilters::default(); + let id = filters + .add_pending_transaction_filter() + .expect("failed adding filter"); + + filters.notify_new_pending_transaction(H256::repeat_byte(0x1)); + + match filters.filters.get(&id).unwrap() { + FilterType::PendingTransaction(f) => { + assert_eq!(vec![H256::repeat_byte(0x1)], f.updates); + } + _ => panic!("invalid filter"), + } + } + + #[test] + fn test_get_new_changes_block_returns_updates_and_clears_them() { + let mut filters = EthFilters::default(); + let id = filters.add_block_filter().expect("failed adding filter"); + filters.notify_new_block(H256::repeat_byte(0x1)); + + let changes = filters + .get_new_changes(id) + .expect("failed retrieving changes"); + + match changes { + FilterChanges::Hashes(result) => { + assert_eq!(vec![H256::repeat_byte(0x1)], result); + } + _ => panic!("unexpected filter changes {:?}", changes), + } + match filters.filters.get(&id).unwrap() { + FilterType::Block(f) => { + assert!(f.updates.is_empty(), "updates were not cleared"); + } + _ => panic!("invalid filter"), + } + } + + #[test] + fn test_get_new_changes_log_appends_mreturng_updates_and_clears_them() { + let mut filters = EthFilters::default(); + let match_address = H160::repeat_byte(0x1); + let id = filters + .add_log_filter( + BlockNumber::Earliest, + BlockNumber::Latest, + vec![match_address], + Default::default(), + ) + .expect("failed adding filter"); + + let log = LogBuilder::new() + .set_address(match_address) + .set_block(U64::from(1)) + .build(); + filters.notify_new_log(&log, U64::from(1)); + + let changes = filters + .get_new_changes(id) + .expect("failed retrieving changes"); + + match changes { + FilterChanges::Logs(result) => { + assert_eq!(vec![log], result); + } + _ => panic!("unexpected filter changes {:?}", changes), + } + match filters.filters.get(&id).unwrap() { + FilterType::Log(f) => { + assert!(f.updates.is_empty(), "updates were not cleared"); + } + _ => panic!("invalid filter"), + } + } + + #[test] + fn test_get_new_changes_pending_transaction_returns_updates_and_clears_them() { + let mut filters = EthFilters::default(); + let id = filters + .add_pending_transaction_filter() + .expect("failed adding filter"); + + filters.notify_new_pending_transaction(H256::repeat_byte(0x1)); + + let changes = filters + .get_new_changes(id) + .expect("failed retrieving changes"); + + match changes { + FilterChanges::Hashes(result) => { + assert_eq!(vec![H256::repeat_byte(0x1)], result); + } + _ => panic!("unexpected filter changes {:?}", changes), + } + match filters.filters.get(&id).unwrap() { + FilterType::PendingTransaction(f) => { + assert!(f.updates.is_empty(), "updates were not cleared"); + } + _ => panic!("invalid filter"), + } + } +} + +#[cfg(test)] +mod log_filter_tests { + use maplit::hashset; + + use crate::testing::LogBuilder; + + use super::*; + + #[test] + fn test_filter_from_block_earliest_accepts_all_block_numbers_lte_latest() { + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + let latest_block_number = 2u64; + for log_block in 0..=latest_block_number { + let matched = filter.matches( + &LogBuilder::new().set_block(U64::from(log_block)).build(), + U64::from(latest_block_number), + ); + assert!( + matched, + "failed matching log for block_number {}", + log_block + ); + } + } + + #[test] + fn test_filter_from_block_latest_accepts_block_number_eq_latest() { + let filter = LogFilter { + from_block: BlockNumber::Latest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + let latest_block_number = U64::from(2); + let input_block_number = U64::from(2); + let matched = filter.matches( + &LogBuilder::new().set_block(input_block_number).build(), + latest_block_number, + ); + assert!(matched); + } + + #[test] + fn test_filter_from_block_latest_rejects_block_number_lt_latest() { + let filter = LogFilter { + from_block: BlockNumber::Latest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + let latest_block_number = U64::from(2); + let matched = filter.matches( + &LogBuilder::new().set_block(U64::from(1)).build(), + latest_block_number, + ); + assert!(!matched); + } + + #[test] + fn test_filter_from_block_accepts_all_block_numbers_gte_input_number() { + let input_block_number = 2u64; + let latest_block_number = 100u64; + let filter = LogFilter { + from_block: BlockNumber::Number(U64::from(input_block_number)), + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + for log_block in input_block_number..=input_block_number + 1 { + let matched = filter.matches( + &LogBuilder::new().set_block(U64::from(log_block)).build(), + U64::from(latest_block_number), + ); + assert!( + matched, + "failed matching log for block_number {}", + log_block + ); + } + } + + #[test] + fn test_filter_from_block_rejects_block_number_lt_input_number() { + let input_block_number = 2u64; + let latest_block_number = 100u64; + let filter = LogFilter { + from_block: BlockNumber::Number(U64::from(input_block_number)), + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_block(U64::from(input_block_number - 1)) + .build(), + U64::from(latest_block_number), + ); + assert!(!matched); + } + + #[test] + fn test_filter_to_block_latest_accepts_block_number_lte_latest() { + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + let latest_block_number = 2u32; + for log_block in 1..=latest_block_number { + let matched = filter.matches( + &LogBuilder::new().set_block(U64::from(log_block)).build(), + U64::from(latest_block_number), + ); + assert!( + matched, + "failed matching log for block_number {}", + log_block + ); + } + } + + #[test] + fn test_filter_to_block_accepts_all_block_numbers_lte_input_number() { + let input_block_number = 2u64; + let latest_block_number = 100u64; + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Number(U64::from(input_block_number)), + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + for log_block in input_block_number - 1..=input_block_number { + let matched = filter.matches( + &LogBuilder::new().set_block(U64::from(log_block)).build(), + U64::from(latest_block_number), + ); + assert!( + matched, + "failed matching log for block_number {}", + log_block + ); + } + } + + #[test] + fn test_filter_to_block_rejects_block_number_gt_input_number() { + let input_block_number = 2u64; + let latest_block_number = 100u64; + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Number(U64::from(input_block_number)), + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_block(U64::from(input_block_number + 1)) + .build(), + U64::from(latest_block_number), + ); + assert!(!matched); + } + + #[test] + fn test_filter_from_and_to_block_rejects_block_number_left_of_range() { + let input_from_block_number = 2u64; + let input_to_block_number = 4u64; + let latest_block_number = 100u64; + let filter = LogFilter { + from_block: BlockNumber::Number(U64::from(input_from_block_number)), + to_block: BlockNumber::Number(U64::from(input_to_block_number)), + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_block(U64::from(input_from_block_number - 1)) + .build(), + U64::from(latest_block_number), + ); + assert!(!matched); + } + + #[test] + fn test_filter_from_and_to_block_rejects_block_number_right_of_range() { + let input_from_block_number = 2u64; + let input_to_block_number = 4u64; + let latest_block_number = 100u64; + let filter = LogFilter { + from_block: BlockNumber::Number(U64::from(input_from_block_number)), + to_block: BlockNumber::Number(U64::from(input_to_block_number)), + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_block(U64::from(input_to_block_number + 1)) + .build(), + U64::from(latest_block_number), + ); + assert!(!matched); + } + + #[test] + fn test_filter_from_and_to_block_accepts_block_number_inclusive_of_range() { + let input_from_block_number = 2u64; + let input_to_block_number = 4u64; + let latest_block_number = 100u64; + let filter = LogFilter { + from_block: BlockNumber::Number(U64::from(input_from_block_number)), + to_block: BlockNumber::Number(U64::from(input_to_block_number)), + addresses: Default::default(), + topics: Default::default(), + updates: Default::default(), + }; + + for log_block in input_from_block_number..=input_to_block_number { + let matched = filter.matches( + &LogBuilder::new().set_block(U64::from(log_block)).build(), + U64::from(latest_block_number), + ); + assert!( + matched, + "failed matching log for block_number {}", + log_block + ); + } + } + + #[test] + fn test_filter_address_rejects_if_address_not_in_set() { + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: vec![H160::repeat_byte(0xa)], + topics: Default::default(), + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_address(H160::repeat_byte(0x1)) + .build(), + U64::from(100), + ); + assert!(!matched); + } + + #[test] + fn test_filter_address_accepts_if_address_in_set() { + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: vec![H160::repeat_byte(0x1)], + topics: Default::default(), + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_address(H160::repeat_byte(0x1)) + .build(), + U64::from(100), + ); + assert!(matched); + } + + #[test] + fn test_filter_address_accepts_if_address_set_empty() { + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: vec![], + topics: Default::default(), + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_address(H160::repeat_byte(0x1)) + .build(), + U64::from(100), + ); + assert!(matched); + } + + #[test] + fn test_filter_topic_none_accepts_any_topic() { + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics: [None, None, None, None], + updates: Default::default(), + }; + + for topic_idx in 0..4 { + let mut input_topics = [H256::zero(); 4].to_vec(); + input_topics[topic_idx] = H256::repeat_byte(0x1); + + let matched = filter.matches( + &LogBuilder::new().set_topics(input_topics).build(), + U64::from(100), + ); + assert!(matched, "failed matching log for topic index {}", topic_idx); + } + } + + #[test] + fn test_filter_topic_exactly_one_accepts_exact_topic() { + for topic_idx in 0..4 { + let match_topic = H256::repeat_byte(0x1); + let mut topics = [None, None, None, None]; + topics[topic_idx] = Some(hashset! { match_topic }); + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics, + updates: Default::default(), + }; + let mut input_topics = [H256::zero(); 4].to_vec(); + input_topics[topic_idx] = match_topic; + + let matched = filter.matches( + &LogBuilder::new().set_topics(input_topics).build(), + U64::from(100), + ); + assert!(matched, "failed matching log for topic index {}", topic_idx); + } + } + + #[test] + fn test_filter_topic_multiple_accepts_either_topic() { + for topic_idx in 0..4 { + let match_topic_1 = H256::repeat_byte(0x1); + let match_topic_2 = H256::repeat_byte(0x2); + let mut topics = [None, None, None, None]; + topics[topic_idx] = Some(hashset! { match_topic_1, match_topic_2, }); + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics, + updates: Default::default(), + }; + + let mut input_topics = [H256::zero(); 4].to_vec(); + input_topics[topic_idx] = match_topic_1; + let matched = filter.matches( + &LogBuilder::new().set_topics(input_topics).build(), + U64::from(100), + ); + assert!( + matched, + "failed matching log for topic index {} for {}", + topic_idx, match_topic_1 + ); + + let mut input_topics = [H256::zero(); 4].to_vec(); + input_topics[topic_idx] = match_topic_2; + let matched = filter.matches( + &LogBuilder::new().set_topics(input_topics).build(), + U64::from(100), + ); + assert!( + matched, + "failed matching log for topic index {} for {}", + topic_idx, match_topic_2 + ); + } + } + + #[test] + fn test_filter_topic_exactly_one_rejects_different_topic() { + for topic_idx in 0..4 { + let match_topic = H256::repeat_byte(0x1); + let mut topics = [None, None, None, None]; + topics[topic_idx] = Some(hashset! { match_topic }); + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics, + updates: Default::default(), + }; + let mut input_topics = [H256::zero(); 4].to_vec(); + input_topics[topic_idx] = H256::repeat_byte(0xa); + + let matched = filter.matches( + &LogBuilder::new().set_topics(input_topics).build(), + U64::from(100), + ); + assert!( + !matched, + "erroneously matched log for topic index {}", + topic_idx + ); + } + } + + #[test] + fn test_filter_topic_multiple_rejects_different_topic() { + for topic_idx in 0..4 { + let match_topic_1 = H256::repeat_byte(0x1); + let match_topic_2 = H256::repeat_byte(0x2); + let mut topics = [None, None, None, None]; + topics[topic_idx] = Some(hashset! { match_topic_1, match_topic_2, }); + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics, + updates: Default::default(), + }; + + let mut input_topics = [H256::zero(); 4].to_vec(); + input_topics[topic_idx] = H256::repeat_byte(0xa); + let matched = filter.matches( + &LogBuilder::new().set_topics(input_topics).build(), + U64::from(100), + ); + assert!( + !matched, + "erroneously matched log for topic index {}", + topic_idx + ); + } + } + + #[test] + fn test_filter_topic_combination_accepts_if_all_topics_valid() { + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics: [ + None, // matches anything + Some(hashset! { H256::repeat_byte(0x1) }), + Some(hashset! { H256::repeat_byte(0x2), H256::repeat_byte(0x3) }), + Some(hashset! {}), // matches anything + ], + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_topics(vec![ + H256::zero(), + H256::repeat_byte(0x1), + H256::repeat_byte(0x3), + H256::repeat_byte(0xa), + ]) + .build(), + U64::from(100), + ); + assert!(matched); + } + + #[test] + fn test_filter_topic_combination_rejects_if_any_topic_is_invalid() { + let filter = LogFilter { + from_block: BlockNumber::Earliest, + to_block: BlockNumber::Latest, + addresses: Default::default(), + topics: [ + None, // matches anything + Some(hashset! { H256::repeat_byte(0x1) }), + Some(hashset! { H256::repeat_byte(0x2), H256::repeat_byte(0x3) }), + Some(hashset! {}), // matches anything + ], + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_topics(vec![ + H256::zero(), + H256::repeat_byte(0xf), // invalid + H256::repeat_byte(0x3), + H256::repeat_byte(0xa), + ]) + .build(), + U64::from(100), + ); + assert!(!matched, "erroneously matched on invalid topic1"); + + let matched = filter.matches( + &LogBuilder::new() + .set_topics(vec![ + H256::zero(), + H256::repeat_byte(0x1), + H256::repeat_byte(0xf), // invalid + H256::repeat_byte(0xa), + ]) + .build(), + U64::from(100), + ); + assert!(!matched, "erroneously matched on invalid topic2"); + } + + #[test] + fn test_filter_combination_accepts_if_all_criteria_valid() { + let filter = LogFilter { + from_block: BlockNumber::Number(U64::from(2)), + to_block: BlockNumber::Number(U64::from(5)), + addresses: vec![H160::repeat_byte(0xab)], + topics: [ + None, + Some(hashset! { H256::repeat_byte(0x1) }), + Some(hashset! { H256::repeat_byte(0x2), H256::repeat_byte(0x3) }), + Some(hashset! {}), + ], + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_block(U64::from(4)) + .set_address(H160::repeat_byte(0xab)) + .set_topics(vec![ + H256::zero(), + H256::repeat_byte(0x1), + H256::repeat_byte(0x3), + H256::repeat_byte(0xa), + ]) + .build(), + U64::from(100), + ); + assert!(matched); + } + + #[test] + fn test_filter_combination_rejects_if_any_criterion_invalid() { + let filter = LogFilter { + from_block: BlockNumber::Number(U64::from(2)), + to_block: BlockNumber::Number(U64::from(5)), + addresses: vec![H160::repeat_byte(0xab)], + topics: [Some(hashset! { H256::repeat_byte(0x1) }), None, None, None], + updates: Default::default(), + }; + + let matched = filter.matches( + &LogBuilder::new() + .set_block(U64::from(1)) // invalid + .set_address(H160::repeat_byte(0xab)) + .set_topics(vec![ + H256::zero(), + H256::repeat_byte(0x1), + H256::repeat_byte(0x3), + H256::repeat_byte(0xa), + ]) + .build(), + U64::from(100), + ); + assert!(!matched, "erroneously matched on invalid block number"); + + let matched = filter.matches( + &LogBuilder::new() + .set_block(U64::from(1)) + .set_address(H160::repeat_byte(0xde)) // invalid + .set_topics(vec![ + H256::zero(), + H256::repeat_byte(0x1), + H256::repeat_byte(0x3), + H256::repeat_byte(0xa), + ]) + .build(), + U64::from(100), + ); + assert!(!matched, "erroneously matched on invalid address"); + + let matched = filter.matches( + &LogBuilder::new() + .set_block(U64::from(1)) + .set_address(H160::repeat_byte(0xde)) + .set_topics(vec![H256::zero(), H256::zero(), H256::zero(), H256::zero()]) // invalid + .build(), + U64::from(100), + ); + assert!(!matched, "erroneously matched on invalid topic"); + } +} diff --git a/.test-node-subtree/src/fork.rs b/.test-node-subtree/src/fork.rs new file mode 100644 index 00000000..69aaf089 --- /dev/null +++ b/.test-node-subtree/src/fork.rs @@ -0,0 +1,541 @@ +//! This file hold tools used for test-forking other networks. +//! +//! There is ForkStorage (that is a wrapper over InMemoryStorage) +//! And ForkDetails - that parses network address and fork height from arguments. + +use std::{ + collections::HashMap, + convert::{TryFrom, TryInto}, + future::Future, + sync::{Arc, RwLock}, +}; + +use tokio::runtime::Builder; +use zksync_basic_types::{Address, L1BatchNumber, L2ChainId, MiniblockNumber, H256, U256, U64}; + +use zksync_types::{ + api::{ + Block, BlockDetails, BlockIdVariant, BlockNumber, BridgeAddresses, Transaction, + TransactionDetails, TransactionVariant, + }, + l2::L2Tx, + ProtocolVersionId, StorageKey, +}; + +use zksync_state::ReadStorage; +use zksync_utils::{bytecode::hash_bytecode, h256_to_u256}; + +use zksync_web3_decl::{ + jsonrpsee::http_client::HttpClient, namespaces::EthNamespaceClient, types::Index, +}; +use zksync_web3_decl::{jsonrpsee::http_client::HttpClientBuilder, namespaces::ZksNamespaceClient}; + +use crate::system_contracts; +use crate::{cache::CacheConfig, node::TEST_NODE_NETWORK_ID}; +use crate::{deps::InMemoryStorage, http_fork_source::HttpForkSource}; + +pub fn block_on(future: F) -> F::Output +where + F::Output: Send, +{ + std::thread::spawn(move || { + let runtime = Builder::new_current_thread() + .enable_all() + .build() + .expect("tokio runtime creation failed"); + runtime.block_on(future) + }) + .join() + .unwrap() +} + +/// In memory storage, that allows 'forking' from other network. +/// If forking is enabled, it reads missing data from remote location. +/// S - is a struct that is used for source of the fork. +#[derive(Debug, Clone)] +pub struct ForkStorage { + pub inner: Arc>>, + pub chain_id: L2ChainId, +} + +#[derive(Debug)] +pub struct ForkStorageInner { + // Underlying local storage + pub raw_storage: InMemoryStorage, + // Cache of data that was read from remote location. + pub value_read_cache: HashMap, + // Cache of factory deps that were read from remote location. + pub factory_dep_cache: HashMap>>, + // If set - it hold the necessary information on where to fetch the data. + // If not set - it will simply read from underlying storage. + pub fork: Option>, +} + +impl ForkStorage { + pub fn new( + fork: Option>, + system_contracts_options: &system_contracts::Options, + ) -> Self { + let chain_id = fork + .as_ref() + .and_then(|d| d.overwrite_chain_id) + .unwrap_or(L2ChainId::from(TEST_NODE_NETWORK_ID)); + tracing::info!("Starting network with chain id: {:?}", chain_id); + + ForkStorage { + inner: Arc::new(RwLock::new(ForkStorageInner { + raw_storage: InMemoryStorage::with_system_contracts_and_chain_id( + chain_id, + hash_bytecode, + system_contracts_options, + ), + value_read_cache: Default::default(), + fork, + factory_dep_cache: Default::default(), + })), + chain_id, + } + } + + fn read_value_internal(&self, key: &StorageKey) -> zksync_types::StorageValue { + let mut mutator = self.inner.write().unwrap(); + let local_storage = mutator.raw_storage.read_value(key); + + if let Some(fork) = &mutator.fork { + if !H256::is_zero(&local_storage) { + return local_storage; + } + + if let Some(value) = mutator.value_read_cache.get(key) { + return *value; + } + let l2_miniblock = fork.l2_miniblock; + let key_ = *key; + + let result = fork + .fork_source + .get_storage_at( + *key_.account().address(), + h256_to_u256(*key_.key()), + Some(BlockIdVariant::BlockNumber(BlockNumber::Number(U64::from( + l2_miniblock, + )))), + ) + .unwrap(); + + mutator.value_read_cache.insert(*key, result); + result + } else { + local_storage + } + } + + fn load_factory_dep_internal(&self, hash: H256) -> Option> { + let mut mutator = self.inner.write().unwrap(); + let local_storage = mutator.raw_storage.load_factory_dep(hash); + if let Some(fork) = &mutator.fork { + if local_storage.is_some() { + return local_storage; + } + if let Some(value) = mutator.factory_dep_cache.get(&hash) { + return value.clone(); + } + + let result = fork.fork_source.get_bytecode_by_hash(hash).unwrap(); + mutator.factory_dep_cache.insert(hash, result.clone()); + result + } else { + local_storage + } + } + + /// Check if this is the first time when we're ever writing to this key. + /// This has impact on amount of pubdata that we have to spend for the write. + fn is_write_initial_internal(&self, key: &StorageKey) -> bool { + // Currently we don't have the zks API to return us the information on whether a given + // key was written to before a given block. + // This means, we have to depend on the following heuristic: we'll read the value of the slot. + // - if value != 0 -> this means that the slot was written to in the past (so we can return intitial_write = false) + // - but if the value = 0 - there is a chance, that slot was written to in the past - and later was reset. + // but unfortunately we cannot detect that with the current zks api, so we'll attempt to do it + // only on local storage. + let value = self.read_value_internal(key); + if value != H256::zero() { + return false; + } + + // If value was 0, there is still a chance, that the slot was written to in the past - and only now set to 0. + // We unfortunately don't have the API to check it on the fork, but we can at least try to check it on local storage. + let mut mutator = self.inner.write().unwrap(); + mutator.raw_storage.is_write_initial(key) + } + + /// Retrieves the enumeration index for a given `key`. + fn get_enumeration_index_internal(&self, _key: &StorageKey) -> Option { + // TODO: Update this file to use proper enumeration index value once it's exposed for forks via API + Some(0_u64) + } +} + +impl ReadStorage for ForkStorage { + fn is_write_initial(&mut self, key: &StorageKey) -> bool { + self.is_write_initial_internal(key) + } + + fn load_factory_dep(&mut self, hash: H256) -> Option> { + self.load_factory_dep_internal(hash) + } + + fn read_value(&mut self, key: &StorageKey) -> zksync_types::StorageValue { + self.read_value_internal(key) + } + + fn get_enumeration_index(&mut self, key: &StorageKey) -> Option { + self.get_enumeration_index_internal(key) + } +} + +impl ReadStorage for &ForkStorage { + fn read_value(&mut self, key: &StorageKey) -> zksync_types::StorageValue { + self.read_value_internal(key) + } + + fn is_write_initial(&mut self, key: &StorageKey) -> bool { + self.is_write_initial_internal(key) + } + + fn load_factory_dep(&mut self, hash: H256) -> Option> { + self.load_factory_dep_internal(hash) + } + + fn get_enumeration_index(&mut self, key: &StorageKey) -> Option { + self.get_enumeration_index_internal(key) + } +} + +impl ForkStorage { + pub fn set_value(&mut self, key: StorageKey, value: zksync_types::StorageValue) { + let mut mutator = self.inner.write().unwrap(); + mutator.raw_storage.set_value(key, value) + } + pub fn store_factory_dep(&mut self, hash: H256, bytecode: Vec) { + let mut mutator = self.inner.write().unwrap(); + mutator.raw_storage.store_factory_dep(hash, bytecode) + } +} + +/// Trait that provides necessary data when +/// forking a remote chain. +/// The method signatures are similar to methods from ETHNamespace and ZKNamespace. +pub trait ForkSource { + /// Returns the Storage value at a given index for given address. + fn get_storage_at( + &self, + address: Address, + idx: U256, + block: Option, + ) -> eyre::Result; + + /// Returns the bytecode stored under this hash (if available). + fn get_bytecode_by_hash(&self, hash: H256) -> eyre::Result>>; + + /// Returns the transaction for a given hash. + fn get_transaction_by_hash(&self, hash: H256) -> eyre::Result>; + + /// Returns the transaction details for a given hash. + fn get_transaction_details(&self, hash: H256) -> eyre::Result>; + + /// Gets all transactions that belong to a given miniblock. + fn get_raw_block_transactions( + &self, + block_number: MiniblockNumber, + ) -> eyre::Result>; + + /// Returns the block for a given hash. + fn get_block_by_hash( + &self, + hash: H256, + full_transactions: bool, + ) -> eyre::Result>>; + + /// Returns the block for a given number. + fn get_block_by_number( + &self, + block_number: zksync_types::api::BlockNumber, + full_transactions: bool, + ) -> eyre::Result>>; + + /// Returns the block details for a given miniblock number. + fn get_block_details(&self, miniblock: MiniblockNumber) -> eyre::Result>; + + /// Returns the transaction count for a given block hash. + fn get_block_transaction_count_by_hash(&self, block_hash: H256) -> eyre::Result>; + + /// Returns the transaction count for a given block number. + fn get_block_transaction_count_by_number( + &self, + block_number: zksync_types::api::BlockNumber, + ) -> eyre::Result>; + + /// Returns information about a transaction by block hash and transaction index position. + fn get_transaction_by_block_hash_and_index( + &self, + block_hash: H256, + index: Index, + ) -> eyre::Result>; + + /// Returns information about a transaction by block number and transaction index position. + fn get_transaction_by_block_number_and_index( + &self, + block_number: BlockNumber, + index: Index, + ) -> eyre::Result>; + + /// Returns addresses of the default bridge contracts. + fn get_bridge_contracts(&self) -> eyre::Result; + + /// Returns confirmed tokens + fn get_confirmed_tokens( + &self, + from: u32, + limit: u8, + ) -> eyre::Result>; +} + +/// Holds the information about the original chain. +/// "S" is the implementation of the ForkSource. +#[derive(Debug, Clone)] +pub struct ForkDetails { + // Source of the fork data (for example HTTPForkSoruce) + pub fork_source: S, + // Block number at which we forked (the next block to create is l1_block + 1) + pub l1_block: L1BatchNumber, + // The actual L2 block + pub l2_block: zksync_types::api::Block, + pub l2_miniblock: u64, + pub l2_miniblock_hash: H256, + pub block_timestamp: u64, + pub overwrite_chain_id: Option, + pub l1_gas_price: u64, +} + +const SUPPORTED_VERSIONS: &[ProtocolVersionId] = &[ + ProtocolVersionId::Version9, + ProtocolVersionId::Version10, + ProtocolVersionId::Version11, + ProtocolVersionId::Version12, + ProtocolVersionId::Version13, + ProtocolVersionId::Version14, + ProtocolVersionId::Version15, + ProtocolVersionId::Version16, + ProtocolVersionId::Version17, + ProtocolVersionId::Version18, + ProtocolVersionId::Version19, +]; + +pub fn supported_protocol_versions(version: ProtocolVersionId) -> bool { + SUPPORTED_VERSIONS.contains(&version) +} + +pub fn supported_versions_to_string() -> String { + let versions: Vec = SUPPORTED_VERSIONS + .iter() + .map(|v| format!("{:?}", v)) + .collect(); + versions.join(", ") +} + +impl ForkDetails { + pub async fn from_url_and_miniblock_and_chain( + url: &str, + client: HttpClient, + miniblock: u64, + chain_id: Option, + cache_config: CacheConfig, + ) -> Self { + let block_details = client + .get_block_details(MiniblockNumber(miniblock as u32)) + .await + .unwrap() + .unwrap_or_else(|| panic!("Could not find block {:?} in {:?}", miniblock, url)); + + let root_hash = block_details + .base + .root_hash + .unwrap_or_else(|| panic!("fork block #{} missing root hash", miniblock)); + let block = client + .get_block_by_hash(root_hash, true) + .await + .expect("failed retrieving block") + .unwrap_or_else(|| { + panic!( + "Could not find block #{:?} ({:#x}) in {:?}", + miniblock, root_hash, url + ) + }); + let l1_batch_number = block_details.l1_batch_number; + + tracing::info!( + "Creating fork from {:?} L1 block: {:?} L2 block: {:?} with timestamp {:?}, L1 gas price {:?} and protocol version: {:?}" , + url, l1_batch_number, miniblock, block_details.base.timestamp, block_details.base.l1_gas_price, block_details.protocol_version + ); + + if !block_details + .protocol_version + .map(supported_protocol_versions) + .unwrap_or(false) + { + panic!( + "This block is using the unsupported protocol version: {:?}. This binary supports versions {}.", + block_details.protocol_version, + supported_versions_to_string() + ); + } + + ForkDetails { + fork_source: HttpForkSource::new(url.to_owned(), cache_config), + l1_block: l1_batch_number, + l2_block: block, + block_timestamp: block_details.base.timestamp, + l2_miniblock: miniblock, + l2_miniblock_hash: root_hash, + overwrite_chain_id: chain_id, + l1_gas_price: block_details.base.l1_gas_price, + } + } + /// Create a fork from a given network at a given height. + pub async fn from_network(fork: &str, fork_at: Option, cache_config: CacheConfig) -> Self { + let (url, client) = Self::fork_to_url_and_client(fork); + let l2_miniblock = if let Some(fork_at) = fork_at { + fork_at + } else { + client.get_block_number().await.unwrap().as_u64() + }; + Self::from_url_and_miniblock_and_chain(url, client, l2_miniblock, None, cache_config).await + } + + /// Create a fork from a given network, at a height BEFORE a transaction. + /// This will allow us to apply this transaction locally on top of this fork. + pub async fn from_network_tx(fork: &str, tx: H256, cache_config: CacheConfig) -> Self { + let (url, client) = Self::fork_to_url_and_client(fork); + let tx_details = client.get_transaction_by_hash(tx).await.unwrap().unwrap(); + let overwrite_chain_id = Some( + L2ChainId::try_from(tx_details.chain_id.as_u64()).unwrap_or_else(|err| { + panic!("erroneous chain id {}: {:?}", tx_details.chain_id, err,) + }), + ); + let miniblock_number = MiniblockNumber(tx_details.block_number.unwrap().as_u32()); + // We have to sync to the one-miniblock before the one where transaction is. + let l2_miniblock = miniblock_number.saturating_sub(1) as u64; + + Self::from_url_and_miniblock_and_chain( + url, + client, + l2_miniblock, + overwrite_chain_id, + cache_config, + ) + .await + } +} + +impl ForkDetails { + /// Return URL and HTTP client for a given fork name. + pub fn fork_to_url_and_client(fork: &str) -> (&str, HttpClient) { + let url = match fork { + "mainnet" => "https://mainnet.era.zksync.io:443", + "sepolia-testnet" => "https://sepolia.era.zksync.dev:443", + "goerli-testnet" => "https://testnet.era.zksync.dev:443", + _ => fork, + }; + + let client = HttpClientBuilder::default() + .build(url) + .expect("Unable to create a client for fork"); + + (url, client) + } + + /// Returns transactions that are in the same L2 miniblock as replay_tx, but were executed before it. + pub async fn get_earlier_transactions_in_same_block(&self, replay_tx: H256) -> Vec { + let tx_details = self + .fork_source + .get_transaction_by_hash(replay_tx) + .unwrap() + .unwrap(); + let miniblock = MiniblockNumber(tx_details.block_number.unwrap().as_u32()); + + // And we're fetching all the transactions from this miniblock. + let block_transactions = self + .fork_source + .get_raw_block_transactions(miniblock) + .unwrap(); + + let mut tx_to_apply = Vec::new(); + + for tx in block_transactions { + let h = tx.hash(); + let l2_tx: L2Tx = tx.try_into().unwrap(); + tx_to_apply.push(l2_tx); + + if h == replay_tx { + return tx_to_apply; + } + } + panic!( + "Cound not find tx {:?} in miniblock: {:?}", + replay_tx, miniblock + ); + } +} + +#[cfg(test)] +mod tests { + use zksync_basic_types::{AccountTreeId, L1BatchNumber, H256}; + use zksync_state::ReadStorage; + use zksync_types::{api::TransactionVariant, StorageKey}; + + use crate::{deps::InMemoryStorage, system_contracts, testing}; + + use super::{ForkDetails, ForkStorage}; + + #[test] + fn test_initial_writes() { + let account = AccountTreeId::default(); + let never_written_key = StorageKey::new(account, H256::from_low_u64_be(1)); + let key_with_some_value = StorageKey::new(account, H256::from_low_u64_be(2)); + let key_with_value_0 = StorageKey::new(account, H256::from_low_u64_be(3)); + let mut in_memory_storage = InMemoryStorage::default(); + in_memory_storage.set_value(key_with_some_value, H256::from_low_u64_be(13)); + in_memory_storage.set_value(key_with_value_0, H256::from_low_u64_be(0)); + + let external_storage = testing::ExternalStorage { + raw_storage: in_memory_storage, + }; + + let options = system_contracts::Options::default(); + + let fork_details = ForkDetails { + fork_source: &external_storage, + l1_block: L1BatchNumber(1), + l2_block: zksync_types::api::Block::::default(), + l2_miniblock: 1, + l2_miniblock_hash: H256::zero(), + block_timestamp: 0, + overwrite_chain_id: None, + l1_gas_price: 100, + }; + + let mut fork_storage = ForkStorage::new(Some(fork_details), &options); + + assert_eq!(fork_storage.is_write_initial(&never_written_key), true); + assert_eq!(fork_storage.is_write_initial(&key_with_some_value), false); + // This is the current limitation of the sytem. In theory, this should return false - as the value was written, but we don't have the API to the + // backend to get this information. + assert_eq!(fork_storage.is_write_initial(&key_with_value_0), true); + + // But writing any value there in the local storage (even 0) - should make it non-initial write immediately. + fork_storage.set_value(key_with_value_0, H256::zero()); + assert_eq!(fork_storage.is_write_initial(&key_with_value_0), false); + } +} diff --git a/.test-node-subtree/src/formatter.rs b/.test-node-subtree/src/formatter.rs new file mode 100644 index 00000000..b6629ce5 --- /dev/null +++ b/.test-node-subtree/src/formatter.rs @@ -0,0 +1,302 @@ +//! Helper methods to display transaction data in more human readable way. +use crate::{node::ShowCalls, resolver}; + +use colored::Colorize; + +use serde::Deserialize; +use std::collections::HashMap; +use std::str; + +use crate::fork::block_on; +use zksync_basic_types::H160; + +use multivm::interface::VmExecutionResultAndLogs; +use zksync_types::{vm_trace::Call, StorageLogQuery, StorageLogQueryType, VmEvent}; + +use lazy_static::lazy_static; + +#[derive(Debug, Deserialize, Clone, PartialEq, Eq)] +pub enum ContractType { + System, + Precompile, + Popular, + Unknown, +} + +#[derive(Debug, Deserialize, Clone)] +pub struct KnownAddress { + address: H160, + name: String, + contract_type: ContractType, +} + +lazy_static! { + /// Loads the known contact addresses from the JSON file. + static ref KNOWN_ADDRESSES: HashMap = { + let json_value = serde_json::from_slice(include_bytes!("data/address_map.json")).unwrap(); + let pairs: Vec = serde_json::from_value(json_value).unwrap(); + + pairs + .into_iter() + .map(|entry| (entry.address, entry)) + .collect() + }; +} + +fn address_to_human_readable(address: H160) -> Option { + KNOWN_ADDRESSES + .get(&address) + .map(|known_address| match known_address.contract_type { + ContractType::System => known_address.name.to_string(), + ContractType::Precompile => format!("{}", known_address.name.dimmed()), + ContractType::Popular => format!("{}", known_address.name.green()), + ContractType::Unknown => known_address.name.to_string(), + }) +} + +/// Pretty-prints event object +/// if skip_resolve is false, will try to contact openchain to resolve the topic hashes. +pub fn print_event(event: &VmEvent, resolve_hashes: bool) { + let event = event.clone(); + block_on(async move { + let mut tt: Vec = vec![]; + if !resolve_hashes { + tt = event + .indexed_topics + .iter() + .map(|t| format!("{:#x}", t)) + .collect(); + } else { + for topic in event.indexed_topics { + let selector = resolver::decode_event_selector(&format!("{:#x}", topic)) + .await + .unwrap(); + tt.push(selector.unwrap_or(format!("{:#x}", topic))); + } + } + + tracing::info!( + "{}", + address_to_human_readable(event.address) + .map(|x| format!("{:42}", x.blue())) + .unwrap_or(format!("{:42}", format!("{:?}", event.address).blue())) + ); + + tracing::info!("{}", " Topics:".truecolor(128, 128, 128)); + for indexed_topic in &tt { + tracing::info!(" {}", indexed_topic); + } + + if event.value.is_empty() { + tracing::info!("{}", " Data: EMPTY".truecolor(128, 128, 128)); + } else { + match str::from_utf8(&event.value) { + Ok(v) => { + tracing::info!( + "{} {}", + " Data (String):".truecolor(128, 128, 128), + v.to_string() + ); + } + Err(_) => { + let hex_str = hex::encode(&event.value); + let display_str = if hex_str.len() > 200 { + format!("{}...", &hex_str[..200]) + } else { + hex_str.to_string() + }; + + tracing::info!( + "{} 0x{}", + " Data (Hex):".truecolor(128, 128, 128), + display_str + ); + } + }; + } + + tracing::info!(""); + }); +} + +/// Pretty-prints contents of a 'call' - including subcalls. +/// If skip_resolve is false, will try to contact openchain to resolve the ABI names. +pub fn print_call(call: &Call, padding: usize, show_calls: &ShowCalls, resolve_hashes: bool) { + let contract_type = KNOWN_ADDRESSES + .get(&call.to) + .cloned() + .map(|known_address| known_address.contract_type) + .unwrap_or(ContractType::Unknown); + + let should_print = match (&contract_type, &show_calls) { + (_, ShowCalls::All) => true, + (_, ShowCalls::None) => false, + // now we're left only with 'user' and 'system' + (ContractType::Unknown, _) => true, + (ContractType::Popular, _) => true, + (ContractType::Precompile, _) => false, + // Now we're left with System + (ContractType::System, ShowCalls::User) => false, + (ContractType::System, ShowCalls::System) => true, + }; + if should_print { + let function_signature = if call.input.len() >= 4 { + let sig = call.input.as_slice()[..4] + .iter() + .map(|byte| format!("{:02x}", byte)) + .collect::>() + .join(""); + + if contract_type == ContractType::Precompile || !resolve_hashes { + format!("{:>16}", sig) + } else { + block_on(async move { + let fetch = resolver::decode_function_selector(&sig).await.unwrap(); + fetch.unwrap_or(format!("{:>16}", format!("0x{}", sig).dimmed())) + }) + } + } else { + format!( + "0x{}", + call.input + .as_slice() + .iter() + .map(|byte| format!("{:02x}", byte)) + .collect::>() + .join("") + ) + }; + + let pretty_print = format!( + "{}{:?} {} {} {} {} {}", + " ".repeat(padding), + call.r#type, + address_to_human_readable(call.to) + .map(|x| format!("{:<52}", x)) + .unwrap_or(format!("{:<52}", format!("{:?}", call.to).bold())), + function_signature, + call.revert_reason + .as_ref() + .map(|s| format!("Revert: {}", s)) + .unwrap_or_default(), + call.error + .as_ref() + .map(|s| format!("Error: {}", s)) + .unwrap_or_default(), + call.gas + ); + + if call.revert_reason.as_ref().is_some() || call.error.as_ref().is_some() { + tracing::info!("{}", pretty_print.on_red()); + } else { + tracing::info!("{}", pretty_print); + } + } + for subcall in &call.calls { + print_call(subcall, padding + 2, show_calls, resolve_hashes); + } +} + +/// Amount of pubdata that given write has cost. +pub enum PubdataBytesInfo { + // This slot is free + FreeSlot, + // This slot costs this much. + Paid(u32), + // This happens when we already paid a litte for this slot in the past. + // This slots costs additional X, the total cost is Y. + AdditionalPayment(u32, u32), + // We already paid for this slot in this transaction. + PaidAlready, +} + +impl std::fmt::Display for PubdataBytesInfo { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + match self { + PubdataBytesInfo::FreeSlot => write!(f, "free slot"), + PubdataBytesInfo::Paid(cost) => write!(f, "{:?} bytes", cost), + PubdataBytesInfo::AdditionalPayment(additional_cost, total_cost) => write!( + f, + "{:?} addditional bytes, {:?} total cost", + additional_cost, total_cost + ), + PubdataBytesInfo::PaidAlready => write!(f, "already paid"), + } + } +} + +impl PubdataBytesInfo { + // Whether the slot incurs any cost + pub fn does_cost(&self) -> bool { + match self { + PubdataBytesInfo::FreeSlot => false, + PubdataBytesInfo::Paid(_) => true, + PubdataBytesInfo::AdditionalPayment(_, _) => true, + PubdataBytesInfo::PaidAlready => false, + } + } +} + +pub fn print_logs(log_query: &StorageLogQuery, pubdata_bytes: Option) { + let separator = "─".repeat(82); + tracing::info!("{:<15} {:?}", "Type:", log_query.log_type); + tracing::info!( + "{:<15} {}", + "Address:", + address_to_human_readable(log_query.log_query.address) + .unwrap_or(format!("{}", log_query.log_query.address)) + ); + tracing::info!("{:<15} {:#066x}", "Key:", log_query.log_query.key); + + tracing::info!( + "{:<15} {:#066x}", + "Read Value:", + log_query.log_query.read_value + ); + + if log_query.log_type != StorageLogQueryType::Read { + tracing::info!( + "{:<15} {:#066x}", + "Written Value:", + log_query.log_query.written_value + ); + } + if let Some(pubdata_bytes) = pubdata_bytes { + tracing::info!("{:<15} {:}", "Pubdata bytes:", pubdata_bytes); + } + tracing::info!("{}", separator); +} + +pub fn print_vm_details(result: &VmExecutionResultAndLogs) { + tracing::info!(""); + tracing::info!("┌──────────────────────────┐"); + tracing::info!("│ VM EXECUTION RESULTS │"); + tracing::info!("└──────────────────────────┘"); + + tracing::info!("Cycles Used: {}", result.statistics.cycles_used); + tracing::info!( + "Computation Gas Used: {}", + result.statistics.computational_gas_used + ); + tracing::info!("Contracts Used: {}", result.statistics.contracts_used); + match &result.result { + multivm::interface::ExecutionResult::Success { .. } => {} + multivm::interface::ExecutionResult::Revert { output } => { + tracing::info!(""); + tracing::info!( + "{}", + format!( + "\n[!] Revert Reason: {}", + output.to_user_friendly_string() + ) + .on_red() + ); + } + multivm::interface::ExecutionResult::Halt { reason } => { + tracing::info!(""); + tracing::info!("{}", format!("\n[!] Halt Reason: {}", reason).on_red()); + } + } + + tracing::info!("════════════════════════════"); +} diff --git a/.test-node-subtree/src/http_fork_source.rs b/.test-node-subtree/src/http_fork_source.rs new file mode 100644 index 00000000..4cbb3439 --- /dev/null +++ b/.test-node-subtree/src/http_fork_source.rs @@ -0,0 +1,761 @@ +use std::sync::{Arc, RwLock}; + +use crate::{ + cache::{Cache, CacheConfig}, + fork::{block_on, ForkSource}, +}; +use eyre::Context; +use zksync_basic_types::{H256, U256}; +use zksync_types::api::{BridgeAddresses, Transaction}; +use zksync_web3_decl::types::Token; +use zksync_web3_decl::{ + jsonrpsee::http_client::{HttpClient, HttpClientBuilder}, + namespaces::{EthNamespaceClient, ZksNamespaceClient}, + types::Index, +}; + +#[derive(Debug, Clone)] +/// Fork source that gets the data via HTTP requests. +pub struct HttpForkSource { + /// URL for the network to fork. + pub fork_url: String, + /// Cache for network data. + pub(crate) cache: Arc>, +} + +impl HttpForkSource { + pub fn new(fork_url: String, cache_config: CacheConfig) -> Self { + Self { + fork_url, + cache: Arc::new(RwLock::new(Cache::new(cache_config))), + } + } + + pub fn create_client(&self) -> HttpClient { + HttpClientBuilder::default() + .build(self.fork_url.clone()) + .unwrap_or_else(|_| panic!("Unable to create a client for fork: {}", self.fork_url)) + } +} + +impl ForkSource for HttpForkSource { + fn get_storage_at( + &self, + address: zksync_basic_types::Address, + idx: zksync_basic_types::U256, + block: Option, + ) -> eyre::Result { + let client = self.create_client(); + block_on(async move { client.get_storage_at(address, idx, block).await }) + .wrap_err("fork http client failed") + } + + fn get_bytecode_by_hash( + &self, + hash: zksync_basic_types::H256, + ) -> eyre::Result>> { + let client = self.create_client(); + block_on(async move { client.get_bytecode_by_hash(hash).await }) + .wrap_err("fork http client failed") + } + + fn get_transaction_by_hash( + &self, + hash: zksync_basic_types::H256, + ) -> eyre::Result> { + if let Ok(Some(transaction)) = self + .cache + .read() + .map(|guard| guard.get_transaction(&hash).cloned()) + { + tracing::debug!("using cached transaction for {hash}"); + return Ok(Some(transaction)); + } + + let client = self.create_client(); + block_on(async move { client.get_transaction_by_hash(hash).await }) + .map(|maybe_transaction| { + if let Some(transaction) = &maybe_transaction { + self.cache + .write() + .map(|mut guard| guard.insert_transaction(hash, transaction.clone())) + .unwrap_or_else(|err| { + tracing::warn!( + "failed writing to cache for 'get_transaction_by_hash': {:?}", + err + ) + }); + } + maybe_transaction + }) + .wrap_err("fork http client failed") + } + + fn get_transaction_details( + &self, + hash: H256, + ) -> eyre::Result> { + let client = self.create_client(); + // n.b- We don't cache these responses as they will change through the lifecycle of the transaction + // and caching could be error-prone. in theory we could cache responses once the txn status + // is `final` or `failed` but currently this does not warrant the additional complexity. + block_on(async move { client.get_transaction_details(hash).await }) + .wrap_err("fork http client failed") + } + + fn get_raw_block_transactions( + &self, + block_number: zksync_basic_types::MiniblockNumber, + ) -> eyre::Result> { + let number = block_number.0 as u64; + if let Ok(Some(transaction)) = self + .cache + .read() + .map(|guard| guard.get_block_raw_transactions(&number).cloned()) + { + tracing::debug!("using cached raw transactions for block {block_number}"); + return Ok(transaction); + } + + let client = self.create_client(); + block_on(async move { client.get_raw_block_transactions(block_number).await }) + .wrap_err("fork http client failed") + .map(|transactions| { + if !transactions.is_empty() { + self.cache + .write() + .map(|mut guard| { + guard.insert_block_raw_transactions(number, transactions.clone()) + }) + .unwrap_or_else(|err| { + tracing::warn!( + "failed writing to cache for 'get_raw_block_transactions': {:?}", + err + ) + }); + } + transactions + }) + } + + fn get_block_by_hash( + &self, + hash: zksync_basic_types::H256, + full_transactions: bool, + ) -> eyre::Result>> { + if let Ok(Some(block)) = self + .cache + .read() + .map(|guard| guard.get_block(&hash, full_transactions).cloned()) + { + tracing::debug!("using cached block for {hash}"); + return Ok(Some(block)); + } + + let client = self.create_client(); + block_on(async move { client.get_block_by_hash(hash, full_transactions).await }) + .map(|block| { + if let Some(block) = &block { + self.cache + .write() + .map(|mut guard| guard.insert_block(hash, full_transactions, block.clone())) + .unwrap_or_else(|err| { + tracing::warn!( + "failed writing to cache for 'get_block_by_hash': {:?}", + err + ) + }); + } + block + }) + .wrap_err("fork http client failed") + } + + fn get_block_by_number( + &self, + block_number: zksync_types::api::BlockNumber, + full_transactions: bool, + ) -> eyre::Result>> { + let maybe_number = match block_number { + zksync_types::api::BlockNumber::Number(block_number) => Some(block_number), + _ => None, + }; + + if let Some(block) = maybe_number.and_then(|number| { + self.cache.read().ok().and_then(|guard| { + guard + .get_block_hash(&number.as_u64()) + .and_then(|hash| guard.get_block(hash, full_transactions).cloned()) + }) + }) { + tracing::debug!("using cached block for {block_number}"); + return Ok(Some(block)); + } + + let client = self.create_client(); + block_on(async move { + client + .get_block_by_number(block_number, full_transactions) + .await + }) + .map(|block| { + if let Some(block) = &block { + self.cache + .write() + .map(|mut guard| { + guard.insert_block(block.hash, full_transactions, block.clone()) + }) + .unwrap_or_else(|err| { + tracing::warn!( + "failed writing to cache for 'get_block_by_number': {:?}", + err + ) + }); + } + block + }) + .wrap_err("fork http client failed") + } + + /// Returns the transaction count for a given block hash. + fn get_block_transaction_count_by_hash(&self, block_hash: H256) -> eyre::Result> { + let client = self.create_client(); + block_on(async move { client.get_block_transaction_count_by_hash(block_hash).await }) + .wrap_err("fork http client failed") + } + + /// Returns the transaction count for a given block number. + fn get_block_transaction_count_by_number( + &self, + block_number: zksync_types::api::BlockNumber, + ) -> eyre::Result> { + let client = self.create_client(); + block_on(async move { + client + .get_block_transaction_count_by_number(block_number) + .await + }) + .wrap_err("fork http client failed") + } + + /// Returns information about a transaction by block hash and transaction index position. + fn get_transaction_by_block_hash_and_index( + &self, + block_hash: H256, + index: Index, + ) -> eyre::Result> { + let client = self.create_client(); + block_on(async move { + client + .get_transaction_by_block_hash_and_index(block_hash, index) + .await + }) + .wrap_err("fork http client failed") + } + + /// Returns information about a transaction by block number and transaction index position. + fn get_transaction_by_block_number_and_index( + &self, + block_number: zksync_types::api::BlockNumber, + index: Index, + ) -> eyre::Result> { + let client = self.create_client(); + block_on(async move { + client + .get_transaction_by_block_number_and_index(block_number, index) + .await + }) + .wrap_err("fork http client failed") + } + + /// Returns details of a block, given miniblock number + fn get_block_details( + &self, + miniblock: zksync_basic_types::MiniblockNumber, + ) -> eyre::Result> { + let client = self.create_client(); + block_on(async move { client.get_block_details(miniblock).await }) + .wrap_err("fork http client failed") + } + + /// Returns addresses of the default bridge contracts. + fn get_bridge_contracts(&self) -> eyre::Result { + if let Some(bridge_addresses) = self + .cache + .read() + .ok() + .and_then(|guard| guard.get_bridge_addresses().cloned()) + { + tracing::debug!("using cached bridge contracts"); + return Ok(bridge_addresses); + }; + + let client = self.create_client(); + block_on(async move { client.get_bridge_contracts().await }) + .map(|bridge_addresses| { + self.cache + .write() + .map(|mut guard| guard.set_bridge_addresses(bridge_addresses.clone())) + .unwrap_or_else(|err| { + tracing::warn!( + "failed writing to cache for 'get_bridge_contracts': {:?}", + err + ) + }); + bridge_addresses + }) + .wrap_err("fork http client failed") + } + + /// Returns known token addresses + fn get_confirmed_tokens(&self, from: u32, limit: u8) -> eyre::Result> { + if let Some(confirmed_tokens) = self + .cache + .read() + .ok() + .and_then(|guard| guard.get_confirmed_tokens(from, limit).cloned()) + { + tracing::debug!("using cached confirmed_tokens"); + return Ok(confirmed_tokens); + }; + + let client = self.create_client(); + block_on(async move { client.get_confirmed_tokens(from, limit).await }) + .map(|confirmed_tokens| { + self.cache + .write() + .map(|mut guard| { + guard.set_confirmed_tokens(from, limit, confirmed_tokens.clone()) + }) + .unwrap_or_else(|err| { + tracing::warn!( + "failed writing to cache for 'set_confirmed_tokens': {:?}", + err + ) + }); + confirmed_tokens + }) + .wrap_err("fork http client failed") + } +} + +#[cfg(test)] +mod tests { + use std::str::FromStr; + + use zksync_basic_types::{Address, MiniblockNumber, H160, H256, U64}; + use zksync_types::api::BlockNumber; + + use crate::testing; + + use super::*; + + #[test] + fn test_get_block_by_hash_full_is_cached() { + let input_block_hash = H256::repeat_byte(0x01); + let input_block_number = 8; + + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getBlockByHash", + "params": [ + format!("{input_block_hash:#x}"), + true + ], + }), + testing::BlockResponseBuilder::new() + .set_hash(input_block_hash) + .set_number(input_block_number) + .build(), + ); + + let fork_source = HttpForkSource::new(mock_server.url(), CacheConfig::Memory); + + let actual_block = fork_source + .get_block_by_hash(input_block_hash, true) + .expect("failed fetching block by hash") + .expect("no block"); + + assert_eq!(input_block_hash, actual_block.hash); + assert_eq!(U64::from(input_block_number), actual_block.number); + + let actual_block = fork_source + .get_block_by_hash(input_block_hash, true) + .expect("failed fetching cached block by hash") + .expect("no block"); + + assert_eq!(input_block_hash, actual_block.hash); + assert_eq!(U64::from(input_block_number), actual_block.number); + } + + #[test] + fn test_get_block_by_hash_minimal_is_cached() { + let input_block_hash = H256::repeat_byte(0x01); + let input_block_number = 8; + + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getBlockByHash", + "params": [ + format!("{input_block_hash:#x}"), + false + ], + }), + testing::BlockResponseBuilder::new() + .set_hash(input_block_hash) + .set_number(input_block_number) + .build(), + ); + + let fork_source = HttpForkSource::new(mock_server.url(), CacheConfig::Memory); + + let actual_block = fork_source + .get_block_by_hash(input_block_hash, false) + .expect("failed fetching block by hash") + .expect("no block"); + + assert_eq!(input_block_hash, actual_block.hash); + assert_eq!(U64::from(input_block_number), actual_block.number); + + let actual_block = fork_source + .get_block_by_hash(input_block_hash, false) + .expect("failed fetching cached block by hash") + .expect("no block"); + + assert_eq!(input_block_hash, actual_block.hash); + assert_eq!(U64::from(input_block_number), actual_block.number); + } + + #[test] + fn test_get_block_by_number_full_is_cached() { + let input_block_hash = H256::repeat_byte(0x01); + let input_block_number = 8; + + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getBlockByNumber", + "params": [ + format!("{input_block_number:#x}"), + true + ], + }), + testing::BlockResponseBuilder::new() + .set_hash(input_block_hash) + .set_number(input_block_number) + .build(), + ); + + let fork_source = HttpForkSource::new(mock_server.url(), CacheConfig::Memory); + + let actual_block = fork_source + .get_block_by_number( + zksync_types::api::BlockNumber::Number(U64::from(input_block_number)), + true, + ) + .expect("failed fetching block by number") + .expect("no block"); + + assert_eq!(input_block_hash, actual_block.hash); + assert_eq!(U64::from(input_block_number), actual_block.number); + + let actual_block = fork_source + .get_block_by_number( + zksync_types::api::BlockNumber::Number(U64::from(input_block_number)), + true, + ) + .expect("failed fetching cached block by number") + .expect("no block"); + + assert_eq!(input_block_hash, actual_block.hash); + assert_eq!(U64::from(input_block_number), actual_block.number); + } + + #[test] + fn test_get_block_by_number_minimal_is_cached() { + let input_block_hash = H256::repeat_byte(0x01); + let input_block_number = 8; + + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getBlockByNumber", + "params": [ + format!("{input_block_number:#x}"), + false + ], + }), + testing::BlockResponseBuilder::new() + .set_hash(input_block_hash) + .set_number(input_block_number) + .build(), + ); + + let fork_source = HttpForkSource::new(mock_server.url(), CacheConfig::Memory); + + let actual_block = fork_source + .get_block_by_number(BlockNumber::Number(U64::from(input_block_number)), false) + .expect("failed fetching block by number") + .expect("no block"); + + assert_eq!(input_block_hash, actual_block.hash); + assert_eq!(U64::from(input_block_number), actual_block.number); + + let actual_block = fork_source + .get_block_by_number(BlockNumber::Number(U64::from(input_block_number)), false) + .expect("failed fetching cached block by number") + .expect("no block"); + + assert_eq!(input_block_hash, actual_block.hash); + assert_eq!(U64::from(input_block_number), actual_block.number); + } + + #[test] + fn test_get_raw_block_transactions_is_cached() { + let input_block_number = 8u32; + + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getRawBlockTransactions", + "params": [ + input_block_number, + ], + }), + testing::RawTransactionsResponseBuilder::new() + .add(1) + .build(), + ); + + let fork_source = HttpForkSource::new(mock_server.url(), CacheConfig::Memory); + + let actual_raw_transactions = fork_source + .get_raw_block_transactions(MiniblockNumber(input_block_number)) + .expect("failed fetching block raw transactions"); + assert_eq!(1, actual_raw_transactions.len()); + + let actual_raw_transactions = fork_source + .get_raw_block_transactions(MiniblockNumber(input_block_number)) + .expect("failed fetching cached block raw transactions"); + assert_eq!(1, actual_raw_transactions.len()); + } + + #[test] + fn test_get_transactions_is_cached() { + let input_tx_hash = H256::repeat_byte(0x01); + + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getTransactionByHash", + "params": [ + input_tx_hash, + ], + }), + testing::TransactionResponseBuilder::new() + .set_hash(input_tx_hash) + .build(), + ); + + let fork_source = HttpForkSource::new(mock_server.url(), CacheConfig::Memory); + + let actual_transaction = fork_source + .get_transaction_by_hash(input_tx_hash) + .expect("failed fetching transaction") + .expect("no transaction"); + assert_eq!(input_tx_hash, actual_transaction.hash); + + let actual_transaction = fork_source + .get_transaction_by_hash(input_tx_hash) + .expect("failed fetching cached transaction") + .expect("no transaction"); + assert_eq!(input_tx_hash, actual_transaction.hash); + } + + #[test] + fn test_get_transaction_details() { + let input_tx_hash = H256::repeat_byte(0x01); + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getTransactionDetails", + "params": [ + input_tx_hash, + ], + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": { + "isL1Originated": false, + "status": "included", + "fee": "0x74293f087500", + "gasPerPubdata": "0x4e20", + "initiatorAddress": "0x63ab285cd87a189f345fed7dd4e33780393e01f0", + "receivedAt": "2023-10-12T15:45:53.094Z", + "ethCommitTxHash": null, + "ethProveTxHash": null, + "ethExecuteTxHash": null + }, + "id": 0 + }), + ); + + let fork_source = HttpForkSource::new(mock_server.url(), CacheConfig::Memory); + let transaction_details = fork_source + .get_transaction_details(input_tx_hash) + .expect("failed fetching transaction") + .expect("no transaction"); + assert_eq!( + transaction_details.initiator_address, + Address::from_str("0x63ab285cd87a189f345fed7dd4e33780393e01f0").unwrap() + ); + } + + #[test] + fn test_get_block_details() { + let miniblock = MiniblockNumber::from(16474138); + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getBlockDetails", + "params": [ + miniblock.0, + ], + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": { + "number": 16474138, + "l1BatchNumber": 270435, + "timestamp": 1697405098, + "l1TxCount": 0, + "l2TxCount": 1, + "rootHash": "0xd9e60f9a684fd7fc16e87ae923341a6e4af24f286e76612efdfc2d55f3f4d064", + "status": "sealed", + "commitTxHash": null, + "committedAt": null, + "proveTxHash": null, + "provenAt": null, + "executeTxHash": null, + "executedAt": null, + "l1GasPrice": 6156252068u64, + "l2FairGasPrice": 250000000u64, + "baseSystemContractsHashes": { + "bootloader": "0x0100089b8a2f2e6a20ba28f02c9e0ed0c13d702932364561a0ea61621f65f0a8", + "default_aa": "0x0100067d16a5485875b4249040bf421f53e869337fe118ec747cf40a4c777e5f" + }, + "operatorAddress": "0xa9232040bf0e0aea2578a5b2243f2916dbfc0a69", + "protocolVersion": "Version15" + }, + "id": 0 + }), + ); + + let fork_source = HttpForkSource::new(mock_server.url(), CacheConfig::Memory); + let block_details = fork_source + .get_block_details(miniblock) + .expect("failed fetching transaction") + .expect("no transaction"); + assert_eq!( + block_details.operator_address, + Address::from_str("0xa9232040bf0e0aea2578a5b2243f2916dbfc0a69").unwrap() + ); + } + + #[test] + fn test_get_bridge_contracts_is_cached() { + let input_bridge_addresses = BridgeAddresses { + l1_erc20_default_bridge: H160::repeat_byte(0x1), + l2_erc20_default_bridge: H160::repeat_byte(0x2), + l1_weth_bridge: Some(H160::repeat_byte(0x3)), + l2_weth_bridge: Some(H160::repeat_byte(0x4)), + }; + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getBridgeContracts", + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": { + "l1Erc20DefaultBridge": format!("{:#x}", input_bridge_addresses.l1_erc20_default_bridge), + "l2Erc20DefaultBridge": format!("{:#x}", input_bridge_addresses.l2_erc20_default_bridge), + "l1WethBridge": format!("{:#x}", input_bridge_addresses.l1_weth_bridge.unwrap()), + "l2WethBridge": format!("{:#x}", input_bridge_addresses.l2_weth_bridge.unwrap()) + }, + "id": 0 + }), + ); + + let fork_source = HttpForkSource::new(mock_server.url(), CacheConfig::Memory); + + let actual_bridge_addresses = fork_source + .get_bridge_contracts() + .expect("failed fetching bridge addresses"); + testing::assert_bridge_addresses_eq(&input_bridge_addresses, &actual_bridge_addresses); + + let actual_bridge_addresses = fork_source + .get_bridge_contracts() + .expect("failed fetching bridge addresses"); + testing::assert_bridge_addresses_eq(&input_bridge_addresses, &actual_bridge_addresses); + } + + #[test] + fn test_get_confirmed_tokens_is_cached() { + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getConfirmedTokens", + "params": [0, 100] + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": [ + { + "decimals": 18, + "l1Address": "0xbe9895146f7af43049ca1c1ae358b0541ea49704", + "l2Address": "0x75af292c1c9a37b3ea2e6041168b4e48875b9ed5", + "name": "Coinbase Wrapped Staked ETH", + "symbol": "cbETH" + } + ], + "id": 0 + }), + ); + + let fork_source = HttpForkSource::new(mock_server.url(), CacheConfig::Memory); + + let tokens = fork_source + .get_confirmed_tokens(0, 100) + .expect("failed fetching tokens"); + assert_eq!(tokens.len(), 1); + assert_eq!(tokens[0].symbol, "cbETH"); + + let tokens = fork_source + .get_confirmed_tokens(0, 100) + .expect("failed fetching tokens"); + assert_eq!(tokens.len(), 1); + } +} diff --git a/.test-node-subtree/src/lib.rs b/.test-node-subtree/src/lib.rs new file mode 100644 index 00000000..d28de8ac --- /dev/null +++ b/.test-node-subtree/src/lib.rs @@ -0,0 +1,59 @@ +//! zkSync Era In-Memory Node +//! +//! The `era-test-node` crate provides an in-memory node designed primarily for local testing. +//! It supports forking the state from other networks, making it a valuable tool for integration testing, +//! bootloader and system contract testing, and prototyping. +//! +//! ## Overview +//! +//! - **In-Memory Database**: The node uses an in-memory database for storing state information, +//! and employs simplified hashmaps for tracking blocks and transactions. +//! +//! - **Forking**: In fork mode, the node fetches missing storage data from a remote source if not available locally. +//! +//! - **Remote Server Interaction**: The node can use the remote server (openchain) to resolve the ABI and topics +//! to human-readable names. +//! +//! - **Local Testing**: Designed for local testing, this node is not intended for production use. +//! +//! ## Features +//! +//! - Fork the state of mainnet, testnet, or a custom network. +//! - Replay existing mainnet or testnet transactions. +//! - Use local bootloader and system contracts. +//! - Operate deterministically in non-fork mode. +//! - Start quickly with pre-configured 'rich' accounts. +//! - Resolve names of ABI functions and Events using openchain. +//! +//! ## Limitations +//! +//! - No communication between Layer 1 and Layer 2. +//! - Many APIs are not yet implemented. +//! - No support for accessing historical data. +//! - Only one transaction allowed per Layer 1 batch. +//! +//! ## Usage +//! +//! To start the node, use the command `era_test_node run`. For more advanced functionalities like forking or +//! replaying transactions, refer to the [official documentation](https://era.zksync.io/docs/tools/testing/era-test-node.html). +//! +//! ## Contributions +//! +//! Contributions to improve `era-test-node` are welcome. Please refer to the [contribution guidelines](https://github.com/matter-labs/era-test-node/blob/main/.github/CONTRIBUTING.md) for more details. + +pub mod bootloader_debug; +pub mod console_log; +pub mod deps; +pub mod filters; +pub mod fork; +pub mod formatter; +pub mod http_fork_source; +pub mod namespaces; +pub mod node; +pub mod observability; +pub mod resolver; +pub mod system_contracts; +pub mod utils; + +mod cache; +mod testing; diff --git a/.test-node-subtree/src/logging_middleware.rs b/.test-node-subtree/src/logging_middleware.rs new file mode 100644 index 00000000..1efde748 --- /dev/null +++ b/.test-node-subtree/src/logging_middleware.rs @@ -0,0 +1,93 @@ +use colored::Colorize; +use futures::Future; +use futures::{future::Either, FutureExt}; +use itertools::Itertools; +use jsonrpc_core::{ + middleware, Call, FutureResponse, Metadata, Middleware, Params, Request, Response, +}; +use tracing_subscriber::filter::LevelFilter; + +#[derive(Clone, Debug, Default)] +pub struct Meta(); +impl Metadata for Meta {} + +pub struct LoggingMiddleware { + log_level_filter: LevelFilter, +} + +impl LoggingMiddleware { + pub fn new(log_level_filter: LevelFilter) -> Self { + Self { log_level_filter } + } +} + +/// Logging Middleware for all in-bound requests +/// Logs out incoming requests and their parameters +/// Useful for debugging applications that are pointed at this service +impl Middleware for LoggingMiddleware { + type Future = FutureResponse; + type CallFuture = middleware::NoopCallFuture; + + fn on_request(&self, request: Request, meta: Meta, next: F) -> Either + where + F: FnOnce(Request, Meta) -> X + Send, + X: Future> + Send + 'static, + { + if let Request::Single(Call::MethodCall(method_call)) = &request { + match self.log_level_filter { + LevelFilter::TRACE => { + let full_params = match &method_call.params { + Params::Array(values) => { + if values.is_empty() { + String::default() + } else { + format!("with [{}]", values.iter().join(", ")) + } + } + _ => String::default(), + }; + + tracing::trace!("{} was called {}", method_call.method.cyan(), full_params); + } + _ => { + // Generate truncated params for requests with massive payloads + let truncated_params = match &method_call.params { + Params::Array(values) => { + if values.is_empty() { + String::default() + } else { + format!( + "with [{}]", + values + .iter() + .map(|s| { + let s_str = s.to_string(); + if s_str.len() > 70 { + format!("{:.67}...", s_str) + } else { + s_str + } + }) + .collect::>() + .join(", ") + ) + } + } + _ => String::default(), + }; + + tracing::debug!( + "{} was called {}", + method_call.method.cyan(), + truncated_params + ); + } + } + }; + + Either::Left(Box::pin(next(request, meta).map(move |res| { + tracing::trace!("API response => {:?}", res); + res + }))) + } +} diff --git a/.test-node-subtree/src/main.rs b/.test-node-subtree/src/main.rs new file mode 100644 index 00000000..8637bbd0 --- /dev/null +++ b/.test-node-subtree/src/main.rs @@ -0,0 +1,409 @@ +use crate::cache::CacheConfig; +use crate::node::{InMemoryNodeConfig, ShowGasDetails, ShowStorageLogs, ShowVMDetails}; +use crate::observability::Observability; +use clap::{Parser, Subcommand, ValueEnum}; +use colored::Colorize; +use fork::{ForkDetails, ForkSource}; +use logging_middleware::LoggingMiddleware; +use node::ShowCalls; +use observability::LogLevel; +use tracing_subscriber::filter::LevelFilter; + +mod bootloader_debug; +mod cache; +mod console_log; +mod deps; +mod filters; +mod fork; +mod formatter; +mod http_fork_source; +mod logging_middleware; +mod namespaces; +mod node; +pub mod observability; +mod resolver; +mod system_contracts; +mod testing; +mod utils; + +use node::InMemoryNode; + +use std::fs::File; +use std::{ + env, + net::{IpAddr, Ipv4Addr, SocketAddr}, + str::FromStr, +}; + +use futures::{ + channel::oneshot, + future::{self}, + FutureExt, +}; +use jsonrpc_core::MetaIoHandler; +use zksync_basic_types::{H160, H256}; + +use crate::namespaces::{ + ConfigurationApiNamespaceT, DebugNamespaceT, EthNamespaceT, EthTestNodeNamespaceT, + EvmNamespaceT, HardhatNamespaceT, NetNamespaceT, Web3NamespaceT, ZksNamespaceT, +}; + +/// List of legacy wallets (address, private key) that we seed with tokens at start. +pub const LEGACY_RICH_WALLETS: [(&str, &str); 10] = [ + ( + "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "0x7726827caac94a7f9e1b160f7ea819f172f7b6f9d2a97f992c38edeab82d4110", + ), + ( + "0xa61464658AfeAf65CccaaFD3a512b69A83B77618", + "0xac1e735be8536c6534bb4f17f06f6afc73b2b5ba84ac2cfb12f7461b20c0bbe3", + ), + ( + "0x0D43eB5B8a47bA8900d84AA36656c92024e9772e", + "0xd293c684d884d56f8d6abd64fc76757d3664904e309a0645baf8522ab6366d9e", + ), + ( + "0xA13c10C0D5bd6f79041B9835c63f91de35A15883", + "0x850683b40d4a740aa6e745f889a6fdc8327be76e122f5aba645a5b02d0248db8", + ), + ( + "0x8002cD98Cfb563492A6fB3E7C8243b7B9Ad4cc92", + "0xf12e28c0eb1ef4ff90478f6805b68d63737b7f33abfa091601140805da450d93", + ), + ( + "0x4F9133D1d3F50011A6859807C837bdCB31Aaab13", + "0xe667e57a9b8aaa6709e51ff7d093f1c5b73b63f9987e4ab4aa9a5c699e024ee8", + ), + ( + "0xbd29A1B981925B94eEc5c4F1125AF02a2Ec4d1cA", + "0x28a574ab2de8a00364d5dd4b07c4f2f574ef7fcc2a86a197f65abaec836d1959", + ), + ( + "0xedB6F5B4aab3dD95C7806Af42881FF12BE7e9daa", + "0x74d8b3a188f7260f67698eb44da07397a298df5427df681ef68c45b34b61f998", + ), + ( + "0xe706e60ab5Dc512C36A4646D719b889F398cbBcB", + "0xbe79721778b48bcc679b78edac0ce48306a8578186ffcb9f2ee455ae6efeace1", + ), + ( + "0xE90E12261CCb0F3F7976Ae611A29e84a6A85f424", + "0x3eb15da85647edd9a1159a4a13b9e7c56877c4eb33f614546d4db06a51868b1c", + ), +]; + +/// List of wallets (address, private key, mnemonic) that we seed with tokens at start. +pub const RICH_WALLETS: [(&str, &str, &str); 10] = [ + ( + "0xBC989fDe9e54cAd2aB4392Af6dF60f04873A033A", + "0x3d3cbc973389cb26f657686445bcc75662b415b656078503592ac8c1abb8810e", + "mass wild lava ripple clog cabbage witness shell unable tribe rubber enter", + ), + ( + "0x55bE1B079b53962746B2e86d12f158a41DF294A6", + "0x509ca2e9e6acf0ba086477910950125e698d4ea70fa6f63e000c5a22bda9361c", + "crumble clutch mammal lecture lazy broken nominee visit gentle gather gym erupt", + ), + ( + "0xCE9e6063674DC585F6F3c7eaBe82B9936143Ba6C", + "0x71781d3a358e7a65150e894264ccc594993fbc0ea12d69508a340bc1d4f5bfbc", + "illegal okay stereo tattoo between alien road nuclear blind wolf champion regular", + ), + ( + "0xd986b0cB0D1Ad4CCCF0C4947554003fC0Be548E9", + "0x379d31d4a7031ead87397f332aab69ef5cd843ba3898249ca1046633c0c7eefe", + "point donor practice wear alien abandon frozen glow they practice raven shiver", + ), + ( + "0x87d6ab9fE5Adef46228fB490810f0F5CB16D6d04", + "0x105de4e75fe465d075e1daae5647a02e3aad54b8d23cf1f70ba382b9f9bee839", + "giraffe organ club limb install nest journey client chunk settle slush copy", + ), + ( + "0x78cAD996530109838eb016619f5931a03250489A", + "0x7becc4a46e0c3b512d380ca73a4c868f790d1055a7698f38fb3ca2b2ac97efbb", + "awful organ version habit giraffe amused wire table begin gym pistol clean", + ), + ( + "0xc981b213603171963F81C687B9fC880d33CaeD16", + "0xe0415469c10f3b1142ce0262497fe5c7a0795f0cbfd466a6bfa31968d0f70841", + "exotic someone fall kitten salute nerve chimney enlist pair display over inside", + ), + ( + "0x42F3dc38Da81e984B92A95CBdAAA5fA2bd5cb1Ba", + "0x4d91647d0a8429ac4433c83254fb9625332693c848e578062fe96362f32bfe91", + "catch tragic rib twelve buffalo also gorilla toward cost enforce artefact slab", + ), + ( + "0x64F47EeD3dC749d13e49291d46Ea8378755fB6DF", + "0x41c9f9518aa07b50cb1c0cc160d45547f57638dd824a8d85b5eb3bf99ed2bdeb", + "arrange price fragile dinner device general vital excite penalty monkey major faculty", + ), + ( + "0xe2b8Cb53a43a56d4d2AB6131C81Bd76B86D3AFe5", + "0xb0680d66303a0163a19294f1ef8c95cd69a9d7902a4aca99c05f3e134e68a11a", + "increase pulp sing wood guilt cement satoshi tiny forum nuclear sudden thank", + ), +]; + +#[allow(clippy::too_many_arguments)] +async fn build_json_http< + S: std::marker::Sync + std::marker::Send + 'static + ForkSource + std::fmt::Debug + Clone, +>( + addr: SocketAddr, + log_level_filter: LevelFilter, + node: InMemoryNode, +) -> tokio::task::JoinHandle<()> { + let (sender, recv) = oneshot::channel::<()>(); + + let io_handler = { + let mut io = MetaIoHandler::with_middleware(LoggingMiddleware::new(log_level_filter)); + + io.extend_with(NetNamespaceT::to_delegate(node.clone())); + io.extend_with(Web3NamespaceT::to_delegate(node.clone())); + io.extend_with(ConfigurationApiNamespaceT::to_delegate(node.clone())); + io.extend_with(DebugNamespaceT::to_delegate(node.clone())); + io.extend_with(EthNamespaceT::to_delegate(node.clone())); + io.extend_with(EthTestNodeNamespaceT::to_delegate(node.clone())); + io.extend_with(EvmNamespaceT::to_delegate(node.clone())); + io.extend_with(HardhatNamespaceT::to_delegate(node.clone())); + io.extend_with(ZksNamespaceT::to_delegate(node)); + io + }; + + std::thread::spawn(move || { + let runtime = tokio::runtime::Builder::new_multi_thread() + .enable_all() + .worker_threads(1) + .build() + .unwrap(); + + let server = jsonrpc_http_server::ServerBuilder::new(io_handler) + .threads(1) + .event_loop_executor(runtime.handle().clone()) + .start_http(&addr) + .unwrap(); + + server.wait(); + let _ = sender; + }); + + tokio::spawn(recv.map(drop)) +} + +/// Cache type config for the node. +#[derive(ValueEnum, Debug, Clone)] +enum CacheType { + None, + Memory, + Disk, +} + +/// System contract options. +#[derive(ValueEnum, Debug, Clone)] +enum DevSystemContracts { + BuiltIn, + BuiltInNoVerify, + Local, +} + +#[derive(Debug, Parser)] +#[command(author = "Matter Labs", version, about = "Test Node", long_about = None)] +struct Cli { + #[command(subcommand)] + command: Command, + #[arg(long, default_value = "8011")] + /// Port to listen on - default: 8011 + port: u16, + #[arg(long, default_value = "none")] + /// Show call debug information + show_calls: ShowCalls, + #[arg(long, default_value = "none")] + /// Show storage log information + show_storage_logs: ShowStorageLogs, + #[arg(long, default_value = "none")] + /// Show VM details information + show_vm_details: ShowVMDetails, + + #[arg(long, default_value = "none")] + /// Show Gas details information + show_gas_details: ShowGasDetails, + + #[arg(long)] + /// If true, the tool will try to contact openchain to resolve the ABI & topic names. + /// It will make debug log more readable, but will decrease the performance. + resolve_hashes: bool, + + /// Specifies the option for the system contracts (use compiled built-in with or without signature verification, or load locally). + /// Default: built-in + #[arg(long, default_value = "built-in")] + dev_system_contracts: DevSystemContracts, + + /// Log filter level - default: info + #[arg(long, default_value = "info")] + log: LogLevel, + + /// Log file path - default: era_test_node.log + #[arg(long, default_value = "era_test_node.log")] + log_file_path: String, + + /// Cache type, can be one of `none`, `memory`, or `disk` - default: "disk" + #[arg(long, default_value = "disk")] + cache: CacheType, + + /// If true, will reset the local `disk` cache. + #[arg(long)] + reset_cache: bool, + + /// Cache directory location for `disk` cache - default: ".cache" + #[arg(long, default_value = ".cache")] + cache_dir: String, +} + +#[derive(Debug, Subcommand)] +enum Command { + /// Starts a new empty local network. + #[command(name = "run")] + Run, + /// Starts a local network that is a fork of another network. + #[command(name = "fork")] + Fork(ForkArgs), + /// Starts a local network that is a fork of another network, and replays a given TX on it. + #[command(name = "replay_tx")] + ReplayTx(ReplayArgs), +} + +#[derive(Debug, Parser)] +struct ForkArgs { + /// Whether to fork from existing network. + /// If not set - will start a new network from genesis. + /// If set - will try to fork a remote network. Possible values: + /// - mainnet + /// - testnet + /// - http://XXX:YY + network: String, + #[arg(long)] + // Fork at a given L2 miniblock height. + // If not set - will use the current finalized block from the network. + fork_at: Option, +} +#[derive(Debug, Parser)] +struct ReplayArgs { + /// Whether to fork from existing network. + /// If not set - will start a new network from genesis. + /// If set - will try to fork a remote network. Possible values: + /// - mainnet + /// - sepolia-testnet + /// - goerli-testnet + /// - http://XXX:YY + network: String, + /// Transaction hash to replay. + tx: H256, +} + +#[tokio::main] +async fn main() -> anyhow::Result<()> { + let opt = Cli::parse(); + let log_level_filter = LevelFilter::from(opt.log); + let log_file = File::create(opt.log_file_path)?; + + // Initialize the tracing subscriber + let observability = + Observability::init(String::from("era_test_node"), log_level_filter, log_file)?; + + if matches!(opt.dev_system_contracts, DevSystemContracts::Local) { + if let Some(path) = env::var_os("ZKSYNC_HOME") { + tracing::info!("+++++ Reading local contracts from {:?} +++++", path); + } + } + let cache_config = match opt.cache { + CacheType::None => CacheConfig::None, + CacheType::Memory => CacheConfig::Memory, + CacheType::Disk => CacheConfig::Disk { + dir: opt.cache_dir, + reset: opt.reset_cache, + }, + }; + + let fork_details = match &opt.command { + Command::Run => None, + Command::Fork(fork) => { + Some(ForkDetails::from_network(&fork.network, fork.fork_at, cache_config).await) + } + Command::ReplayTx(replay_tx) => { + Some(ForkDetails::from_network_tx(&replay_tx.network, replay_tx.tx, cache_config).await) + } + }; + + // If we're replaying the transaction, we need to sync to the previous block + // and then replay all the transactions that happened in + let transactions_to_replay = if let Command::ReplayTx(replay_tx) = &opt.command { + fork_details + .as_ref() + .unwrap() + .get_earlier_transactions_in_same_block(replay_tx.tx) + .await + } else { + vec![] + }; + let system_contracts_options = match opt.dev_system_contracts { + DevSystemContracts::BuiltIn => system_contracts::Options::BuiltIn, + DevSystemContracts::BuiltInNoVerify => system_contracts::Options::BuiltInWithoutSecurity, + DevSystemContracts::Local => system_contracts::Options::Local, + }; + + let node = InMemoryNode::new( + fork_details, + Some(observability), + InMemoryNodeConfig { + show_calls: opt.show_calls, + show_storage_logs: opt.show_storage_logs, + show_vm_details: opt.show_vm_details, + show_gas_details: opt.show_gas_details, + resolve_hashes: opt.resolve_hashes, + system_contracts_options, + }, + ); + + if !transactions_to_replay.is_empty() { + let _ = node.apply_txs(transactions_to_replay); + } + + tracing::info!(""); + tracing::info!("Rich Accounts"); + tracing::info!("============="); + for (_, wallet) in LEGACY_RICH_WALLETS.iter().enumerate() { + let address = wallet.0; + node.set_rich_account(H160::from_str(address).unwrap()); + } + for (index, wallet) in RICH_WALLETS.iter().enumerate() { + let address = wallet.0; + let private_key = wallet.1; + let mnemonic_phrase = wallet.2; + node.set_rich_account(H160::from_str(address).unwrap()); + tracing::info!( + "Account #{}: {} ({})", + index, + address, + "1_000_000_000_000 ETH".cyan() + ); + tracing::info!("Private Key: {}", private_key); + tracing::info!("Mnemonic: {}", &mnemonic_phrase.truecolor(128, 128, 128)); + tracing::info!(""); + } + + let threads = build_json_http( + SocketAddr::new(IpAddr::V4(Ipv4Addr::new(0, 0, 0, 0)), opt.port), + log_level_filter, + node, + ) + .await; + + tracing::info!("========================================"); + tracing::info!(" Node is ready at 127.0.0.1:{}", opt.port); + tracing::info!("========================================"); + + future::select_all(vec![threads]).await.0.unwrap(); + + Ok(()) +} diff --git a/.test-node-subtree/src/namespaces/config.rs b/.test-node-subtree/src/namespaces/config.rs new file mode 100644 index 00000000..32214b8c --- /dev/null +++ b/.test-node-subtree/src/namespaces/config.rs @@ -0,0 +1,93 @@ +use crate::namespaces::Result; +use crate::observability::LogLevel; +use jsonrpc_derive::rpc; + +#[rpc] +pub trait ConfigurationApiNamespaceT { + /// Get the InMemoryNodeInner's show_calls property as a string + /// + /// # Returns + /// The current `show_calls` value for the InMemoryNodeInner. + #[rpc(name = "config_getShowCalls", returns = "String")] + fn config_get_show_calls(&self) -> Result; + + /// Get the InMemoryNodeInner's current_timestamp property + /// + /// # Returns + /// The current `current_timestamp` value for the InMemoryNodeInner. + #[rpc(name = "config_getCurrentTimestamp", returns = "u64")] + fn config_get_current_timestamp(&self) -> Result; + + /// Set show_calls for the InMemoryNodeInner + /// + /// # Parameters + /// - `value`: A ShowCalls enum to update show_calls to + /// + /// # Returns + /// The updated/current `show_calls` value for the InMemoryNodeInner. + #[rpc(name = "config_setShowCalls", returns = "String")] + fn config_set_show_calls(&self, value: String) -> Result; + + /// Set show_storage_logs for the InMemoryNodeInner + /// + /// # Parameters + /// - `value`: A ShowStorageLogs enum to update show_storage_logs to + /// + /// # Returns + /// The updated/current `show_storage_logs` value for the InMemoryNodeInner. + #[rpc(name = "config_setShowStorageLogs", returns = "String")] + fn config_set_show_storage_logs(&self, value: String) -> Result; + + /// Set show_vm_details for the InMemoryNodeInner + /// + /// # Parameters + /// - `value`: A ShowVMDetails enum to update show_vm_details to + /// + /// # Returns + /// The updated/current `show_vm_details` value for the InMemoryNodeInner. + #[rpc(name = "config_setShowVmDetails", returns = "String")] + fn config_set_show_vm_details(&self, value: String) -> Result; + + /// Set show_gas_details for the InMemoryNodeInner + /// + /// # Parameters + /// - `value`: A ShowGasDetails enum to update show_gas_details to + /// + /// # Returns + /// The updated/current `show_gas_details` value for the InMemoryNodeInner. + #[rpc(name = "config_setShowGasDetails", returns = "String")] + fn config_set_show_gas_details(&self, value: String) -> Result; + + /// Set resolve_hashes for the InMemoryNodeInner + /// + /// # Parameters + /// - `value`: A bool to update resolve_hashes to + /// + /// # Returns + /// The updated `resolve_hashes` value for the InMemoryNodeInner. + #[rpc(name = "config_setResolveHashes", returns = "bool")] + fn config_set_resolve_hashes(&self, value: bool) -> Result; + + /// Set the logging for the InMemoryNodeInner + /// + /// # Parameters + /// - `level`: The log level to set. One of: ["trace", "debug", "info", "warn", "error"] + /// + /// # Returns + /// `true` if the operation succeeded, `false` otherwise. + #[rpc(name = "config_setLogLevel", returns = "bool")] + fn config_set_log_level(&self, level: LogLevel) -> Result; + + /// Set the logging for the InMemoryNodeInner + /// + /// # Parameters + /// - `level`: The logging directive to set. Example: + /// * "my_crate=debug" + /// * "my_crate::module=trace" + /// * "my_crate=debug,other_crate=warn" + /// + /// # Returns + /// `true` if the operation succeeded, `false` otherwise. + #[rpc(name = "config_setLogging", returns = "bool")] + fn config_set_logging(&self, directive: String) -> Result; +} diff --git a/.test-node-subtree/src/namespaces/debug.rs b/.test-node-subtree/src/namespaces/debug.rs new file mode 100644 index 00000000..421154a5 --- /dev/null +++ b/.test-node-subtree/src/namespaces/debug.rs @@ -0,0 +1,576 @@ +use crate::{ + fork::ForkSource, + node::{InMemoryNodeInner, MAX_TX_SIZE}, + utils::{create_debug_output, storage_view::StorageView, to_real_block_number}, +}; +use itertools::Itertools; +use jsonrpc_core::{BoxFuture, Result}; +use multivm::interface::VmInterface; +use multivm::vm_latest::{constants::ETH_CALL_GAS_LIMIT, CallTracer, Vm}; +use once_cell::sync::OnceCell; +use std::sync::{Arc, RwLock}; +use zksync_basic_types::H256; +use zksync_core::api_server::web3::backend_jsonrpc::{ + error::into_jsrpc_error, namespaces::debug::DebugNamespaceT, +}; +use zksync_types::{ + api::{BlockId, BlockNumber, DebugCall, ResultDebugCall, TracerConfig, TransactionVariant}, + l2::L2Tx, + transaction_request::CallRequest, + PackedEthSignature, Transaction, U64, +}; +use zksync_web3_decl::error::Web3Error; + +/// Implementation of DebugNamespaceImpl +pub struct DebugNamespaceImpl { + node: Arc>>, +} + +impl DebugNamespaceImpl { + /// Creates a new `Debug` instance with the given `node`. + pub fn new(node: Arc>>) -> Self { + Self { node } + } +} + +impl DebugNamespaceT + for DebugNamespaceImpl +{ + fn trace_block_by_number( + &self, + block: BlockNumber, + options: Option, + ) -> BoxFuture>> { + let only_top = options.is_some_and(|o| o.tracer_config.only_top_call); + let inner = Arc::clone(&self.node); + Box::pin(async move { + let inner = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let block = { + let number = + to_real_block_number(block, U64::from(inner.current_miniblock)).as_u64(); + + inner + .block_hashes + .get(&number) + .and_then(|hash| inner.blocks.get(hash)) + .ok_or_else(|| { + into_jsrpc_error(Web3Error::SubmitTransactionError( + "Block not found".to_string(), + vec![], + )) + })? + }; + + let tx_hashes = block + .transactions + .iter() + .map(|tx| match tx { + TransactionVariant::Full(tx) => tx.hash, + TransactionVariant::Hash(hash) => *hash, + }) + .collect_vec(); + + let debug_calls = tx_hashes + .into_iter() + .map(|tx_hash| { + let tx = inner.tx_results.get(&tx_hash).ok_or_else(|| { + into_jsrpc_error(Web3Error::SubmitTransactionError( + "Transaction not found".to_string(), + vec![], + )) + })?; + Ok(tx.debug_info(only_top)) + }) + .collect::>>()? + .into_iter() + .map(|result| ResultDebugCall { result }) + .collect_vec(); + + Ok(debug_calls) + }) + } + + fn trace_block_by_hash( + &self, + hash: H256, + options: Option, + ) -> BoxFuture>> { + let only_top = options.is_some_and(|o| o.tracer_config.only_top_call); + let inner = Arc::clone(&self.node); + Box::pin(async move { + let inner = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let block = inner.blocks.get(&hash).ok_or_else(|| { + into_jsrpc_error(Web3Error::SubmitTransactionError( + "Block not found".to_string(), + vec![], + )) + })?; + + let tx_hashes = block + .transactions + .iter() + .map(|tx| match tx { + TransactionVariant::Full(tx) => tx.hash, + TransactionVariant::Hash(hash) => *hash, + }) + .collect_vec(); + + let debug_calls = tx_hashes + .into_iter() + .map(|tx_hash| { + let tx = inner.tx_results.get(&tx_hash).ok_or_else(|| { + into_jsrpc_error(Web3Error::SubmitTransactionError( + "Transaction not found".to_string(), + vec![], + )) + })?; + Ok(tx.debug_info(only_top)) + }) + .collect::>>()? + .into_iter() + .map(|result| ResultDebugCall { result }) + .collect_vec(); + + Ok(debug_calls) + }) + } + + /// Trace execution of a transaction. + fn trace_call( + &self, + request: CallRequest, + block: Option, + options: Option, + ) -> BoxFuture> { + let only_top = options.is_some_and(|o| o.tracer_config.only_top_call); + let inner = Arc::clone(&self.node); + Box::pin(async move { + if block.is_some() && !matches!(block, Some(BlockId::Number(BlockNumber::Latest))) { + return Err(jsonrpc_core::Error::invalid_params( + "tracing only supported at `latest` block", + )); + } + + let inner = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let mut l2_tx = match L2Tx::from_request(request.into(), MAX_TX_SIZE) { + Ok(tx) => tx, + Err(e) => { + let error = Web3Error::SerializationError(e); + return Err(into_jsrpc_error(error)); + } + }; + + let execution_mode = multivm::interface::TxExecutionMode::EthCall; + let storage = StorageView::new(&inner.fork_storage).into_rc_ptr(); + + let bootloader_code = inner.system_contracts.contracts_for_l2_call(); + + // init vm + let (mut l1_batch_env, _block_context) = inner.create_l1_batch_env(storage.clone()); + + // update the enforced_base_fee within l1_batch_env to match the logic in zksync_core + l1_batch_env.enforced_base_fee = Some(l2_tx.common_data.fee.max_fee_per_gas.as_u64()); + let system_env = inner.create_system_env(bootloader_code.clone(), execution_mode); + let mut vm: Vm<_, HistoryDisabled> = Vm::new(l1_batch_env, system_env, storage); + + // We must inject *some* signature (otherwise bootloader code fails to generate hash). + if l2_tx.common_data.signature.is_empty() { + l2_tx.common_data.signature = + PackedEthSignature::default().serialize_packed().into(); + } + + // Match behavior of zksync_core: + // Protection against infinite-loop eth_calls and alike: + // limiting the amount of gas the call can use. + l2_tx.common_data.fee.gas_limit = ETH_CALL_GAS_LIMIT.into(); + + let tx: Transaction = l2_tx.clone().into(); + vm.push_transaction(tx); + + let call_tracer_result = Arc::new(OnceCell::default()); + let tracer = CallTracer::new(call_tracer_result.clone()).into_tracer_pointer(); + let tx_result = vm.inspect(tracer.into(), multivm::interface::VmExecutionMode::OneTx); + + let call_traces = if only_top { + vec![] + } else { + Arc::try_unwrap(call_tracer_result) + .unwrap() + .take() + .unwrap_or_default() + }; + + let debug = + create_debug_output(&l2_tx, &tx_result, call_traces).map_err(into_jsrpc_error)?; + + Ok(debug) + }) + } + + fn trace_transaction( + &self, + tx_hash: H256, + options: Option, + ) -> BoxFuture>> { + let only_top = options.is_some_and(|o| o.tracer_config.only_top_call); + let inner = Arc::clone(&self.node); + Box::pin(async move { + let inner = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + Ok(inner + .tx_results + .get(&tx_hash) + .map(|tx| tx.debug_info(only_top))) + }) + } +} + +#[cfg(test)] +mod tests { + use super::*; + use crate::{ + deps::system_contracts::bytecode_from_slice, + http_fork_source::HttpForkSource, + node::{InMemoryNode, TransactionResult}, + testing::{self, LogBuilder}, + }; + use ethers::abi::{short_signature, AbiEncode, HumanReadableParser, ParamType, Token}; + use zksync_basic_types::{Address, Nonce, H160, U256}; + use zksync_types::{ + api::{Block, CallTracerConfig, SupportedTracers, TransactionReceipt}, + transaction_request::CallRequestBuilder, + utils::deployed_address_create, + }; + + fn deploy_test_contracts(node: &InMemoryNode) -> (Address, Address) { + let private_key = H256::repeat_byte(0xee); + let from_account = zksync_types::PackedEthSignature::address_from_private_key(&private_key) + .expect("failed generating address"); + node.set_rich_account(from_account); + + // first, deploy secondary contract + let secondary_bytecode = bytecode_from_slice( + "Secondary", + include_bytes!("deps/test-contracts/Secondary.json"), + ); + let secondary_deployed_address = deployed_address_create(from_account, U256::zero()); + testing::deploy_contract( + &node, + H256::repeat_byte(0x1), + private_key, + secondary_bytecode, + Some((U256::from(2),).encode()), + Nonce(0), + ); + + // deploy primary contract using the secondary contract address as a constructor parameter + let primary_bytecode = bytecode_from_slice( + "Primary", + include_bytes!("deps/test-contracts/Primary.json"), + ); + let primary_deployed_address = deployed_address_create(from_account, U256::one()); + testing::deploy_contract( + &node, + H256::repeat_byte(0x1), + private_key, + primary_bytecode, + Some((secondary_deployed_address).encode()), + Nonce(1), + ); + (primary_deployed_address, secondary_deployed_address) + } + + #[tokio::test] + async fn test_trace_deployed_contract() { + let node = InMemoryNode::::default(); + let debug = DebugNamespaceImpl::new(node.get_inner()); + + let (primary_deployed_address, secondary_deployed_address) = deploy_test_contracts(&node); + + // trace a call to the primary contract + let func = HumanReadableParser::parse_function("calculate(uint)").unwrap(); + let calldata = func.encode_input(&[Token::Uint(U256::from(42))]).unwrap(); + let request = CallRequestBuilder::default() + .to(primary_deployed_address) + .data(calldata.clone().into()) + .gas(80_000_000.into()) + .build(); + let trace = debug + .trace_call(request.clone(), None, None) + .await + .expect("trace call"); + + // call should not revert + assert!(trace.error.is_none()); + assert!(trace.revert_reason.is_none()); + + // check that the call was successful + let output = + ethers::abi::decode(&[ParamType::Uint(256)], &trace.output.0.as_slice()).unwrap(); + assert_eq!(output[0], Token::Uint(U256::from(84))); + + // find the call to primary contract in the trace + let contract_call = trace + .calls + .first() + .unwrap() + .calls + .last() + .unwrap() + .calls + .first() + .unwrap(); + + assert_eq!(contract_call.to, primary_deployed_address); + assert_eq!(contract_call.input, calldata.into()); + + // check that it contains a call to secondary contract + let subcall = contract_call.calls.first().unwrap(); + assert_eq!(subcall.to, secondary_deployed_address); + assert_eq!(subcall.from, primary_deployed_address); + assert_eq!(subcall.output, U256::from(84).encode().into()); + } + + #[tokio::test] + async fn test_trace_only_top() { + let node = InMemoryNode::::default(); + let debug = DebugNamespaceImpl::new(node.get_inner()); + + let (primary_deployed_address, _) = deploy_test_contracts(&node); + + // trace a call to the primary contract + let func = HumanReadableParser::parse_function("calculate(uint)").unwrap(); + let calldata = func.encode_input(&[Token::Uint(U256::from(42))]).unwrap(); + let request = CallRequestBuilder::default() + .to(primary_deployed_address) + .data(calldata.into()) + .gas(80_000_000.into()) + .build(); + + // if we trace with onlyTopCall=true, we should get only the top-level call + let trace = debug + .trace_call( + request, + None, + Some(TracerConfig { + tracer: SupportedTracers::CallTracer, + tracer_config: CallTracerConfig { + only_top_call: true, + }, + }), + ) + .await + .expect("trace call"); + // call should not revert + assert!(trace.error.is_none()); + assert!(trace.revert_reason.is_none()); + + // call should not contain any subcalls + assert!(trace.calls.is_empty()); + } + + #[tokio::test] + async fn test_trace_reverts() { + let node = InMemoryNode::::default(); + let debug = DebugNamespaceImpl::new(node.get_inner()); + + let (primary_deployed_address, _) = deploy_test_contracts(&node); + + // trace a call to the primary contract + let request = CallRequestBuilder::default() + .to(primary_deployed_address) + .data(short_signature("shouldRevert()", &[]).into()) + .gas(80_000_000.into()) + .build(); + let trace = debug + .trace_call(request, None, None) + .await + .expect("trace call"); + + // call should revert + assert!(trace.revert_reason.is_some()); + + // find the call to primary contract in the trace + let contract_call = trace + .calls + .first() + .unwrap() + .calls + .last() + .unwrap() + .calls + .first() + .unwrap(); + + // the contract subcall should have reverted + assert!(contract_call.revert_reason.is_some()); + } + + #[tokio::test] + async fn test_trace_transaction() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + writer.tx_results.insert( + H256::repeat_byte(0x1), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![LogBuilder::new() + .set_address(H160::repeat_byte(0xa1)) + .build()], + ..Default::default() + }, + debug: testing::default_tx_debug_info(), + }, + ); + } + let result = DebugNamespaceImpl::new(inner) + .trace_transaction(H256::repeat_byte(0x1), None) + .await + .unwrap() + .unwrap(); + assert_eq!(result.calls.len(), 1); + } + + #[tokio::test] + async fn test_trace_transaction_only_top() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + writer.tx_results.insert( + H256::repeat_byte(0x1), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![LogBuilder::new() + .set_address(H160::repeat_byte(0xa1)) + .build()], + ..Default::default() + }, + debug: testing::default_tx_debug_info(), + }, + ); + } + let result = DebugNamespaceImpl::new(inner) + .trace_transaction( + H256::repeat_byte(0x1), + Some(TracerConfig { + tracer: SupportedTracers::CallTracer, + tracer_config: CallTracerConfig { + only_top_call: true, + }, + }), + ) + .await + .unwrap() + .unwrap(); + assert!(result.calls.is_empty()); + } + + #[tokio::test] + async fn test_trace_transaction_not_found() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + let result = DebugNamespaceImpl::new(inner) + .trace_transaction(H256::repeat_byte(0x1), None) + .await + .unwrap(); + assert!(result.is_none()); + } + + #[tokio::test] + async fn test_trace_block_by_hash_empty() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + let block = Block::::default(); + writer.blocks.insert(H256::repeat_byte(0x1), block); + } + let result = DebugNamespaceImpl::new(inner) + .trace_block_by_hash(H256::repeat_byte(0x1), None) + .await + .unwrap(); + assert_eq!(result.len(), 0); + } + + #[tokio::test] + async fn test_trace_block_by_hash() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + let tx = zksync_types::api::Transaction::default(); + let tx_hash = tx.hash; + let mut block = Block::::default(); + block.transactions.push(TransactionVariant::Full(tx)); + writer.blocks.insert(H256::repeat_byte(0x1), block); + writer.tx_results.insert( + tx_hash, + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt::default(), + debug: testing::default_tx_debug_info(), + }, + ); + } + let result = DebugNamespaceImpl::new(inner) + .trace_block_by_hash(H256::repeat_byte(0x1), None) + .await + .unwrap(); + assert_eq!(result.len(), 1); + assert_eq!(result[0].result.calls.len(), 1); + } + + #[tokio::test] + async fn test_trace_block_by_number() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + let tx = zksync_types::api::Transaction::default(); + let tx_hash = tx.hash; + let mut block = Block::::default(); + block.transactions.push(TransactionVariant::Full(tx)); + writer.blocks.insert(H256::repeat_byte(0x1), block); + writer.block_hashes.insert(0, H256::repeat_byte(0x1)); + writer.tx_results.insert( + tx_hash, + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt::default(), + debug: testing::default_tx_debug_info(), + }, + ); + } + // check `latest` alias + let result = DebugNamespaceImpl::new(node.get_inner()) + .trace_block_by_number(BlockNumber::Latest, None) + .await + .unwrap(); + assert_eq!(result.len(), 1); + assert_eq!(result[0].result.calls.len(), 1); + + // check block number + let result = DebugNamespaceImpl::new(node.get_inner()) + .trace_block_by_number(BlockNumber::Number(0.into()), None) + .await + .unwrap(); + assert_eq!(result.len(), 1); + assert_eq!(result[0].result.calls.len(), 1); + } +} diff --git a/.test-node-subtree/src/namespaces/eth_test.rs b/.test-node-subtree/src/namespaces/eth_test.rs new file mode 100644 index 00000000..bbdebe1a --- /dev/null +++ b/.test-node-subtree/src/namespaces/eth_test.rs @@ -0,0 +1,13 @@ +use jsonrpc_core::{BoxFuture, Result}; +use jsonrpc_derive::rpc; +use zksync_basic_types::H256; +use zksync_types::transaction_request::CallRequest; + +/// +/// ETH namespace extension for the test node. +/// +#[rpc] +pub trait EthTestNodeNamespaceT { + #[rpc(name = "eth_sendTransaction")] + fn send_transaction(&self, tx: CallRequest) -> BoxFuture>; +} diff --git a/.test-node-subtree/src/namespaces/evm.rs b/.test-node-subtree/src/namespaces/evm.rs new file mode 100644 index 00000000..79b95341 --- /dev/null +++ b/.test-node-subtree/src/namespaces/evm.rs @@ -0,0 +1,70 @@ +use jsonrpc_derive::rpc; +use zksync_basic_types::U64; + +use crate::namespaces::RpcResult; + +#[rpc] +pub trait EvmNamespaceT { + /// Increase the current timestamp for the node + /// + /// # Parameters + /// - `time_delta`: The number of seconds to increase time by + /// + /// # Returns + /// The applied time delta to `current_timestamp` value for the InMemoryNodeInner. + #[rpc(name = "evm_increaseTime")] + fn increase_time(&self, time_delta_seconds: u64) -> RpcResult; + + /// Force a single block to be mined. + /// + /// Will mine an empty block (containing zero transactions) + /// + /// # Returns + /// The string "0x0". + #[rpc(name = "evm_mine")] + fn evm_mine(&self) -> RpcResult; + + /// Set the current timestamp for the node. The timestamp must be in future. + /// + /// # Parameters + /// - `timestamp`: The timestamp to set the time to + /// + /// # Returns + /// The new timestamp value for the InMemoryNodeInner. + #[rpc(name = "evm_setNextBlockTimestamp")] + fn set_next_block_timestamp(&self, timestamp: u64) -> RpcResult; + + /// Set the current timestamp for the node. + /// Warning: This will allow you to move backwards in time, which may cause new blocks to appear to be + /// mined before old blocks. This will result in an invalid state. + /// + /// # Parameters + /// - `time`: The timestamp to set the time to + /// + /// # Returns + /// The difference between the `current_timestamp` and the new timestamp for the InMemoryNodeInner. + #[rpc(name = "evm_setTime")] + fn set_time(&self, time: u64) -> RpcResult; + + /// Snapshot the state of the blockchain at the current block. Takes no parameters. Returns the id of the snapshot + /// that was created. A snapshot can only be reverted once. After a successful evm_revert, the same snapshot id cannot + /// be used again. Consider creating a new snapshot after each evm_revert if you need to revert to the same + /// point multiple times. + /// + /// # Returns + /// The `U64` identifier for this snapshot. + #[rpc(name = "evm_snapshot")] + fn snapshot(&self) -> RpcResult; + + /// Revert the state of the blockchain to a previous snapshot. Takes a single parameter, + /// which is the snapshot id to revert to. This deletes the given snapshot, as well as any snapshots + /// taken after (e.g.: reverting to id 0x1 will delete snapshots with ids 0x1, 0x2, etc.) + /// + /// # Parameters + /// - `snapshot_id`: The snapshot id to revert. + /// + /// # Returns + /// `true` if a snapshot was reverted, otherwise `false`. + #[rpc(name = "evm_revert")] + fn revert_snapshot(&self, snapshot_id: U64) -> RpcResult; +} diff --git a/.test-node-subtree/src/namespaces/hardhat.rs b/.test-node-subtree/src/namespaces/hardhat.rs new file mode 100644 index 00000000..5a69f6b5 --- /dev/null +++ b/.test-node-subtree/src/namespaces/hardhat.rs @@ -0,0 +1,89 @@ +use jsonrpc_derive::rpc; +use zksync_basic_types::{Address, U256, U64}; + +use super::RpcResult; + +#[rpc] +pub trait HardhatNamespaceT { + /// Sets the balance of the given address to the given balance. + /// + /// # Arguments + /// + /// * `address` - The `Address` whose balance will be edited + /// * `balance` - The new balance to set for the given address, in wei + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a `bool` representing the success of the operation. + #[rpc(name = "hardhat_setBalance")] + fn set_balance(&self, address: Address, balance: U256) -> RpcResult; + + /// Modifies an account's nonce by overwriting it. + /// + /// # Arguments + /// + /// * `address` - The `Address` whose nonce is to be changed + /// * `nonce` - The new nonce + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a `bool` representing the success of the operation. + #[rpc(name = "hardhat_setNonce")] + fn set_nonce(&self, address: Address, balance: U256) -> RpcResult; + + /// Sometimes you may want to advance the latest block number of the network by a large number of blocks. + /// One way to do this would be to call the evm_mine RPC method multiple times, but this is too slow if you want to mine thousands of blocks. + /// The hardhat_mine method can mine any number of blocks at once, in constant time. (It exhibits the same performance no matter how many blocks are mined.) + /// + /// # Arguments + /// + /// * `num_blocks` - The number of blocks to mine, defaults to 1 + /// * `interval` - The interval between the timestamps of each block, in seconds, and it also defaults to 1 + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a `bool` representing the success of the operation. + #[rpc(name = "hardhat_mine")] + fn hardhat_mine(&self, num_blocks: Option, interval: Option) -> RpcResult; + + /// Hardhat Network allows you to send transactions impersonating specific account and contract addresses. + /// To impersonate an account use this method, passing the address to impersonate as its parameter. + /// After calling this method, any transactions with this sender will be executed without verification. + /// Multiple addresses can be impersonated at once. + /// + /// # Arguments + /// + /// * `address` - The address to impersonate + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a `bool` representing the success of the operation. + #[rpc(name = "hardhat_impersonateAccount")] + fn impersonate_account(&self, address: Address) -> RpcResult; + + /// Use this method to stop impersonating an account after having previously used `hardhat_impersonateAccount` + /// The method returns `true` if the account was being impersonated and `false` otherwise. + /// + /// # Arguments + /// + /// * `address` - The address to stop impersonating. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a `bool` representing the success of the operation. + #[rpc(name = "hardhat_stopImpersonatingAccount")] + fn stop_impersonating_account(&self, address: Address) -> RpcResult; + + /// Modifies the bytecode stored at an account's address. + /// + /// # Arguments + /// + /// * `address` - The address where the given code should be stored. + /// * `code` - The code to be stored. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a `bool` representing the success of the operation. + #[rpc(name = "hardhat_setCode")] + fn set_code(&self, address: Address, code: Vec) -> RpcResult<()>; +} diff --git a/.test-node-subtree/src/namespaces/mod.rs b/.test-node-subtree/src/namespaces/mod.rs new file mode 100644 index 00000000..8c359b3e --- /dev/null +++ b/.test-node-subtree/src/namespaces/mod.rs @@ -0,0 +1,21 @@ +mod config; +mod eth_test; +mod evm; +mod hardhat; +mod net; +mod web3; + +use zksync_core::api_server::web3::backend_jsonrpc::namespaces::{debug, eth, zks}; + +pub use config::ConfigurationApiNamespaceT; +pub use debug::DebugNamespaceT; +pub use eth::EthNamespaceT; +pub use eth_test::EthTestNodeNamespaceT; +pub use evm::EvmNamespaceT; +pub use hardhat::HardhatNamespaceT; +pub use net::NetNamespaceT; +pub use web3::Web3NamespaceT; +pub use zks::ZksNamespaceT; + +pub type Result = jsonrpc_core::Result; +pub type RpcResult = jsonrpc_core::BoxFuture>; diff --git a/.test-node-subtree/src/namespaces/net.rs b/.test-node-subtree/src/namespaces/net.rs new file mode 100644 index 00000000..f18aa142 --- /dev/null +++ b/.test-node-subtree/src/namespaces/net.rs @@ -0,0 +1,16 @@ +use jsonrpc_derive::rpc; +use zksync_basic_types::U256; + +use crate::namespaces::Result; + +#[rpc] +pub trait NetNamespaceT { + #[rpc(name = "net_version", returns = "String")] + fn net_version(&self) -> Result; + + #[rpc(name = "net_peerCount", returns = "U256")] + fn net_peer_count(&self) -> Result; + + #[rpc(name = "net_listening", returns = "bool")] + fn net_listening(&self) -> Result; +} diff --git a/.test-node-subtree/src/namespaces/web3.rs b/.test-node-subtree/src/namespaces/web3.rs new file mode 100644 index 00000000..9bfb233c --- /dev/null +++ b/.test-node-subtree/src/namespaces/web3.rs @@ -0,0 +1,9 @@ +use jsonrpc_derive::rpc; + +use crate::namespaces::Result; + +#[rpc] +pub trait Web3NamespaceT { + #[rpc(name = "web3_clientVersion", returns = "String")] + fn web3_client_version(&self) -> Result; +} diff --git a/.test-node-subtree/src/node/config.rs b/.test-node-subtree/src/node/config.rs new file mode 100644 index 00000000..81f350ef --- /dev/null +++ b/.test-node-subtree/src/node/config.rs @@ -0,0 +1,189 @@ +use zksync_core::api_server::web3::backend_jsonrpc::error::into_jsrpc_error; +use zksync_web3_decl::error::Web3Error; + +use crate::{ + fork::ForkSource, + namespaces::{ConfigurationApiNamespaceT, Result}, + node::InMemoryNode, + observability::LogLevel, +}; + +use super::{ShowCalls, ShowGasDetails, ShowStorageLogs, ShowVMDetails}; + +impl ConfigurationApiNamespaceT + for InMemoryNode +{ + fn config_get_show_calls(&self) -> Result { + self.get_inner() + .read() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .map(|reader| reader.show_calls.to_string()) + } + + fn config_get_current_timestamp(&self) -> Result { + self.get_inner() + .read() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .map(|reader| reader.current_timestamp) + } + + fn config_set_show_calls(&self, value: String) -> Result { + let show_calls = match value.parse::() { + Ok(value) => value, + Err(_) => return self.config_get_show_calls(), + }; + + self.get_inner() + .write() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .map(|mut writer| { + writer.show_calls = show_calls; + writer.show_calls.to_string() + }) + } + + fn config_set_show_storage_logs(&self, value: String) -> Result { + let show_storage_logs = match value.parse::() { + Ok(value) => value, + Err(_) => { + return self + .get_inner() + .read() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .map(|reader| reader.show_storage_logs.to_string()) + } + }; + + self.get_inner() + .write() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .map(|mut writer| { + writer.show_storage_logs = show_storage_logs; + writer.show_storage_logs.to_string() + }) + } + + fn config_set_show_vm_details(&self, value: String) -> Result { + let show_vm_details = match value.parse::() { + Ok(value) => value, + Err(_) => { + return self + .get_inner() + .read() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .map(|reader| reader.show_vm_details.to_string()) + } + }; + + self.get_inner() + .write() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .map(|mut writer| { + writer.show_vm_details = show_vm_details; + writer.show_vm_details.to_string() + }) + } + + fn config_set_show_gas_details(&self, value: String) -> Result { + let show_gas_details = match value.parse::() { + Ok(value) => value, + Err(_) => { + return self + .get_inner() + .read() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .map(|reader| reader.show_gas_details.to_string()) + } + }; + + self.get_inner() + .write() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .map(|mut writer| { + writer.show_gas_details = show_gas_details; + writer.show_gas_details.to_string() + }) + } + + fn config_set_resolve_hashes(&self, value: bool) -> Result { + self.get_inner() + .write() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .map(|mut writer| { + writer.resolve_hashes = value; + writer.resolve_hashes + }) + } + + fn config_set_log_level(&self, level: LogLevel) -> Result { + if let Some(observability) = &self + .get_inner() + .read() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + })? + .observability + { + match observability.set_log_level(level.clone()) { + Ok(_) => tracing::info!("set log level to '{}'", level), + Err(err) => { + tracing::error!("failed setting log level {:?}", err); + return Ok(false); + } + } + } + Ok(true) + } + + fn config_set_logging(&self, directive: String) -> Result { + if let Some(observability) = &self + .get_inner() + .read() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + })? + .observability + { + match observability.set_logging(&directive) { + Ok(_) => tracing::info!("set logging to '{}'", directive), + Err(err) => { + tracing::error!("failed setting logging to '{}': {:?}", directive, err); + return Ok(false); + } + } + } + Ok(true) + } +} diff --git a/.test-node-subtree/src/node/debug.rs b/.test-node-subtree/src/node/debug.rs new file mode 100644 index 00000000..7bf11179 --- /dev/null +++ b/.test-node-subtree/src/node/debug.rs @@ -0,0 +1,564 @@ +use itertools::Itertools; +use once_cell::sync::OnceCell; +use std::sync::Arc; + +use multivm::interface::VmInterface; +use multivm::tracers::CallTracer; +use multivm::vm_latest::HistoryDisabled; +use multivm::vm_latest::{constants::ETH_CALL_GAS_LIMIT, ToTracerPointer, Vm}; + +use zksync_basic_types::H256; +use zksync_core::api_server::web3::backend_jsonrpc::error::into_jsrpc_error; +use zksync_types::{ + api::{BlockId, BlockNumber, DebugCall, ResultDebugCall, TracerConfig, TransactionVariant}, + l2::L2Tx, + transaction_request::CallRequest, + PackedEthSignature, Transaction, U64, +}; +use zksync_web3_decl::error::Web3Error; + +use crate::deps::storage_view::StorageView; +use crate::{ + fork::ForkSource, + namespaces::{DebugNamespaceT, Result, RpcResult}, + node::{InMemoryNode, MAX_TX_SIZE}, + utils::{create_debug_output, to_real_block_number}, +}; + +impl DebugNamespaceT + for InMemoryNode +{ + fn trace_block_by_number( + &self, + block: BlockNumber, + options: Option, + ) -> RpcResult> { + let only_top = options.is_some_and(|o| o.tracer_config.only_top_call); + let inner = self.get_inner().clone(); + Box::pin(async move { + let inner = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let block = { + let number = + to_real_block_number(block, U64::from(inner.current_miniblock)).as_u64(); + + inner + .block_hashes + .get(&number) + .and_then(|hash| inner.blocks.get(hash)) + .ok_or_else(|| { + into_jsrpc_error(Web3Error::SubmitTransactionError( + "Block not found".to_string(), + vec![], + )) + })? + }; + + let tx_hashes = block + .transactions + .iter() + .map(|tx| match tx { + TransactionVariant::Full(tx) => tx.hash, + TransactionVariant::Hash(hash) => *hash, + }) + .collect_vec(); + + let debug_calls = tx_hashes + .into_iter() + .map(|tx_hash| { + let tx = inner.tx_results.get(&tx_hash).ok_or_else(|| { + into_jsrpc_error(Web3Error::SubmitTransactionError( + "Transaction not found".to_string(), + vec![], + )) + })?; + Ok(tx.debug_info(only_top)) + }) + .collect::>>()? + .into_iter() + .map(|result| ResultDebugCall { result }) + .collect_vec(); + + Ok(debug_calls) + }) + } + + fn trace_block_by_hash( + &self, + hash: H256, + options: Option, + ) -> RpcResult> { + let only_top = options.is_some_and(|o| o.tracer_config.only_top_call); + let inner = self.get_inner().clone(); + Box::pin(async move { + let inner = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let block = inner.blocks.get(&hash).ok_or_else(|| { + into_jsrpc_error(Web3Error::SubmitTransactionError( + "Block not found".to_string(), + vec![], + )) + })?; + + let tx_hashes = block + .transactions + .iter() + .map(|tx| match tx { + TransactionVariant::Full(tx) => tx.hash, + TransactionVariant::Hash(hash) => *hash, + }) + .collect_vec(); + + let debug_calls = tx_hashes + .into_iter() + .map(|tx_hash| { + let tx = inner.tx_results.get(&tx_hash).ok_or_else(|| { + into_jsrpc_error(Web3Error::SubmitTransactionError( + "Transaction not found".to_string(), + vec![], + )) + })?; + Ok(tx.debug_info(only_top)) + }) + .collect::>>()? + .into_iter() + .map(|result| ResultDebugCall { result }) + .collect_vec(); + + Ok(debug_calls) + }) + } + + /// Trace execution of a transaction. + fn trace_call( + &self, + request: CallRequest, + block: Option, + options: Option, + ) -> RpcResult { + let only_top = options.is_some_and(|o| o.tracer_config.only_top_call); + let inner = self.get_inner().clone(); + Box::pin(async move { + if block.is_some() && !matches!(block, Some(BlockId::Number(BlockNumber::Latest))) { + return Err(jsonrpc_core::Error::invalid_params( + "tracing only supported at `latest` block", + )); + } + + let inner = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let mut l2_tx = match L2Tx::from_request(request.into(), MAX_TX_SIZE) { + Ok(tx) => tx, + Err(e) => { + let error = Web3Error::SerializationError(e); + return Err(into_jsrpc_error(error)); + } + }; + + let execution_mode = multivm::interface::TxExecutionMode::EthCall; + let storage = StorageView::new(&inner.fork_storage).into_rc_ptr(); + + let bootloader_code = inner.system_contracts.contracts_for_l2_call(); + + // init vm + let (mut l1_batch_env, _block_context) = inner.create_l1_batch_env(storage.clone()); + + // update the enforced_base_fee within l1_batch_env to match the logic in zksync_core + l1_batch_env.enforced_base_fee = Some(l2_tx.common_data.fee.max_fee_per_gas.as_u64()); + let system_env = inner.create_system_env(bootloader_code.clone(), execution_mode); + let mut vm: Vm<_, HistoryDisabled> = Vm::new(l1_batch_env, system_env, storage); + + // We must inject *some* signature (otherwise bootloader code fails to generate hash). + if l2_tx.common_data.signature.is_empty() { + l2_tx.common_data.signature = + PackedEthSignature::default().serialize_packed().into(); + } + + // Match behavior of zksync_core: + // Protection against infinite-loop eth_calls and alike: + // limiting the amount of gas the call can use. + l2_tx.common_data.fee.gas_limit = ETH_CALL_GAS_LIMIT.into(); + + let tx: Transaction = l2_tx.clone().into(); + vm.push_transaction(tx); + + let call_tracer_result = Arc::new(OnceCell::default()); + let tracer = CallTracer::new(call_tracer_result.clone()).into_tracer_pointer(); + let tx_result = vm.inspect(tracer.into(), multivm::interface::VmExecutionMode::OneTx); + + let call_traces = if only_top { + vec![] + } else { + Arc::try_unwrap(call_tracer_result) + .unwrap() + .take() + .unwrap_or_default() + }; + + let debug = + create_debug_output(&l2_tx, &tx_result, call_traces).map_err(into_jsrpc_error)?; + + Ok(debug) + }) + } + + fn trace_transaction( + &self, + tx_hash: H256, + options: Option, + ) -> RpcResult> { + let only_top = options.is_some_and(|o| o.tracer_config.only_top_call); + let inner = self.get_inner().clone(); + Box::pin(async move { + let inner = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + Ok(inner + .tx_results + .get(&tx_hash) + .map(|tx| tx.debug_info(only_top))) + }) + } +} + +#[cfg(test)] +mod tests { + use super::*; + use crate::{ + deps::system_contracts::bytecode_from_slice, + http_fork_source::HttpForkSource, + node::{InMemoryNode, TransactionResult}, + testing::{self, LogBuilder}, + }; + use ethers::abi::{short_signature, AbiEncode, HumanReadableParser, ParamType, Token}; + use zksync_basic_types::{Address, Nonce, H160, U256}; + use zksync_types::{ + api::{Block, CallTracerConfig, SupportedTracers, TransactionReceipt}, + transaction_request::CallRequestBuilder, + utils::deployed_address_create, + }; + + fn deploy_test_contracts(node: &InMemoryNode) -> (Address, Address) { + let private_key = H256::repeat_byte(0xee); + let from_account = zksync_types::PackedEthSignature::address_from_private_key(&private_key) + .expect("failed generating address"); + node.set_rich_account(from_account); + + // first, deploy secondary contract + let secondary_bytecode = bytecode_from_slice( + "Secondary", + include_bytes!("../deps/test-contracts/Secondary.json"), + ); + let secondary_deployed_address = deployed_address_create(from_account, U256::zero()); + testing::deploy_contract( + node, + H256::repeat_byte(0x1), + private_key, + secondary_bytecode, + Some((U256::from(2),).encode()), + Nonce(0), + ); + + // deploy primary contract using the secondary contract address as a constructor parameter + let primary_bytecode = bytecode_from_slice( + "Primary", + include_bytes!("../deps/test-contracts/Primary.json"), + ); + let primary_deployed_address = deployed_address_create(from_account, U256::one()); + testing::deploy_contract( + node, + H256::repeat_byte(0x1), + private_key, + primary_bytecode, + Some((secondary_deployed_address).encode()), + Nonce(1), + ); + (primary_deployed_address, secondary_deployed_address) + } + + #[tokio::test] + async fn test_trace_deployed_contract() { + let node = InMemoryNode::::default(); + + let (primary_deployed_address, secondary_deployed_address) = deploy_test_contracts(&node); + + // trace a call to the primary contract + let func = HumanReadableParser::parse_function("calculate(uint)").unwrap(); + let calldata = func.encode_input(&[Token::Uint(U256::from(42))]).unwrap(); + let request = CallRequestBuilder::default() + .to(primary_deployed_address) + .data(calldata.clone().into()) + .gas(80_000_000.into()) + .build(); + let trace = node + .trace_call(request.clone(), None, None) + .await + .expect("trace call"); + + // call should not revert + assert!(trace.error.is_none()); + assert!(trace.revert_reason.is_none()); + + // check that the call was successful + let output = + ethers::abi::decode(&[ParamType::Uint(256)], trace.output.0.as_slice()).unwrap(); + assert_eq!(output[0], Token::Uint(U256::from(84))); + + // find the call to primary contract in the trace + let contract_call = trace + .calls + .first() + .unwrap() + .calls + .last() + .unwrap() + .calls + .first() + .unwrap(); + + assert_eq!(contract_call.to, primary_deployed_address); + assert_eq!(contract_call.input, calldata.into()); + + // check that it contains a call to secondary contract + let subcall = contract_call.calls.first().unwrap(); + assert_eq!(subcall.to, secondary_deployed_address); + assert_eq!(subcall.from, primary_deployed_address); + assert_eq!(subcall.output, U256::from(84).encode().into()); + } + + #[tokio::test] + async fn test_trace_only_top() { + let node = InMemoryNode::::default(); + + let (primary_deployed_address, _) = deploy_test_contracts(&node); + + // trace a call to the primary contract + let func = HumanReadableParser::parse_function("calculate(uint)").unwrap(); + let calldata = func.encode_input(&[Token::Uint(U256::from(42))]).unwrap(); + let request = CallRequestBuilder::default() + .to(primary_deployed_address) + .data(calldata.into()) + .gas(80_000_000.into()) + .build(); + + // if we trace with onlyTopCall=true, we should get only the top-level call + let trace = node + .trace_call( + request, + None, + Some(TracerConfig { + tracer: SupportedTracers::CallTracer, + tracer_config: CallTracerConfig { + only_top_call: true, + }, + }), + ) + .await + .expect("trace call"); + // call should not revert + assert!(trace.error.is_none()); + assert!(trace.revert_reason.is_none()); + + // call should not contain any subcalls + assert!(trace.calls.is_empty()); + } + + #[tokio::test] + async fn test_trace_reverts() { + let node = InMemoryNode::::default(); + + let (primary_deployed_address, _) = deploy_test_contracts(&node); + + // trace a call to the primary contract + let request = CallRequestBuilder::default() + .to(primary_deployed_address) + .data(short_signature("shouldRevert()", &[]).into()) + .gas(80_000_000.into()) + .build(); + let trace = node + .trace_call(request, None, None) + .await + .expect("trace call"); + + // call should revert + assert!(trace.revert_reason.is_some()); + + // find the call to primary contract in the trace + let contract_call = trace + .calls + .first() + .unwrap() + .calls + .last() + .unwrap() + .calls + .first() + .unwrap(); + + // the contract subcall should have reverted + assert!(contract_call.revert_reason.is_some()); + } + + #[tokio::test] + async fn test_trace_transaction() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + writer.tx_results.insert( + H256::repeat_byte(0x1), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![LogBuilder::new() + .set_address(H160::repeat_byte(0xa1)) + .build()], + ..Default::default() + }, + debug: testing::default_tx_debug_info(), + }, + ); + } + let result = node + .trace_transaction(H256::repeat_byte(0x1), None) + .await + .unwrap() + .unwrap(); + assert_eq!(result.calls.len(), 1); + } + + #[tokio::test] + async fn test_trace_transaction_only_top() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + writer.tx_results.insert( + H256::repeat_byte(0x1), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![LogBuilder::new() + .set_address(H160::repeat_byte(0xa1)) + .build()], + ..Default::default() + }, + debug: testing::default_tx_debug_info(), + }, + ); + } + let result = node + .trace_transaction( + H256::repeat_byte(0x1), + Some(TracerConfig { + tracer: SupportedTracers::CallTracer, + tracer_config: CallTracerConfig { + only_top_call: true, + }, + }), + ) + .await + .unwrap() + .unwrap(); + assert!(result.calls.is_empty()); + } + + #[tokio::test] + async fn test_trace_transaction_not_found() { + let node = InMemoryNode::::default(); + let result = node + .trace_transaction(H256::repeat_byte(0x1), None) + .await + .unwrap(); + assert!(result.is_none()); + } + + #[tokio::test] + async fn test_trace_block_by_hash_empty() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + let block = Block::::default(); + writer.blocks.insert(H256::repeat_byte(0x1), block); + } + let result = node + .trace_block_by_hash(H256::repeat_byte(0x1), None) + .await + .unwrap(); + assert_eq!(result.len(), 0); + } + + #[tokio::test] + async fn test_trace_block_by_hash() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + let tx = zksync_types::api::Transaction::default(); + let tx_hash = tx.hash; + let mut block = Block::::default(); + block.transactions.push(TransactionVariant::Full(tx)); + writer.blocks.insert(H256::repeat_byte(0x1), block); + writer.tx_results.insert( + tx_hash, + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt::default(), + debug: testing::default_tx_debug_info(), + }, + ); + } + let result = node + .trace_block_by_hash(H256::repeat_byte(0x1), None) + .await + .unwrap(); + assert_eq!(result.len(), 1); + assert_eq!(result[0].result.calls.len(), 1); + } + + #[tokio::test] + async fn test_trace_block_by_number() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + let tx = zksync_types::api::Transaction::default(); + let tx_hash = tx.hash; + let mut block = Block::::default(); + block.transactions.push(TransactionVariant::Full(tx)); + writer.blocks.insert(H256::repeat_byte(0x1), block); + writer.block_hashes.insert(0, H256::repeat_byte(0x1)); + writer.tx_results.insert( + tx_hash, + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt::default(), + debug: testing::default_tx_debug_info(), + }, + ); + } + // check `latest` alias + let result = node + .trace_block_by_number(BlockNumber::Latest, None) + .await + .unwrap(); + assert_eq!(result.len(), 1); + assert_eq!(result[0].result.calls.len(), 1); + + // check block number + let result = node + .trace_block_by_number(BlockNumber::Number(0.into()), None) + .await + .unwrap(); + assert_eq!(result.len(), 1); + assert_eq!(result[0].result.calls.len(), 1); + } +} diff --git a/.test-node-subtree/src/node/eth.rs b/.test-node-subtree/src/node/eth.rs new file mode 100644 index 00000000..d51ffb4c --- /dev/null +++ b/.test-node-subtree/src/node/eth.rs @@ -0,0 +1,3194 @@ +use std::collections::HashSet; + +use colored::Colorize; +use futures::FutureExt; +use itertools::Itertools; +use multivm::interface::{ExecutionResult, TxExecutionMode}; +use multivm::vm_latest::constants::ETH_CALL_GAS_LIMIT; +use zksync_basic_types::{web3, AccountTreeId, Address, Bytes, H160, H256, U256, U64}; +use zksync_core::api_server::web3::backend_jsonrpc::error::into_jsrpc_error; +use zksync_state::ReadStorage; +use zksync_types::{ + api::{Block, BlockIdVariant, BlockNumber, TransactionVariant}, + fee::Fee, + get_code_key, get_nonce_key, + l2::L2Tx, + transaction_request::TransactionRequest, + utils::storage_key_for_standard_token_balance, + PackedEthSignature, StorageKey, L2_ETH_TOKEN_ADDRESS, +}; +use zksync_utils::{h256_to_u256, u256_to_h256}; +use zksync_web3_decl::{ + error::Web3Error, + types::{FeeHistory, Filter, FilterChanges, SyncState}, +}; + +use crate::{ + filters::{FilterType, LogFilter}, + fork::ForkSource, + namespaces::{EthNamespaceT, EthTestNodeNamespaceT, RpcResult}, + node::{InMemoryNode, TransactionResult, L2_GAS_PRICE, MAX_TX_SIZE, PROTOCOL_VERSION}, + utils::{self, h256_to_u64, not_implemented, IntoBoxedFuture}, +}; + +impl EthNamespaceT + for InMemoryNode +{ + /// Returns the chain ID of the node. + fn chain_id(&self) -> RpcResult { + match self.get_inner().read() { + Ok(inner) => Ok(U64::from(inner.fork_storage.chain_id.as_u64())).into_boxed_future(), + Err(_) => Err(into_jsrpc_error(Web3Error::InternalError)).into_boxed_future(), + } + } + + /// Calls the specified function on the L2 contract with the given arguments. + /// + /// # Arguments + /// + /// * `req` - The call request containing the function name and arguments. + /// * `_block` - The block ID variant (unused). + /// + /// # Returns + /// + /// A boxed future containing the result of the function call. + fn call( + &self, + req: zksync_types::transaction_request::CallRequest, + _block: Option, + ) -> RpcResult { + match L2Tx::from_request(req.into(), MAX_TX_SIZE) { + Ok(mut tx) => { + tx.common_data.fee.gas_limit = ETH_CALL_GAS_LIMIT.into(); + let result = self.run_l2_call(tx); + + match result { + Ok(execution_result) => match execution_result.result { + ExecutionResult::Success { output } => { + let gas_used = execution_result.statistics.gas_used; + tracing::debug!("GAS USED: {gas_used}"); + let mut result = vec![]; + result.extend_from_slice(&gas_used.to_le_bytes()); + result.extend_from_slice(&output); + Ok(result.into()).into_boxed_future() + } + ExecutionResult::Revert { output } => { + let message = output.to_user_friendly_string(); + let pretty_message = format!( + "execution reverted{}{}", + if message.is_empty() { "" } else { ": " }, + message + ); + + tracing::info!("{}", pretty_message.on_red()); + Err(into_jsrpc_error(Web3Error::SubmitTransactionError( + pretty_message, + output.encoded_data(), + ))) + .into_boxed_future() + } + ExecutionResult::Halt { reason } => { + let message = reason.to_string(); + let pretty_message = format!( + "execution halted {}{}", + if message.is_empty() { "" } else { ": " }, + message + ); + + tracing::info!("{}", pretty_message.on_red()); + Err(into_jsrpc_error(Web3Error::SubmitTransactionError( + pretty_message, + vec![], + ))) + .into_boxed_future() + } + }, + Err(e) => { + let error = Web3Error::InvalidTransactionData( + zksync_types::ethabi::Error::InvalidName(e), + ); + Err(into_jsrpc_error(error)).into_boxed_future() + } + } + } + Err(e) => { + let error = Web3Error::SerializationError(e); + Err(into_jsrpc_error(error)).into_boxed_future() + } + } + } + + /// Returns the balance of the specified address. + /// + /// # Arguments + /// + /// * `address` - The address to get the balance of. + /// * `_block` - The block ID variant (optional). + /// + /// # Returns + /// + /// A `BoxFuture` that resolves to a `Result` containing the balance of the specified address as a `U256` or a `jsonrpc_core::Error` if an error occurred. + fn get_balance(&self, address: Address, _block: Option) -> RpcResult { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let balance_key = storage_key_for_standard_token_balance( + AccountTreeId::new(L2_ETH_TOKEN_ADDRESS), + &address, + ); + + match inner.write() { + Ok(mut inner_guard) => { + let balance = inner_guard.fork_storage.read_value(&balance_key); + Ok(h256_to_u256(balance)) + } + Err(_) => { + let web3_error = Web3Error::InternalError; + Err(into_jsrpc_error(web3_error)) + } + } + }) + } + + /// Returns a block by its number. + /// + /// # Arguments + /// + /// * `block_number` - A `BlockNumber` enum variant representing the block number to retrieve. + /// * `full_transactions` - A boolean value indicating whether to retrieve full transactions or not. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to an `Option` of `Block`. + fn get_block_by_number( + &self, + block_number: BlockNumber, + full_transactions: bool, + ) -> RpcResult>> { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let maybe_block = { + let reader = match inner.read() { + Ok(r) => r, + Err(_) => return Err(into_jsrpc_error(Web3Error::InternalError)), + }; + let number = + utils::to_real_block_number(block_number, U64::from(reader.current_miniblock)) + .as_u64(); + + reader + .block_hashes + .get(&number) + .and_then(|hash| reader.blocks.get(hash)) + .cloned() + .or_else(|| { + reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_block_by_number(block_number, true) + .ok() + .flatten() + }) + }) + }; + + match maybe_block { + Some(mut block) => { + let block_hash = block.hash; + block.transactions = block + .transactions + .into_iter() + .map(|transaction| match &transaction { + TransactionVariant::Full(inner) => { + if full_transactions { + transaction + } else { + TransactionVariant::Hash(inner.hash) + } + } + TransactionVariant::Hash(_) => { + if full_transactions { + panic!( + "unexpected non full transaction for block {}", + block_hash + ) + } else { + transaction + } + } + }) + .collect(); + + Ok(Some(block)) + } + None => Ok(None), + } + }) + } + + /// Returns the code stored at the specified address. + /// + /// # Arguments + /// + /// * `address` - The address to retrieve the code from. + /// * `_block` - An optional block ID variant. + /// + /// # Returns + /// + /// A `BoxFuture` containing the result of the operation, which is a `jsonrpc_core::Result` containing + /// the code as a `zksync_basic_types::Bytes` object. + fn get_code( + &self, + address: zksync_basic_types::Address, + _block: Option, + ) -> RpcResult { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let code_key = get_code_key(&address); + + match inner.write() { + Ok(mut guard) => { + let code_hash = guard.fork_storage.read_value(&code_key); + + let code = guard + .fork_storage + .load_factory_dep(code_hash) + .unwrap_or_default(); + + Ok(Bytes::from(code)) + } + Err(_) => Err(into_jsrpc_error(Web3Error::InternalError)), + } + }) + } + + /// Returns the transaction count for a given address. + /// + /// # Arguments + /// + /// * `address` - The address to get the transaction count for. + /// * `_block` - Optional block ID variant. + /// + /// # Returns + /// + /// Returns a `BoxFuture` containing the transaction count as a `U256` wrapped in a `jsonrpc_core::Result`. + fn get_transaction_count( + &self, + address: zksync_basic_types::Address, + _block: Option, + ) -> RpcResult { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let nonce_key = get_nonce_key(&address); + + match inner.write() { + Ok(mut guard) => { + let result = guard.fork_storage.read_value(&nonce_key); + Ok(h256_to_u64(result).into()) + } + Err(_) => Err(into_jsrpc_error(Web3Error::InternalError)), + } + }) + } + + /// Retrieves the transaction receipt for a given transaction hash. + /// + /// # Arguments + /// + /// * `hash` - The hash of the transaction to retrieve the receipt for. + /// + /// # Returns + /// + /// A `BoxFuture` that resolves to an `Option` of a `TransactionReceipt` or an error. + fn get_transaction_receipt( + &self, + hash: zksync_basic_types::H256, + ) -> RpcResult> { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let reader = match inner.read() { + Ok(r) => r, + Err(_) => return Err(into_jsrpc_error(Web3Error::InternalError)), + }; + + let receipt = reader + .tx_results + .get(&hash) + .map(|info| info.receipt.clone()); + Ok(receipt) + }) + } + + /// Sends a raw transaction to the L2 network. + /// + /// # Arguments + /// + /// * `tx_bytes` - The transaction bytes to send. + /// + /// # Returns + /// + /// A future that resolves to the hash of the transaction if successful, or an error if the transaction is invalid or execution fails. + fn send_raw_transaction( + &self, + tx_bytes: zksync_basic_types::Bytes, + ) -> RpcResult { + let chain_id = match self.get_inner().read() { + Ok(reader) => reader.fork_storage.chain_id, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + + let (tx_req, hash) = match TransactionRequest::from_bytes(&tx_bytes.0, chain_id) { + Ok(result) => result, + Err(e) => { + return futures::future::err(into_jsrpc_error(Web3Error::SerializationError(e))) + .boxed() + } + }; + + let mut l2_tx: L2Tx = match L2Tx::from_request(tx_req, MAX_TX_SIZE) { + Ok(tx) => tx, + Err(e) => { + return futures::future::err(into_jsrpc_error(Web3Error::SerializationError(e))) + .boxed() + } + }; + + l2_tx.set_input(tx_bytes.0, hash); + if hash != l2_tx.hash() { + return futures::future::err(into_jsrpc_error(Web3Error::InvalidTransactionData( + zksync_types::ethabi::Error::InvalidData, + ))) + .boxed(); + }; + + match self.run_l2_tx(l2_tx.clone(), TxExecutionMode::VerifyExecute) { + Ok(_) => Ok(hash).into_boxed_future(), + Err(e) => { + let error_message = format!("Execution error: {}", e); + futures::future::err(into_jsrpc_error(Web3Error::SubmitTransactionError( + error_message, + l2_tx.hash().as_bytes().to_vec(), + ))) + .boxed() + } + } + } + + /// Returns a block by its hash. Currently, only hashes for blocks in memory are supported. + /// + /// # Arguments + /// + /// * `hash` - A `H256` type representing the hash of the block to retrieve. + /// * `full_transactions` - A boolean value indicating whether to retrieve full transactions or not. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to an `Option` of `Block`. + fn get_block_by_hash( + &self, + hash: zksync_basic_types::H256, + full_transactions: bool, + ) -> RpcResult>> { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let maybe_block = { + let reader = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + // try retrieving block from memory, and if unavailable subsequently from the fork + reader.blocks.get(&hash).cloned().or_else(|| { + reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_block_by_hash(hash, true) + .ok() + .flatten() + }) + }) + }; + + match maybe_block { + Some(mut block) => { + let block_hash = block.hash; + block.transactions = block + .transactions + .into_iter() + .map(|transaction| match &transaction { + TransactionVariant::Full(inner) => { + if full_transactions { + transaction + } else { + TransactionVariant::Hash(inner.hash) + } + } + TransactionVariant::Hash(_) => { + if full_transactions { + panic!( + "unexpected non full transaction for block {}", + block_hash + ) + } else { + transaction + } + } + }) + .collect(); + + Ok(Some(block)) + } + None => Ok(None), + } + }) + } + + /// Returns a future that resolves to an optional transaction with the given hash. + /// + /// # Arguments + /// + /// * `hash` - A 32-byte hash of the transaction. + /// + /// # Returns + /// + /// A `jsonrpc_core::BoxFuture` that resolves to a `jsonrpc_core::Result` containing an optional `zksync_types::api::Transaction`. + fn get_transaction_by_hash( + &self, + hash: zksync_basic_types::H256, + ) -> RpcResult> { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let reader = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let maybe_result = { + // try retrieving transaction from memory, and if unavailable subsequently from the fork + reader.tx_results.get(&hash).and_then(|TransactionResult { info, .. }| { + let input_data = info.tx.common_data.input.clone().or(None)?; + let chain_id = info.tx.common_data.extract_chain_id().or(None)?; + Some(zksync_types::api::Transaction { + hash, + nonce: U256::from(info.tx.common_data.nonce.0), + block_hash: Some(hash), + block_number: Some(U64::from(info.miniblock_number)), + transaction_index: Some(U64::from(1)), + from: Some(info.tx.initiator_account()), + to: Some(info.tx.recipient_account()), + value: info.tx.execute.value, + gas_price: Some(U256::from(0)), + gas: Default::default(), + input: input_data.data.into(), + v: Some(chain_id.into()), + r: Some(U256::zero()), + s: Some(U256::zero()), + raw: None, + transaction_type: { + let tx_type = match info.tx.common_data.transaction_type { + zksync_types::l2::TransactionType::LegacyTransaction => 0, + zksync_types::l2::TransactionType::EIP2930Transaction => 1, + zksync_types::l2::TransactionType::EIP1559Transaction => 2, + zksync_types::l2::TransactionType::EIP712Transaction => 113, + zksync_types::l2::TransactionType::PriorityOpTransaction => 255, + zksync_types::l2::TransactionType::ProtocolUpgradeTransaction => 254, + }; + Some(tx_type.into()) + }, + access_list: None, + max_fee_per_gas: Some(info.tx.common_data.fee.max_fee_per_gas), + max_priority_fee_per_gas: Some( + info.tx.common_data.fee.max_priority_fee_per_gas, + ), + chain_id: U256::from(chain_id), + l1_batch_number: Some(U64::from(info.batch_number as u64)), + l1_batch_tx_index: None, + }) + }).or_else(|| { + reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_transaction_by_hash(hash) + .ok() + .flatten() + }) + }) + }; + + Ok(maybe_result) + }) + } + + /// Returns the current block number as a `U64` wrapped in a `BoxFuture`. + fn get_block_number(&self) -> RpcResult { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let reader = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + Ok(U64::from(reader.current_miniblock)) + }) + } + + /// Estimates the gas required for a given call request. + /// + /// # Arguments + /// + /// * `req` - A `CallRequest` struct representing the call request to estimate gas for. + /// * `_block` - An optional `BlockNumber` struct representing the block number to estimate gas for. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a `U256` representing the estimated gas required. + fn estimate_gas( + &self, + req: zksync_types::transaction_request::CallRequest, + _block: Option, + ) -> RpcResult { + let inner = self.get_inner().clone(); + let reader = match inner.read() { + Ok(r) => r, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + + let result: jsonrpc_core::Result = reader.estimate_gas_impl(req); + match result { + Ok(fee) => Ok(fee.gas_limit).into_boxed_future(), + Err(err) => return futures::future::err(err).boxed(), + } + } + + /// Returns the current gas price in U256 format. + fn gas_price(&self) -> RpcResult { + let fair_l2_gas_price: u64 = L2_GAS_PRICE; + Ok(U256::from(fair_l2_gas_price)).into_boxed_future() + } + + /// Creates a filter object, based on filter options, to notify when the state changes (logs). + /// To check if the state has changed, call `eth_getFilterChanges`. + /// + /// # Arguments + /// + /// * `filter`: The filter options - + /// fromBlock: - Integer block number, or the string "latest", "earliest" or "pending". + /// toBlock: - Integer block number, or the string "latest", "earliest" or "pending". + /// address: - Contract address or a list of addresses from which the logs should originate. + /// topics: - [H256] topics. Topics are order-dependent. Each topic can also be an array with "or" options. + /// + /// If the from `fromBlock` or `toBlock` option are equal to "latest" the filter continually appends logs for newly mined blocks. + /// Topics are order-dependent. A transaction with a log with topics [A, B] will be matched by the following topic filters: + /// * \[\] "anything" + /// * \[A\] "A in first position (and anything after)" + /// * \[null, B\] "anything in first position AND B in second position (and anything after)" + /// * \[A, B\] "A in first position AND B in second position (and anything after)" + /// * \[\[A, B\], \[A, B\]\] "(A OR B) in first position AND (A OR B) in second position (and anything after)" + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to an `U256` filter id. + fn new_filter(&self, filter: Filter) -> RpcResult { + let inner = self.get_inner().clone(); + let mut writer = match inner.write() { + Ok(r) => r, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + + let from_block = filter.from_block.unwrap_or(BlockNumber::Latest); + let to_block = filter.to_block.unwrap_or(BlockNumber::Latest); + let addresses = filter.address.unwrap_or_default().0; + let mut topics: [Option>; 4] = Default::default(); + + if let Some(filter_topics) = filter.topics { + filter_topics + .into_iter() + .take(4) + .enumerate() + .for_each(|(i, maybe_topic_set)| { + if let Some(topic_set) = maybe_topic_set { + topics[i] = Some(topic_set.0.into_iter().collect()); + } + }) + } + + writer + .filters + .add_log_filter(from_block, to_block, addresses, topics) + .map_err(|_| into_jsrpc_error(Web3Error::InternalError)) + .into_boxed_future() + } + + /// Creates a filter in the node, to notify when a new block arrives. + /// To check if the state has changed, call `eth_getFilterChanges`. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to an `U256` filter id. + fn new_block_filter(&self) -> RpcResult { + let inner = self.get_inner().clone(); + let mut writer = match inner.write() { + Ok(r) => r, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + + writer + .filters + .add_block_filter() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError)) + .into_boxed_future() + } + + /// Creates a filter in the node, to notify when new pending transactions arrive. + /// To check if the state has changed, call `eth_getFilterChanges`. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to an `U256` filter id. + fn new_pending_transaction_filter(&self) -> RpcResult { + let inner = self.get_inner().clone(); + let mut writer = match inner.write() { + Ok(r) => r, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + + writer + .filters + .add_pending_transaction_filter() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError)) + .into_boxed_future() + } + + /// Uninstalls a filter with given id. Should always be called when watch is no longer needed. + /// + /// # Arguments + /// + /// * `id`: The filter id + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to an `U256` filter id. + fn uninstall_filter(&self, id: U256) -> RpcResult { + let inner = self.get_inner().clone(); + let mut writer = match inner.write() { + Ok(r) => r, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + + let result = writer.filters.remove_filter(id); + Ok(result).into_boxed_future() + } + + /// Returns an array of all logs matching a given filter. + /// + /// # Arguments + /// + /// * `filter`: The filter options - + /// fromBlock - Integer block number, or the string "latest", "earliest" or "pending". + /// toBlock - Integer block number, or the string "latest", "earliest" or "pending". + /// address - Contract address or a list of addresses from which the logs should originate. + /// topics - [H256] topics. Topics are order-dependent. Each topic can also be an array with "or" options. + /// See `new_filter` documention for how to specify topics. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to an array of logs. + fn get_logs(&self, filter: Filter) -> RpcResult> { + let inner = self.get_inner(); + let reader = match inner.read() { + Ok(r) => r, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + let from_block = filter.from_block.unwrap_or(BlockNumber::Earliest); + let to_block = filter.to_block.unwrap_or(BlockNumber::Latest); + let addresses = filter.address.unwrap_or_default().0; + let mut topics: [Option>; 4] = Default::default(); + + if let Some(filter_topics) = filter.topics { + filter_topics + .into_iter() + .take(4) + .enumerate() + .for_each(|(i, maybe_topic_set)| { + if let Some(topic_set) = maybe_topic_set { + topics[i] = Some(topic_set.0.into_iter().collect()); + } + }) + } + + let log_filter = LogFilter::new(from_block, to_block, addresses, topics); + + let latest_block_number = U64::from(reader.current_miniblock); + let logs = reader + .tx_results + .values() + .flat_map(|tx_result| { + tx_result + .receipt + .logs + .iter() + .filter(|log| log_filter.matches(log, latest_block_number)) + .cloned() + }) + .collect_vec(); + + Ok(logs).into_boxed_future() + } + + /// Returns an array of all logs matching filter with given id. + /// + /// # Arguments + /// + /// * `id`: The filter id + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to an array of logs. + fn get_filter_logs(&self, id: U256) -> RpcResult { + let inner = self.get_inner(); + let reader = match inner.read() { + Ok(r) => r, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + + let latest_block_number = U64::from(reader.current_miniblock); + let logs = match reader.filters.get_filter(id) { + Some(FilterType::Log(f)) => reader + .tx_results + .values() + .flat_map(|tx_result| { + tx_result + .receipt + .logs + .iter() + .filter(|log| f.matches(log, latest_block_number)) + .cloned() + }) + .collect_vec(), + _ => return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed(), + }; + + Ok(FilterChanges::Logs(logs)).into_boxed_future() + } + + /// Polling method for a filter, which returns an array of logs, block hashes, or transaction hashes, + /// depending on the filter type, which occurred since last poll. + /// + /// # Arguments + /// + /// * `id`: The filter id + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to an array of logs, block hashes, or transaction hashes, + /// depending on the filter type, which occurred since last poll. + /// * Filters created with `eth_newFilter` return [zksync_types::api::Log] objects. + /// * Filters created with `eth_newBlockFilter` return block hashes. + /// * Filters created with `eth_newPendingTransactionFilter` return transaction hashes. + fn get_filter_changes(&self, id: U256) -> RpcResult { + let inner = self.get_inner().clone(); + let mut writer = match inner.write() { + Ok(r) => r, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + + writer + .filters + .get_new_changes(id) + .map_err(|_| into_jsrpc_error(Web3Error::InternalError)) + .into_boxed_future() + } + + fn get_block_transaction_count_by_number( + &self, + block_number: BlockNumber, + ) -> RpcResult> { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let maybe_result = { + let reader = match inner.read() { + Ok(r) => r, + Err(_) => return Err(into_jsrpc_error(Web3Error::InternalError)), + }; + let number = + utils::to_real_block_number(block_number, U64::from(reader.current_miniblock)) + .as_u64(); + + reader + .block_hashes + .get(&number) + .and_then(|hash| reader.blocks.get(hash)) + .map(|block| U256::from(block.transactions.len())) + .or_else(|| { + reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_block_transaction_count_by_number(block_number) + .ok() + .flatten() + }) + }) + }; + + match maybe_result { + Some(value) => Ok(Some(value)), + None => Err(into_jsrpc_error(Web3Error::NoBlock)), + } + }) + } + + fn get_block_transaction_count_by_hash( + &self, + block_hash: zksync_basic_types::H256, + ) -> RpcResult> { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let reader = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + // try retrieving block from memory, and if unavailable subsequently from the fork + let maybe_result = reader + .blocks + .get(&block_hash) + .map(|block| U256::from(block.transactions.len())) + .or_else(|| { + reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_block_transaction_count_by_hash(block_hash) + .ok() + .flatten() + }) + }); + + match maybe_result { + Some(value) => Ok(Some(value)), + None => Err(into_jsrpc_error(Web3Error::NoBlock)), + } + }) + } + + /// Returns the value from a storage position at a given address. + /// + /// # Arguments + /// + /// * `address`: Address of the storage + /// * `idx`: Integer of the position in the storage + /// * `block`: The block storage to target + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to a [H256] value in the storage. + fn get_storage( + &self, + address: zksync_basic_types::Address, + idx: U256, + block: Option, + ) -> RpcResult { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let mut writer = match inner.write() { + Ok(r) => r, + Err(_) => { + return Err(into_jsrpc_error(Web3Error::InternalError)); + } + }; + + let storage_key = StorageKey::new(AccountTreeId::new(address), u256_to_h256(idx)); + + let block_number = block + .map(|block| match block { + BlockIdVariant::BlockNumber(block_number) => Ok(utils::to_real_block_number( + block_number, + U64::from(writer.current_miniblock), + )), + BlockIdVariant::BlockNumberObject(o) => Ok(utils::to_real_block_number( + o.block_number, + U64::from(writer.current_miniblock), + )), + BlockIdVariant::BlockHashObject(o) => writer + .blocks + .get(&o.block_hash) + .map(|block| block.number) + .ok_or_else(|| { + tracing::error!( + "unable to map block number to hash #{:#x}", + o.block_hash + ); + into_jsrpc_error(Web3Error::InternalError) + }), + }) + .unwrap_or_else(|| Ok(U64::from(writer.current_miniblock)))?; + + if block_number.as_u64() == writer.current_miniblock { + Ok(H256(writer.fork_storage.read_value(&storage_key).0)) + } else if writer.block_hashes.contains_key(&block_number.as_u64()) { + let value = writer + .block_hashes + .get(&block_number.as_u64()) + .and_then(|block_hash| writer.previous_states.get(block_hash)) + .and_then(|state| state.get(&storage_key)) + .cloned() + .unwrap_or_default(); + + if value.is_zero() { + Ok(H256(writer.fork_storage.read_value(&storage_key).0)) + } else { + Ok(value) + } + } else { + writer + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| fork.fork_source.get_storage_at(address, idx, block).ok()) + .ok_or_else(|| { + tracing::error!( + "unable to get storage at address {:?}, index {:?} for block {:?}", + address, + idx, + block + ); + into_jsrpc_error(Web3Error::InternalError) + }) + } + }) + } + + /// Returns information about a transaction by block hash and transaction index position. + /// + /// # Arguments + /// + /// * `block_hash`: Hash of a block + /// * `index`: Integer of the transaction index position + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that maybe resolves to a [zksync_types::api::Transaction], if found. + fn get_transaction_by_block_hash_and_index( + &self, + block_hash: zksync_basic_types::H256, + index: zksync_basic_types::web3::types::Index, + ) -> RpcResult> { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let reader = match inner.read() { + Ok(r) => r, + Err(_) => { + return Err(into_jsrpc_error(Web3Error::InternalError)); + } + }; + + let maybe_tx = reader + .blocks + .get(&block_hash) + .and_then(|block| block.transactions.get(index.as_usize())) + .and_then(|tx| match tx { + TransactionVariant::Full(tx) => Some(tx.clone()), + TransactionVariant::Hash(tx_hash) => reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_transaction_by_hash(*tx_hash) + .ok() + .flatten() + }), + }) + .or_else(|| { + reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_transaction_by_block_hash_and_index(block_hash, index) + .ok() + }) + .flatten() + }); + + Ok(maybe_tx) + }) + } + + /// Returns information about a transaction by block number and transaction index position. + /// + /// # Arguments + /// + /// * `block_number`: A block number, or the string "earliest", "latest" or "pending". + /// * `index`: Integer of the transaction index position + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that maybe resolves to a [zksync_types::api::Transaction], if found. + fn get_transaction_by_block_number_and_index( + &self, + block_number: BlockNumber, + index: zksync_basic_types::web3::types::Index, + ) -> RpcResult> { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let reader = match inner.read() { + Ok(r) => r, + Err(_) => { + return Err(into_jsrpc_error(Web3Error::InternalError)); + } + }; + + let real_block_number = + utils::to_real_block_number(block_number, U64::from(reader.current_miniblock)); + let maybe_tx = reader + .block_hashes + .get(&real_block_number.as_u64()) + .and_then(|block_hash| reader.blocks.get(block_hash)) + .and_then(|block| block.transactions.get(index.as_usize())) + .and_then(|tx| match tx { + TransactionVariant::Full(tx) => Some(tx.clone()), + TransactionVariant::Hash(tx_hash) => reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_transaction_by_hash(*tx_hash) + .ok() + .flatten() + }), + }) + .or_else(|| { + reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_transaction_by_block_number_and_index(block_number, index) + .ok() + }) + .flatten() + }); + + Ok(maybe_tx) + }) + } + + /// Returns the protocol version. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to a hex `String` of the version number. + fn protocol_version(&self) -> RpcResult { + Ok(String::from(PROTOCOL_VERSION)).into_boxed_future() + } + + fn syncing(&self) -> RpcResult { + Ok(SyncState::NotSyncing).into_boxed_future() + } + /// Returns a list of available accounts. + /// + /// This function fetches the accounts from the inner state, and returns them as a list of addresses (`H160`). + /// + /// # Errors + /// + /// Returns a `jsonrpc_core::Result` error if acquiring a write lock on the inner state fails. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `jsonrpc_core::Result` that resolves to a `Vec` of addresses. + fn accounts(&self) -> RpcResult> { + let inner = self.get_inner().clone(); + let reader = match inner.read() { + Ok(r) => r, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + + let accounts: Vec = reader.rich_accounts.clone().into_iter().collect(); + futures::future::ok(accounts).boxed() + } + + fn coinbase(&self) -> RpcResult { + not_implemented("eth_coinbase") + } + + fn compilers(&self) -> RpcResult> { + not_implemented("eth_getCompilers") + } + + fn hashrate(&self) -> RpcResult { + not_implemented("eth_hashrate") + } + + fn get_uncle_count_by_block_hash( + &self, + _hash: zksync_basic_types::H256, + ) -> RpcResult> { + not_implemented("eth_getUncleCountByBlockHash") + } + + fn get_uncle_count_by_block_number(&self, _number: BlockNumber) -> RpcResult> { + not_implemented("eth_getUncleCountByBlockNumber") + } + + fn mining(&self) -> RpcResult { + not_implemented("eth_mining") + } + + /// Returns the fee history for a given range of blocks. + /// + /// Note: This implementation is limited to using the hard-coded value + /// of L2_GAS_PRICE as the history gas price + /// + /// # Arguments + /// + /// * `block_count` - The number of blocks in the requested range. Between 1 and 1024 blocks can be requested in a single query. It will return less than the requested range if not all blocks are available. + /// * `newest_block` - The highest number block of the requested range. As this implementation is using hard-coded values, this argument is ignored. + /// * `reward_percentiles` - A list of percentile values with a monotonic increase in value. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a `FeeHistory` representing the fee history of the specified range of blocks. + fn fee_history( + &self, + block_count: U64, + _newest_block: BlockNumber, + reward_percentiles: Vec, + ) -> RpcResult { + let inner = self.get_inner().clone(); + + Box::pin(async move { + let reader = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let block_count = block_count + .as_u64() + .min(1024) + // Can't be more than the total number of blocks + .clamp(1, reader.current_miniblock + 1); + + let mut base_fee_per_gas = vec![U256::from(L2_GAS_PRICE); block_count as usize]; + + let oldest_block = reader.current_miniblock + 1 - base_fee_per_gas.len() as u64; + // We do not store gas used ratio for blocks, returns array of zeroes as a placeholder. + let gas_used_ratio = vec![0.0; base_fee_per_gas.len()]; + // Effective priority gas price is currently 0. + let reward = Some(vec![ + vec![U256::zero(); reward_percentiles.len()]; + base_fee_per_gas.len() + ]); + + // `base_fee_per_gas` for next miniblock cannot be calculated, appending last fee as a placeholder. + base_fee_per_gas.push(*base_fee_per_gas.last().unwrap()); + + Ok(FeeHistory { + oldest_block: web3::types::BlockNumber::Number(oldest_block.into()), + base_fee_per_gas, + gas_used_ratio, + reward, + }) + }) + } +} + +impl EthTestNodeNamespaceT + for InMemoryNode +{ + /// Sends a transaction to the L2 network. Can be used for the impersonated account. + /// + /// # Arguments + /// + /// * `tx` - A `CallRequest` struct representing the transaction. + /// + /// # Returns + /// + /// A future that resolves to the hash of the transaction if successful, or an error if the transaction is invalid or execution fails. + fn send_transaction( + &self, + tx: zksync_types::transaction_request::CallRequest, + ) -> jsonrpc_core::BoxFuture> { + let chain_id = match self.get_inner().read() { + Ok(reader) => reader.fork_storage.chain_id, + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + }; + + let mut tx_req = TransactionRequest::from(tx.clone()); + // EIP-1559 gas fields should be processed separately + if tx.gas_price.is_some() { + if tx.max_fee_per_gas.is_some() || tx.max_priority_fee_per_gas.is_some() { + return futures::future::err(into_jsrpc_error(Web3Error::InvalidTransactionData( + zksync_types::ethabi::Error::InvalidData, + ))) + .boxed(); + } + } else { + tx_req.gas_price = tx.max_fee_per_gas.unwrap_or_default(); + tx_req.max_priority_fee_per_gas = tx.max_priority_fee_per_gas; + if tx_req.transaction_type.is_none() { + tx_req.transaction_type = Some(zksync_types::EIP_1559_TX_TYPE.into()); + } + } + // Needed to calculate hash + tx_req.r = Some(U256::default()); + tx_req.s = Some(U256::default()); + tx_req.v = Some(U64::from(27)); + + let hash = match tx_req.get_tx_hash(chain_id) { + Ok(result) => result, + Err(e) => { + return futures::future::err(into_jsrpc_error(Web3Error::SerializationError(e))) + .boxed() + } + }; + let bytes = tx_req.get_signed_bytes( + &PackedEthSignature::from_rsv(&H256::default(), &H256::default(), 27), + chain_id, + ); + let mut l2_tx: L2Tx = match L2Tx::from_request(tx_req, MAX_TX_SIZE) { + Ok(tx) => tx, + Err(e) => { + return futures::future::err(into_jsrpc_error(Web3Error::SerializationError(e))) + .boxed() + } + }; + + // `v` was overwritten with 0 during converting into l2 tx + let mut signature = vec![0u8; 65]; + signature[64] = 27; + l2_tx.common_data.signature = signature; + + l2_tx.set_input(bytes, hash); + + match self.get_inner().read() { + Ok(reader) => { + if !reader + .impersonated_accounts + .contains(&l2_tx.common_data.initiator_address) + { + return futures::future::err(into_jsrpc_error( + Web3Error::InvalidTransactionData(zksync_types::ethabi::Error::InvalidData), + )) + .boxed(); + } + } + Err(_) => { + return futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + } + + match self.run_l2_tx(l2_tx.clone(), TxExecutionMode::VerifyExecute) { + Ok(_) => Ok(l2_tx.hash()).into_boxed_future(), + Err(e) => { + let error_message = format!("Execution error: {}", e); + futures::future::err(into_jsrpc_error(Web3Error::SubmitTransactionError( + error_message, + l2_tx.hash().as_bytes().to_vec(), + ))) + .boxed() + } + } + } +} + +#[cfg(test)] +mod tests { + use crate::{ + cache::CacheConfig, + fork::ForkDetails, + http_fork_source::HttpForkSource, + node::{compute_hash, InMemoryNode, Snapshot}, + testing::{ + self, default_tx_debug_info, ForkBlockConfig, LogBuilder, MockServer, + TransactionResponseBuilder, + }, + }; + use maplit::hashmap; + use zksync_basic_types::{web3, Nonce}; + use zksync_types::{ + api::{BlockHashObject, BlockNumber, BlockNumberObject, TransactionReceipt}, + utils::deployed_address_create, + PackedEthSignature, + }; + use zksync_web3_decl::types::{SyncState, ValueOrArray}; + + use super::*; + + #[tokio::test] + async fn test_eth_syncing() { + let node = InMemoryNode::::default(); + let syncing = node.syncing().await.expect("failed syncing"); + assert!(matches!(syncing, SyncState::NotSyncing)); + } + + #[tokio::test] + async fn test_get_fee_history_with_1_block() { + let node = InMemoryNode::::default(); + + let fee_history = node + .fee_history(U64::from(1), BlockNumber::Latest, vec![25.0, 50.0, 75.0]) + .await + .expect("fee_history failed"); + + assert_eq!( + fee_history.oldest_block, + web3::types::BlockNumber::Number(U64::from(0)) + ); + assert_eq!( + fee_history.base_fee_per_gas, + vec![U256::from(L2_GAS_PRICE); 2] + ); + assert_eq!(fee_history.gas_used_ratio, vec![0.0]); + assert_eq!(fee_history.reward, Some(vec![vec![U256::from(0); 3]])); + } + + #[tokio::test] + async fn test_get_fee_history_with_no_reward_percentiles() { + let node = InMemoryNode::::default(); + + let fee_history = node + .fee_history(U64::from(1), BlockNumber::Latest, vec![]) + .await + .expect("fee_history failed"); + + assert_eq!( + fee_history.oldest_block, + web3::types::BlockNumber::Number(U64::from(0)) + ); + assert_eq!( + fee_history.base_fee_per_gas, + vec![U256::from(L2_GAS_PRICE); 2] + ); + assert_eq!(fee_history.gas_used_ratio, vec![0.0]); + assert_eq!(fee_history.reward, Some(vec![vec![]])); + } + + #[tokio::test] + async fn test_get_fee_history_with_multiple_blocks() { + // Arrange + let node = InMemoryNode::::default(); + testing::apply_tx(&node, H256::repeat_byte(0x01)); + + // Act + let latest_block = node + .get_block_number() + .await + .expect("Block number fetch failed"); + let fee_history = node + .fee_history(U64::from(2), BlockNumber::Latest, vec![25.0, 50.0, 75.0]) + .await + .expect("fee_history failed"); + + // Assert + // We should receive 2 fees: from block 1 and 2. + assert_eq!(latest_block, U64::from(2)); + assert_eq!( + fee_history.oldest_block, + web3::types::BlockNumber::Number(U64::from(1)) + ); + assert_eq!( + fee_history.base_fee_per_gas, + vec![U256::from(L2_GAS_PRICE); 3] + ); + assert_eq!(fee_history.gas_used_ratio, vec![0.0, 0.0]); + assert_eq!(fee_history.reward, Some(vec![vec![U256::from(0); 3]; 2])); + } + + #[tokio::test] + async fn test_get_block_by_hash_returns_none_for_non_existing_block() { + let node = InMemoryNode::::default(); + + let result = node + .get_block_by_hash(H256::repeat_byte(0x01), false) + .await + .expect("failed fetching block by hash"); + + assert!(result.is_none()); + } + + #[tokio::test] + async fn test_node_has_genesis_block() { + let node = InMemoryNode::::default(); + + let block = node + .get_block_by_number(BlockNumber::Latest, false) + .await + .expect("failed fetching block by number") + .expect("no block"); + + assert_eq!(0, block.number.as_u64()); + assert_eq!(compute_hash(0, H256::zero()), block.hash); + } + + #[tokio::test] + async fn test_node_creates_genesis_block_with_hash_and_zero_parent_hash() { + let node = InMemoryNode::::default(); + + let block = node + .get_block_by_hash(compute_hash(0, H256::zero()), false) + .await + .expect("failed fetching block by hash") + .expect("no block"); + + assert_eq!(block.parent_hash, H256::zero()); + } + + #[tokio::test] + async fn test_node_produces_blocks_with_parent_hash_links() { + let node = InMemoryNode::::default(); + testing::apply_tx(&node, H256::repeat_byte(0x01)); + + let genesis_block = node + .get_block_by_number(BlockNumber::from(0), false) + .await + .expect("failed fetching block by number") + .expect("no block"); + let first_block = node + .get_block_by_number(BlockNumber::from(1), false) + .await + .expect("failed fetching block by number") + .expect("no block"); + let second_block = node + .get_block_by_number(BlockNumber::from(2), false) + .await + .expect("failed fetching block by number") + .expect("no block"); + + assert_eq!(genesis_block.hash, first_block.parent_hash); + assert_eq!(first_block.hash, second_block.parent_hash); + } + + #[tokio::test] + async fn test_get_block_by_hash_for_produced_block() { + let node = InMemoryNode::::default(); + let (expected_block_hash, _) = testing::apply_tx(&node, H256::repeat_byte(0x01)); + + let actual_block = node + .get_block_by_hash(expected_block_hash, false) + .await + .expect("failed fetching block by hash") + .expect("no block"); + + assert_eq!(expected_block_hash, actual_block.hash); + assert_eq!(U64::from(1), actual_block.number); + assert_eq!(Some(U64::from(1)), actual_block.l1_batch_number); + } + + #[tokio::test] + async fn test_node_block_mapping_is_correctly_populated_when_using_fork_source() { + let input_block_number = 8; + let input_block_hash = H256::repeat_byte(0x01); + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: input_block_number, + hash: input_block_hash, + transaction_count: 0, + }); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let inner = node.get_inner(); + let inner = inner.read().unwrap(); + assert!( + inner.blocks.contains_key(&input_block_hash), + "block wasn't cached" + ); + assert!( + inner.block_hashes.contains_key(&input_block_number), + "block number wasn't cached" + ); + } + + #[tokio::test] + async fn test_get_block_by_hash_uses_fork_source() { + let input_block_hash = H256::repeat_byte(0x01); + + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + hash: H256::repeat_byte(0xab), + transaction_count: 0, + }); + let mock_block_number = 8; + let block_response = testing::BlockResponseBuilder::new() + .set_hash(input_block_hash) + .set_number(mock_block_number) + .build(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getBlockByHash", + "params": [ + format!("{input_block_hash:#x}"), + true + ], + }), + block_response, + ); + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_block = node + .get_block_by_hash(input_block_hash, false) + .await + .expect("failed fetching block by hash") + .expect("no block"); + + assert_eq!(input_block_hash, actual_block.hash); + assert_eq!(U64::from(mock_block_number), actual_block.number); + assert_eq!(Some(U64::from(6)), actual_block.l1_batch_number); + } + + #[tokio::test] + async fn test_get_block_by_number_returns_none_for_non_existing_block() { + let node = InMemoryNode::::default(); + + let result = node + .get_block_by_number(BlockNumber::Number(U64::from(42)), false) + .await + .expect("failed fetching block by number"); + + assert!(result.is_none()); + } + + #[tokio::test] + async fn test_get_block_by_number_for_produced_block() { + let node = InMemoryNode::::default(); + testing::apply_tx(&node, H256::repeat_byte(0x01)); + let expected_block_number = 1; + + let actual_block = node + .get_block_by_number(BlockNumber::Number(U64::from(expected_block_number)), false) + .await + .expect("failed fetching block by hash") + .expect("no block"); + + assert_eq!(U64::from(expected_block_number), actual_block.number); + assert_eq!(1, actual_block.transactions.len()); + } + + #[tokio::test] + async fn test_get_block_by_number_uses_fork_source_if_missing_number() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + hash: H256::repeat_byte(0xab), + transaction_count: 0, + }); + let mock_block_number = 8; + let block_response = testing::BlockResponseBuilder::new() + .set_number(mock_block_number) + .build(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getBlockByNumber", + "params": [ + "0x8", + true + ], + }), + block_response, + ); + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_block = node + .get_block_by_number(BlockNumber::Number(U64::from(8)), false) + .await + .expect("failed fetching block by hash") + .expect("no block"); + assert_eq!(U64::from(mock_block_number), actual_block.number); + } + + #[tokio::test] + async fn test_get_block_by_number_for_latest_block_produced_locally() { + let node = InMemoryNode::::default(); + testing::apply_tx(&node, H256::repeat_byte(0x01)); + + // The latest block, will be the 'virtual' one with 0 transactions (block 2). + let virtual_block = node + .get_block_by_number(BlockNumber::Latest, true) + .await + .expect("failed fetching block by hash") + .expect("no block"); + + assert_eq!(U64::from(2), virtual_block.number); + assert_eq!(0, virtual_block.transactions.len()); + + let actual_block = node + .get_block_by_number(BlockNumber::Number(U64::from(1)), true) + .await + .expect("failed fetching block by hash") + .expect("no block"); + + assert_eq!(U64::from(1), actual_block.number); + assert_eq!(1, actual_block.transactions.len()); + } + + #[tokio::test] + async fn test_get_block_by_number_uses_locally_available_block_for_latest_block() { + let input_block_number = 10; + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: input_block_number, + hash: H256::repeat_byte(0x01), + transaction_count: 0, + }); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_block = node + .get_block_by_number(BlockNumber::Latest, false) + .await + .expect("failed fetching block by hash") + .expect("no block"); + assert_eq!(U64::from(input_block_number), actual_block.number); + } + + #[tokio::test] + async fn test_get_block_by_number_uses_fork_source_for_earliest_block() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + hash: H256::repeat_byte(0xab), + transaction_count: 0, + }); + let input_block_number = 1; + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getBlockByNumber", + "params": [ + "earliest", + true + ], + }), + testing::BlockResponseBuilder::new() + .set_number(input_block_number) + .build(), + ); + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_block = node + .get_block_by_number(BlockNumber::Earliest, false) + .await + .expect("failed fetching block by hash") + .expect("no block"); + assert_eq!(U64::from(input_block_number), actual_block.number); + } + + #[tokio::test] + async fn test_get_block_by_number_uses_locally_available_for_latest_alike_blocks() { + for block_number in [ + BlockNumber::Pending, + BlockNumber::Committed, + BlockNumber::Finalized, + ] { + let input_block_number = 10; + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: input_block_number, + hash: H256::repeat_byte(0xab), + transaction_count: 0, + }); + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_block = node + .get_block_by_number(block_number, false) + .await + .expect("failed fetching block by hash") + .expect("no block"); + assert_eq!( + U64::from(input_block_number), + actual_block.number, + "case {}", + block_number, + ); + } + } + + #[tokio::test] + async fn test_get_block_transaction_count_by_hash_for_produced_block() { + let node = InMemoryNode::::default(); + + let (expected_block_hash, _) = testing::apply_tx(&node, H256::repeat_byte(0x01)); + let actual_transaction_count = node + .get_block_transaction_count_by_hash(expected_block_hash) + .await + .expect("failed fetching block by hash") + .expect("no result"); + + assert_eq!(U256::from(1), actual_transaction_count); + } + + #[tokio::test] + async fn test_get_block_transaction_count_by_hash_uses_fork_source() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + hash: H256::repeat_byte(0xab), + transaction_count: 0, + }); + let input_block_hash = H256::repeat_byte(0x01); + let input_transaction_count = 1; + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getBlockTransactionCountByHash", + "params": [ + format!("{:#x}", input_block_hash), + ], + }), + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "result": format!("{:#x}", input_transaction_count), + }), + ); + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_transaction_count = node + .get_block_transaction_count_by_hash(input_block_hash) + .await + .expect("failed fetching block by hash") + .expect("no result"); + + assert_eq!( + U256::from(input_transaction_count), + actual_transaction_count + ); + } + + #[tokio::test] + async fn test_get_block_transaction_count_by_number_for_produced_block() { + let node = InMemoryNode::::default(); + + testing::apply_tx(&node, H256::repeat_byte(0x01)); + let actual_transaction_count = node + .get_block_transaction_count_by_number(BlockNumber::Number(U64::from(1))) + .await + .expect("failed fetching block by hash") + .expect("no result"); + + assert_eq!(U256::from(1), actual_transaction_count); + } + + #[tokio::test] + async fn test_get_block_transaction_count_by_number_uses_fork_source() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + hash: H256::repeat_byte(0xab), + transaction_count: 0, + }); + let input_block_number = 1; + let input_transaction_count = 1; + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getBlockTransactionCountByNumber", + "params": [ + format!("{:#x}", input_block_number), + ], + }), + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "result": format!("{:#x}", input_transaction_count), + }), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_transaction_count = node + .get_block_transaction_count_by_number(BlockNumber::Number(U64::from(1))) + .await + .expect("failed fetching block by hash") + .expect("no result"); + + assert_eq!( + U256::from(input_transaction_count), + actual_transaction_count + ); + } + + #[tokio::test] + async fn test_get_block_transaction_count_by_number_earliest_uses_fork_source() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + hash: H256::repeat_byte(0xab), + transaction_count: 0, + }); + let input_transaction_count = 1; + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getBlockTransactionCountByNumber", + "params": [ + "earliest", + ], + }), + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "result": format!("{:#x}", input_transaction_count), + }), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_transaction_count = node + .get_block_transaction_count_by_number(BlockNumber::Earliest) + .await + .expect("failed fetching block by hash") + .expect("no result"); + + assert_eq!( + U256::from(input_transaction_count), + actual_transaction_count + ); + } + + #[tokio::test] + async fn test_get_block_transaction_count_by_number_latest_alike_uses_fork_source() { + for block_number in [ + BlockNumber::Latest, + BlockNumber::Pending, + BlockNumber::Committed, + BlockNumber::Finalized, + ] { + let input_transaction_count = 1; + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: input_transaction_count, + hash: H256::repeat_byte(0xab), + }); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_transaction_count = node + .get_block_transaction_count_by_number(block_number) + .await + .expect("failed fetching block by hash") + .expect("no result"); + + assert_eq!( + U256::from(input_transaction_count), + actual_transaction_count, + "case {}", + block_number, + ); + } + } + + #[tokio::test] + async fn test_get_transaction_receipt_uses_produced_block_hash() { + let node = InMemoryNode::::default(); + let tx_hash = H256::repeat_byte(0x01); + let (expected_block_hash, _) = testing::apply_tx(&node, tx_hash); + + let actual_tx_receipt = node + .get_transaction_receipt(tx_hash) + .await + .expect("failed fetching transaction receipt by hash") + .expect("no transaction receipt"); + + assert_eq!(Some(expected_block_hash), actual_tx_receipt.block_hash); + } + + #[tokio::test] + async fn test_new_block_filter_returns_filter_id() { + let node = InMemoryNode::::default(); + + let actual_filter_id = node + .new_block_filter() + .await + .expect("failed creating filter"); + + assert_eq!(U256::from(1), actual_filter_id); + } + + #[tokio::test] + async fn test_new_filter_returns_filter_id() { + let node = InMemoryNode::::default(); + + let actual_filter_id = node + .new_filter(Filter::default()) + .await + .expect("failed creating filter"); + + assert_eq!(U256::from(1), actual_filter_id); + } + + #[tokio::test] + async fn test_new_pending_transaction_filter_returns_filter_id() { + let node = InMemoryNode::::default(); + + let actual_filter_id = node + .new_pending_transaction_filter() + .await + .expect("failed creating filter"); + + assert_eq!(U256::from(1), actual_filter_id); + } + + #[tokio::test] + async fn test_uninstall_filter_returns_true_if_filter_exists() { + let node = InMemoryNode::::default(); + let filter_id = node + .new_block_filter() + .await + .expect("failed creating filter"); + + let actual_result = node + .uninstall_filter(filter_id) + .await + .expect("failed creating filter"); + + assert!(actual_result); + } + + #[tokio::test] + async fn test_uninstall_filter_returns_false_if_filter_does_not_exist() { + let node = InMemoryNode::::default(); + + let actual_result = node + .uninstall_filter(U256::from(100)) + .await + .expect("failed creating filter"); + + assert!(!actual_result); + } + + #[tokio::test] + async fn test_get_filter_changes_returns_block_hash_updates_only_once() { + let node = InMemoryNode::::default(); + let filter_id = node + .new_block_filter() + .await + .expect("failed creating filter"); + let (block_hash, _) = testing::apply_tx(&node, H256::repeat_byte(0x1)); + + match node + .get_filter_changes(filter_id) + .await + .expect("failed getting filter changes") + { + FilterChanges::Hashes(result) => { + // Get the block hash and the virtual block hash. + assert_eq!(2, result.len()); + assert_eq!(block_hash, result[0]); + } + changes => panic!("unexpected filter changes: {:?}", changes), + } + + match node + .get_filter_changes(filter_id) + .await + .expect("failed getting filter changes") + { + FilterChanges::Empty(_) => (), + changes => panic!("expected no changes in the second call, got {:?}", changes), + } + } + + #[tokio::test] + async fn test_get_filter_changes_returns_log_updates_only_once() { + let node = InMemoryNode::::default(); + let filter_id = node + .new_filter(Filter { + from_block: None, + to_block: None, + address: None, + topics: None, + block_hash: None, + }) + .await + .expect("failed creating filter"); + testing::apply_tx(&node, H256::repeat_byte(0x1)); + + match node + .get_filter_changes(filter_id) + .await + .expect("failed getting filter changes") + { + FilterChanges::Logs(result) => assert_eq!(3, result.len()), + changes => panic!("unexpected filter changes: {:?}", changes), + } + + match node + .get_filter_changes(filter_id) + .await + .expect("failed getting filter changes") + { + FilterChanges::Empty(_) => (), + changes => panic!("expected no changes in the second call, got {:?}", changes), + } + } + + #[tokio::test] + async fn test_get_filter_changes_returns_pending_transaction_updates_only_once() { + let node = InMemoryNode::::default(); + let filter_id = node + .new_pending_transaction_filter() + .await + .expect("failed creating filter"); + testing::apply_tx(&node, H256::repeat_byte(0x1)); + + match node + .get_filter_changes(filter_id) + .await + .expect("failed getting filter changes") + { + FilterChanges::Hashes(result) => assert_eq!(vec![H256::repeat_byte(0x1)], result), + changes => panic!("unexpected filter changes: {:?}", changes), + } + + match node + .get_filter_changes(filter_id) + .await + .expect("failed getting filter changes") + { + FilterChanges::Empty(_) => (), + changes => panic!("expected no changes in the second call, got {:?}", changes), + } + } + + #[tokio::test] + async fn test_produced_block_archives_previous_blocks() { + let node = InMemoryNode::::default(); + + let input_storage_key = StorageKey::new( + AccountTreeId::new(H160::repeat_byte(0x1)), + u256_to_h256(U256::zero()), + ); + let input_storage_value = H256::repeat_byte(0xcd); + node.get_inner() + .write() + .unwrap() + .fork_storage + .set_value(input_storage_key, input_storage_value); + let initial_miniblock = node.get_inner().read().unwrap().current_miniblock; + + testing::apply_tx(&node, H256::repeat_byte(0x1)); + let current_miniblock = node.get_inner().read().unwrap().current_miniblock; + + let inner = node.get_inner(); + let reader = inner.read().unwrap(); + for miniblock in initial_miniblock..current_miniblock { + let actual_cached_value = reader + .block_hashes + .get(&miniblock) + .map(|hash| { + reader + .previous_states + .get(hash) + .unwrap_or_else(|| panic!("state was not cached for block {}", miniblock)) + }) + .and_then(|state| state.get(&input_storage_key)) + .copied(); + + assert_eq!( + Some(input_storage_value), + actual_cached_value, + "unexpected cached state value for block {}", + miniblock + ); + } + } + + #[tokio::test] + async fn test_get_storage_fetches_zero_value_for_non_existent_key() { + let node = InMemoryNode::::default(); + + let value = node + .get_storage(H160::repeat_byte(0xf1), U256::from(1024), None) + .await + .expect("failed retrieving storage"); + assert_eq!(H256::zero(), value); + } + + #[tokio::test] + async fn test_get_storage_uses_fork_to_get_value_for_historical_block() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let input_address = H160::repeat_byte(0x1); + let input_storage_value = H256::repeat_byte(0xcd); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getStorageAt", + "params": [ + format!("{:#x}", input_address), + "0x0", + { "blockNumber": "0x2" }, + ], + }), + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "result": format!("{:#x}", input_storage_value), + }), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_value = node + .get_storage( + input_address, + U256::zero(), + Some(zksync_types::api::BlockIdVariant::BlockNumberObject( + BlockNumberObject { + block_number: BlockNumber::Number(U64::from(2)), + }, + )), + ) + .await + .expect("failed retrieving storage"); + assert_eq!(input_storage_value, actual_value); + } + + #[tokio::test] + async fn test_get_storage_uses_archived_storage_to_get_value_for_missing_key() { + let input_address = H160::repeat_byte(0x1); + let input_storage_key = StorageKey::new( + AccountTreeId::new(input_address), + u256_to_h256(U256::zero()), + ); + let input_storage_value = H256::repeat_byte(0xcd); + + let node = InMemoryNode::::default(); + node.get_inner() + .write() + .map(|mut writer| { + let historical_block = Block:: { + hash: H256::repeat_byte(0x2), + number: U64::from(2), + ..Default::default() + }; + writer.block_hashes.insert(2, historical_block.hash); + + writer.previous_states.insert( + historical_block.hash, + hashmap! { + input_storage_key => input_storage_value, + }, + ); + writer + .blocks + .insert(historical_block.hash, historical_block); + }) + .expect("failed setting storage for historical block"); + + let actual_value = node + .get_storage( + input_address, + U256::zero(), + Some(zksync_types::api::BlockIdVariant::BlockNumberObject( + BlockNumberObject { + block_number: BlockNumber::Number(U64::from(2)), + }, + )), + ) + .await + .expect("failed retrieving storage"); + assert_eq!(input_storage_value, actual_value); + } + + #[tokio::test] + async fn test_get_storage_uses_fork_to_get_value_for_latest_block_for_missing_key() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let input_address = H160::repeat_byte(0x1); + let input_storage_value = H256::repeat_byte(0xcd); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getStorageAt", + "params": [ + format!("{:#x}", input_address), + "0x0", + "0xa", + ], + }), + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "result": format!("{:#x}", input_storage_value), + }), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + node.get_inner() + .write() + .map(|mut writer| { + let historical_block = Block:: { + hash: H256::repeat_byte(0x2), + number: U64::from(2), + ..Default::default() + }; + writer.block_hashes.insert(2, historical_block.hash); + writer + .previous_states + .insert(historical_block.hash, Default::default()); + writer + .blocks + .insert(historical_block.hash, historical_block); + }) + .expect("failed setting storage for historical block"); + + let actual_value = node + .get_storage( + input_address, + U256::zero(), + Some(zksync_types::api::BlockIdVariant::BlockNumberObject( + BlockNumberObject { + block_number: BlockNumber::Number(U64::from(2)), + }, + )), + ) + .await + .expect("failed retrieving storage"); + assert_eq!(input_storage_value, actual_value); + } + + #[tokio::test] + async fn test_get_storage_fetches_state_for_deployed_smart_contract_in_current_block() { + let node = InMemoryNode::::default(); + + let private_key = H256::repeat_byte(0xef); + let from_account = zksync_types::PackedEthSignature::address_from_private_key(&private_key) + .expect("failed generating address"); + node.set_rich_account(from_account); + + let deployed_address = deployed_address_create(from_account, U256::zero()); + + testing::deploy_contract( + &node, + H256::repeat_byte(0x1), + private_key, + hex::decode(testing::STORAGE_CONTRACT_BYTECODE).unwrap(), + None, + Nonce(0), + ); + + let number1 = node + .get_storage(deployed_address, U256::from(0), None) + .await + .expect("failed retrieving storage at slot 0"); + assert_eq!(U256::from(1024), h256_to_u256(number1)); + + let number2 = node + .get_storage(deployed_address, U256::from(1), None) + .await + .expect("failed retrieving storage at slot 1"); + assert_eq!(U256::MAX, h256_to_u256(number2)); + } + + #[tokio::test] + async fn test_get_storage_fetches_state_for_deployed_smart_contract_in_old_block() { + let node = InMemoryNode::::default(); + + let private_key = H256::repeat_byte(0xef); + let from_account = zksync_types::PackedEthSignature::address_from_private_key(&private_key) + .expect("failed generating address"); + node.set_rich_account(from_account); + + let deployed_address = deployed_address_create(from_account, U256::zero()); + + let initial_block_hash = testing::deploy_contract( + &node, + H256::repeat_byte(0x1), + private_key, + hex::decode(testing::STORAGE_CONTRACT_BYTECODE).unwrap(), + None, + Nonce(0), + ); + + // simulate a tx modifying the storage + testing::apply_tx(&node, H256::repeat_byte(0x2)); + let key = StorageKey::new( + AccountTreeId::new(deployed_address), + u256_to_h256(U256::from(0)), + ); + node.get_inner() + .write() + .unwrap() + .fork_storage + .inner + .write() + .unwrap() + .raw_storage + .state + .insert(key, u256_to_h256(U256::from(512))); + + let number1_current = node + .get_storage(deployed_address, U256::from(0), None) + .await + .expect("failed retrieving storage at slot 0"); + assert_eq!(U256::from(512), h256_to_u256(number1_current)); + + let number1_old = node + .get_storage( + deployed_address, + U256::from(0), + Some(zksync_types::api::BlockIdVariant::BlockHashObject( + BlockHashObject { + block_hash: initial_block_hash, + }, + )), + ) + .await + .expect("failed retrieving storage at slot 0"); + assert_eq!(U256::from(1024), h256_to_u256(number1_old)); + } + + #[tokio::test] + async fn test_get_filter_logs_returns_matching_logs_for_valid_id() { + let node = InMemoryNode::::default(); + + // populate tx receipts with 2 tx each having logs + { + let inner = node.get_inner(); + let mut writer = inner.write().unwrap(); + writer.tx_results.insert( + H256::repeat_byte(0x1), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![LogBuilder::new() + .set_address(H160::repeat_byte(0xa1)) + .build()], + ..Default::default() + }, + debug: default_tx_debug_info(), + }, + ); + writer.tx_results.insert( + H256::repeat_byte(0x2), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![ + LogBuilder::new() + .set_address(H160::repeat_byte(0xa1)) + .build(), + LogBuilder::new() + .set_address(H160::repeat_byte(0xa2)) + .build(), + ], + ..Default::default() + }, + debug: default_tx_debug_info(), + }, + ); + } + + let filter_id = node + .new_filter(Filter { + address: Some(ValueOrArray(vec![H160::repeat_byte(0xa1)])), + ..Default::default() + }) + .await + .expect("failed creating filter"); + + match node + .get_filter_logs(filter_id) + .await + .expect("failed getting filter changes") + { + FilterChanges::Logs(result) => assert_eq!(2, result.len()), + changes => panic!("unexpected filter changes: {:?}", changes), + } + } + + #[tokio::test] + async fn test_get_filter_logs_returns_error_for_invalid_id() { + let node = InMemoryNode::::default(); + + // populate tx receipts with 2 tx each having logs + { + let inner = node.get_inner(); + let mut writer = inner.write().unwrap(); + writer.tx_results.insert( + H256::repeat_byte(0x1), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![LogBuilder::new() + .set_address(H160::repeat_byte(0xa1)) + .build()], + ..Default::default() + }, + debug: default_tx_debug_info(), + }, + ); + } + + let invalid_filter_id = U256::from(100); + let result = node.get_filter_logs(invalid_filter_id).await; + + assert!(result.is_err(), "expected an error for invalid filter id"); + } + + #[tokio::test] + async fn test_get_logs_returns_matching_logs() { + let node = InMemoryNode::::default(); + + // populate tx receipts with 2 tx each having logs + { + let inner = node.get_inner(); + let mut writer = inner.write().unwrap(); + writer.tx_results.insert( + H256::repeat_byte(0x1), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![LogBuilder::new() + .set_address(H160::repeat_byte(0xa1)) + .build()], + ..Default::default() + }, + debug: testing::default_tx_debug_info(), + }, + ); + writer.tx_results.insert( + H256::repeat_byte(0x2), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![ + LogBuilder::new() + .set_address(H160::repeat_byte(0xa1)) + .build(), + LogBuilder::new() + .set_address(H160::repeat_byte(0xa2)) + .build(), + ], + ..Default::default() + }, + debug: testing::default_tx_debug_info(), + }, + ); + } + + let result = node + .get_logs(Filter { + address: Some(ValueOrArray(vec![H160::repeat_byte(0xa2)])), + ..Default::default() + }) + .await + .expect("failed getting filter changes"); + assert_eq!(1, result.len()); + + let result = node + .get_logs(Filter { + address: Some(ValueOrArray(vec![H160::repeat_byte(0xa1)])), + ..Default::default() + }) + .await + .expect("failed getting filter changes"); + assert_eq!(2, result.len()); + + let result = node + .get_logs(Filter { + address: Some(ValueOrArray(vec![H160::repeat_byte(0x11)])), + ..Default::default() + }) + .await + .expect("failed getting filter changes"); + assert_eq!(0, result.len()); + } + + #[tokio::test] + async fn test_accounts() { + let node = InMemoryNode::::default(); + + let private_key = H256::repeat_byte(0x01); + let from_account = PackedEthSignature::address_from_private_key(&private_key).unwrap(); + node.set_rich_account(from_account); + + let account_result = node.accounts().await; + let expected_accounts: Vec = vec![from_account]; + + match account_result { + Ok(accounts) => { + assert_eq!(expected_accounts, accounts); + } + Err(e) => { + panic!("Failed to fetch accounts: {:?}", e); + } + } + } + + #[tokio::test] + async fn test_snapshot() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + let mut inner = inner.write().unwrap(); + + inner + .blocks + .insert(H256::repeat_byte(0x1), Default::default()); + inner.block_hashes.insert(1, H256::repeat_byte(0x1)); + inner.tx_results.insert( + H256::repeat_byte(0x1), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: Default::default(), + debug: testing::default_tx_debug_info(), + }, + ); + inner.current_batch = 1; + inner.current_miniblock = 1; + inner.current_miniblock_hash = H256::repeat_byte(0x1); + inner.current_timestamp = 1; + inner + .filters + .add_block_filter() + .expect("failed adding block filter"); + inner.impersonated_accounts.insert(H160::repeat_byte(0x1)); + inner.rich_accounts.insert(H160::repeat_byte(0x1)); + inner + .previous_states + .insert(H256::repeat_byte(0x1), Default::default()); + inner.fork_storage.set_value( + StorageKey::new(AccountTreeId::new(H160::repeat_byte(0x1)), H256::zero()), + H256::repeat_byte(0x1), + ); + + let storage = inner.fork_storage.inner.read().unwrap(); + let expected_snapshot = Snapshot { + current_timestamp: inner.current_timestamp, + current_batch: inner.current_batch, + current_miniblock: inner.current_miniblock, + current_miniblock_hash: inner.current_miniblock_hash, + l1_gas_price: inner.l1_gas_price, + tx_results: inner.tx_results.clone(), + blocks: inner.blocks.clone(), + block_hashes: inner.block_hashes.clone(), + filters: inner.filters.clone(), + impersonated_accounts: inner.impersonated_accounts.clone(), + rich_accounts: inner.rich_accounts.clone(), + previous_states: inner.previous_states.clone(), + raw_storage: storage.raw_storage.clone(), + value_read_cache: storage.value_read_cache.clone(), + factory_dep_cache: storage.factory_dep_cache.clone(), + }; + let actual_snapshot = inner.snapshot().expect("failed taking snapshot"); + + assert_eq!( + expected_snapshot.current_timestamp, + actual_snapshot.current_timestamp + ); + assert_eq!( + expected_snapshot.current_batch, + actual_snapshot.current_batch + ); + assert_eq!( + expected_snapshot.current_miniblock, + actual_snapshot.current_miniblock + ); + assert_eq!( + expected_snapshot.current_miniblock_hash, + actual_snapshot.current_miniblock_hash + ); + assert_eq!(expected_snapshot.l1_gas_price, actual_snapshot.l1_gas_price); + assert_eq!( + expected_snapshot.tx_results.keys().collect_vec(), + actual_snapshot.tx_results.keys().collect_vec() + ); + assert_eq!(expected_snapshot.blocks, actual_snapshot.blocks); + assert_eq!(expected_snapshot.block_hashes, actual_snapshot.block_hashes); + assert_eq!(expected_snapshot.filters, actual_snapshot.filters); + assert_eq!( + expected_snapshot.impersonated_accounts, + actual_snapshot.impersonated_accounts + ); + assert_eq!( + expected_snapshot.rich_accounts, + actual_snapshot.rich_accounts + ); + assert_eq!( + expected_snapshot.previous_states, + actual_snapshot.previous_states + ); + assert_eq!(expected_snapshot.raw_storage, actual_snapshot.raw_storage); + assert_eq!( + expected_snapshot.value_read_cache, + actual_snapshot.value_read_cache + ); + assert_eq!( + expected_snapshot.factory_dep_cache, + actual_snapshot.factory_dep_cache + ); + } + + #[tokio::test] + async fn test_snapshot_restore() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + let mut inner = inner.write().unwrap(); + + inner + .blocks + .insert(H256::repeat_byte(0x1), Default::default()); + inner.block_hashes.insert(1, H256::repeat_byte(0x1)); + inner.tx_results.insert( + H256::repeat_byte(0x1), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: Default::default(), + debug: testing::default_tx_debug_info(), + }, + ); + inner.current_batch = 1; + inner.current_miniblock = 1; + inner.current_miniblock_hash = H256::repeat_byte(0x1); + inner.current_timestamp = 1; + inner + .filters + .add_block_filter() + .expect("failed adding block filter"); + inner.impersonated_accounts.insert(H160::repeat_byte(0x1)); + inner.rich_accounts.insert(H160::repeat_byte(0x1)); + inner + .previous_states + .insert(H256::repeat_byte(0x1), Default::default()); + inner.fork_storage.set_value( + StorageKey::new(AccountTreeId::new(H160::repeat_byte(0x1)), H256::zero()), + H256::repeat_byte(0x1), + ); + + let expected_snapshot = { + let storage = inner.fork_storage.inner.read().unwrap(); + Snapshot { + current_timestamp: inner.current_timestamp, + current_batch: inner.current_batch, + current_miniblock: inner.current_miniblock, + current_miniblock_hash: inner.current_miniblock_hash, + l1_gas_price: inner.l1_gas_price, + tx_results: inner.tx_results.clone(), + blocks: inner.blocks.clone(), + block_hashes: inner.block_hashes.clone(), + filters: inner.filters.clone(), + impersonated_accounts: inner.impersonated_accounts.clone(), + rich_accounts: inner.rich_accounts.clone(), + previous_states: inner.previous_states.clone(), + raw_storage: storage.raw_storage.clone(), + value_read_cache: storage.value_read_cache.clone(), + factory_dep_cache: storage.factory_dep_cache.clone(), + } + }; + + // snapshot and modify node state + let snapshot = inner.snapshot().expect("failed taking snapshot"); + inner + .blocks + .insert(H256::repeat_byte(0x2), Default::default()); + inner.block_hashes.insert(2, H256::repeat_byte(0x2)); + inner.tx_results.insert( + H256::repeat_byte(0x2), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: Default::default(), + debug: default_tx_debug_info(), + }, + ); + inner.current_batch = 2; + inner.current_miniblock = 2; + inner.current_miniblock_hash = H256::repeat_byte(0x2); + inner.current_timestamp = 2; + inner + .filters + .add_pending_transaction_filter() + .expect("failed adding pending transaction filter"); + inner.impersonated_accounts.insert(H160::repeat_byte(0x2)); + inner.rich_accounts.insert(H160::repeat_byte(0x2)); + inner + .previous_states + .insert(H256::repeat_byte(0x2), Default::default()); + inner.fork_storage.set_value( + StorageKey::new(AccountTreeId::new(H160::repeat_byte(0x2)), H256::zero()), + H256::repeat_byte(0x2), + ); + + // restore + inner + .restore_snapshot(snapshot) + .expect("failed restoring snapshot"); + + let storage = inner.fork_storage.inner.read().unwrap(); + assert_eq!(expected_snapshot.current_timestamp, inner.current_timestamp); + assert_eq!(expected_snapshot.current_batch, inner.current_batch); + assert_eq!(expected_snapshot.current_miniblock, inner.current_miniblock); + assert_eq!( + expected_snapshot.current_miniblock_hash, + inner.current_miniblock_hash + ); + assert_eq!(expected_snapshot.l1_gas_price, inner.l1_gas_price); + assert_eq!( + expected_snapshot.tx_results.keys().collect_vec(), + inner.tx_results.keys().collect_vec() + ); + assert_eq!(expected_snapshot.blocks, inner.blocks); + assert_eq!(expected_snapshot.block_hashes, inner.block_hashes); + assert_eq!(expected_snapshot.filters, inner.filters); + assert_eq!( + expected_snapshot.impersonated_accounts, + inner.impersonated_accounts + ); + assert_eq!(expected_snapshot.rich_accounts, inner.rich_accounts); + assert_eq!(expected_snapshot.previous_states, inner.previous_states); + assert_eq!(expected_snapshot.raw_storage, storage.raw_storage); + assert_eq!(expected_snapshot.value_read_cache, storage.value_read_cache); + assert_eq!( + expected_snapshot.factory_dep_cache, + storage.factory_dep_cache + ); + } + + #[tokio::test] + async fn test_get_transaction_by_block_hash_and_index_returns_none_for_invalid_block_hash() { + let node = InMemoryNode::::default(); + let input_tx_hash = H256::repeat_byte(0x01); + let (input_block_hash, _) = testing::apply_tx(&node, input_tx_hash); + let invalid_block_hash = H256::repeat_byte(0xab); + assert_ne!(input_block_hash, invalid_block_hash); + + let result = node + .get_transaction_by_block_hash_and_index(invalid_block_hash, U64::from(0)) + .await + .expect("failed fetching transaction"); + + assert!(result.is_none()); + } + + #[tokio::test] + async fn test_get_transaction_by_block_hash_and_index_returns_none_for_invalid_index() { + let node = InMemoryNode::::default(); + let input_tx_hash = H256::repeat_byte(0x01); + let (input_block_hash, _) = testing::apply_tx(&node, input_tx_hash); + + let result = node + .get_transaction_by_block_hash_and_index(input_block_hash, U64::from(10)) + .await + .expect("failed fetching transaction"); + + assert!(result.is_none()); + } + + #[tokio::test] + async fn test_get_transaction_by_block_hash_and_index_returns_transaction_for_valid_input() { + let node = InMemoryNode::::default(); + let input_tx_hash = H256::repeat_byte(0x01); + let (input_block_hash, _) = testing::apply_tx(&node, input_tx_hash); + + let actual_tx = node + .get_transaction_by_block_hash_and_index(input_block_hash, U64::from(0)) + .await + .expect("failed fetching transaction") + .expect("no transaction"); + + assert_eq!(input_tx_hash, actual_tx.hash); + } + + #[tokio::test] + async fn test_get_transaction_by_block_hash_and_index_fetches_full_transaction_for_hash_from_fork( + ) { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let input_block_hash = H256::repeat_byte(0x01); + let input_tx_hash = H256::repeat_byte(0x02); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getTransactionByHash", + "params": [ + format!("{:#x}", input_tx_hash), + ], + }), + TransactionResponseBuilder::new() + .set_hash(input_tx_hash) + .set_block_hash(input_block_hash) + .set_block_number(U64::from(1)) + .build(), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + // store the block info with just the tx hash invariant + { + let inner = node.get_inner(); + let mut writer = inner.write().unwrap(); + writer.blocks.insert( + input_block_hash, + Block { + transactions: vec![TransactionVariant::Hash(input_tx_hash)], + ..Default::default() + }, + ); + } + + let actual_tx = node + .get_transaction_by_block_hash_and_index(input_block_hash, U64::from(0)) + .await + .expect("failed fetching transaction") + .expect("no transaction"); + + assert_eq!(input_tx_hash, actual_tx.hash); + assert_eq!(Some(U64::from(1)), actual_tx.block_number); + } + + #[tokio::test] + async fn test_get_transaction_by_block_hash_and_index_fetches_from_fork_if_block_missing() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let input_block_hash = H256::repeat_byte(0x01); + let input_tx_hash = H256::repeat_byte(0x02); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getTransactionByBlockHashAndIndex", + "params": [ + format!("{:#x}", input_block_hash), + "0x1" + ], + }), + TransactionResponseBuilder::new() + .set_hash(input_tx_hash) + .set_block_hash(input_block_hash) + .set_block_number(U64::from(100)) + .build(), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_tx = node + .get_transaction_by_block_hash_and_index(input_block_hash, U64::from(1)) + .await + .expect("failed fetching transaction") + .expect("no transaction"); + + assert_eq!(input_tx_hash, actual_tx.hash); + assert_eq!(Some(U64::from(100)), actual_tx.block_number); + } + + #[tokio::test] + async fn test_get_transaction_by_block_number_and_index_returns_none_for_invalid_block_number() + { + let node = InMemoryNode::::default(); + let input_tx_hash = H256::repeat_byte(0x01); + let (input_block_hash, _) = testing::apply_tx(&node, input_tx_hash); + let invalid_block_hash = H256::repeat_byte(0xab); + assert_ne!(input_block_hash, invalid_block_hash); + + let result = node + .get_transaction_by_block_number_and_index( + BlockNumber::Number(U64::from(100)), + U64::from(0), + ) + .await + .expect("failed fetching transaction"); + + assert!(result.is_none()); + } + + #[tokio::test] + async fn test_get_transaction_by_block_number_and_index_returns_none_for_invalid_index() { + let node = InMemoryNode::::default(); + let input_tx_hash = H256::repeat_byte(0x01); + testing::apply_tx(&node, input_tx_hash); + + let result = node + .get_transaction_by_block_number_and_index(BlockNumber::Latest, U64::from(10)) + .await + .expect("failed fetching transaction"); + + assert!(result.is_none()); + } + + #[tokio::test] + async fn test_get_transaction_by_block_number_and_index_returns_transaction_for_valid_input() { + let node = InMemoryNode::::default(); + let input_tx_hash = H256::repeat_byte(0x01); + let (_, input_block_number) = testing::apply_tx(&node, input_tx_hash); + + let actual_tx = node + .get_transaction_by_block_number_and_index( + BlockNumber::Number(input_block_number), + U64::from(0), + ) + .await + .expect("failed fetching transaction") + .expect("no transaction"); + + assert_eq!(input_tx_hash, actual_tx.hash); + } + + #[tokio::test] + async fn test_get_transaction_by_block_number_and_index_fetches_full_transaction_for_hash_from_fork( + ) { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let input_block_hash = H256::repeat_byte(0x01); + let input_block_number = U64::from(100); + let input_tx_hash = H256::repeat_byte(0x02); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getTransactionByHash", + "params": [ + format!("{:#x}", input_tx_hash), + ], + }), + TransactionResponseBuilder::new() + .set_hash(input_tx_hash) + .set_block_hash(input_block_hash) + .set_block_number(input_block_number) + .build(), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + // store the block info with just the tx hash invariant + { + let inner = node.get_inner(); + let mut writer = inner.write().unwrap(); + writer + .block_hashes + .insert(input_block_number.as_u64(), input_block_hash); + writer.blocks.insert( + input_block_hash, + Block { + transactions: vec![TransactionVariant::Hash(input_tx_hash)], + ..Default::default() + }, + ); + } + + let actual_tx = node + .get_transaction_by_block_number_and_index( + BlockNumber::Number(input_block_number), + U64::from(0), + ) + .await + .expect("failed fetching transaction") + .expect("no transaction"); + + assert_eq!(input_tx_hash, actual_tx.hash); + assert_eq!(Some(input_block_number), actual_tx.block_number); + } + + #[tokio::test] + async fn test_get_transaction_by_block_number_and_index_fetches_from_fork_if_block_missing() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let input_block_hash = H256::repeat_byte(0x01); + let input_block_number = U64::from(100); + let input_tx_hash = H256::repeat_byte(0x02); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_getTransactionByBlockNumberAndIndex", + "params": [ + format!("{:#x}", input_block_number), + "0x1" + ], + }), + TransactionResponseBuilder::new() + .set_hash(input_tx_hash) + .set_block_hash(input_block_hash) + .set_block_number(input_block_number) + .build(), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_tx = node + .get_transaction_by_block_number_and_index( + BlockNumber::Number(input_block_number), + U64::from(1), + ) + .await + .expect("failed fetching transaction") + .expect("no transaction"); + + assert_eq!(input_tx_hash, actual_tx.hash); + assert_eq!(Some(input_block_number), actual_tx.block_number); + } + + #[tokio::test] + async fn test_protocol_version_returns_currently_supported_version() { + let node = InMemoryNode::::default(); + + let expected_version = String::from(PROTOCOL_VERSION); + let actual_version = node + .protocol_version() + .await + .expect("failed creating filter"); + + assert_eq!(expected_version, actual_version); + } +} diff --git a/.test-node-subtree/src/node/evm.rs b/.test-node-subtree/src/node/evm.rs new file mode 100644 index 00000000..71af8c19 --- /dev/null +++ b/.test-node-subtree/src/node/evm.rs @@ -0,0 +1,68 @@ +use zksync_basic_types::U64; +use zksync_core::api_server::web3::backend_jsonrpc::error::into_jsrpc_error; +use zksync_web3_decl::error::Web3Error; + +use crate::{ + fork::ForkSource, + namespaces::{EvmNamespaceT, RpcResult}, + node::InMemoryNode, + utils::IntoBoxedFuture, +}; + +impl EvmNamespaceT + for InMemoryNode +{ + fn increase_time(&self, time_delta_seconds: u64) -> RpcResult { + self.increase_time(time_delta_seconds) + .map_err(|err| { + tracing::error!("failed increasing time: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } + + fn evm_mine(&self) -> RpcResult { + self.mine_block() + .map_err(|err| { + tracing::error!("failed mining block: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } + + fn set_next_block_timestamp(&self, timestamp: u64) -> RpcResult { + self.set_next_block_timestamp(timestamp) + .map_err(|err| { + tracing::error!("failed setting time for next timestamp: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } + + fn set_time(&self, time: u64) -> RpcResult { + self.set_time(time) + .map_err(|err| { + tracing::error!("failed setting time: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } + + fn snapshot(&self) -> RpcResult { + self.snapshot() + .map_err(|err| { + tracing::error!("failed creating snapshot: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } + + fn revert_snapshot(&self, snapshot_id: U64) -> RpcResult { + self.revert_snapshot(snapshot_id) + .map_err(|err| { + tracing::error!("failed reverting snapshot: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } +} diff --git a/.test-node-subtree/src/node/hardhat.rs b/.test-node-subtree/src/node/hardhat.rs new file mode 100644 index 00000000..23abda98 --- /dev/null +++ b/.test-node-subtree/src/node/hardhat.rs @@ -0,0 +1,68 @@ +use zksync_basic_types::{Address, U256, U64}; +use zksync_core::api_server::web3::backend_jsonrpc::error::into_jsrpc_error; +use zksync_web3_decl::error::Web3Error; + +use crate::{ + fork::ForkSource, + namespaces::{HardhatNamespaceT, RpcResult}, + node::InMemoryNode, + utils::IntoBoxedFuture, +}; + +impl HardhatNamespaceT + for InMemoryNode +{ + fn set_balance(&self, address: Address, balance: U256) -> RpcResult { + self.set_balance(address, balance) + .map_err(|err| { + tracing::error!("failed setting balance : {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } + + fn set_nonce(&self, address: Address, balance: U256) -> RpcResult { + self.set_nonce(address, balance) + .map_err(|err| { + tracing::error!("failed setting nonce: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } + + fn hardhat_mine(&self, num_blocks: Option, interval: Option) -> RpcResult { + self.mine_blocks(num_blocks, interval) + .map_err(|err| { + tracing::error!("failed mining blocks: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } + + fn impersonate_account(&self, address: Address) -> RpcResult { + self.impersonate_account(address) + .map_err(|err| { + tracing::error!("failed impersonating account: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } + + fn stop_impersonating_account(&self, address: Address) -> RpcResult { + InMemoryNode::::stop_impersonating_account(self, address) + .map_err(|err| { + tracing::error!("failed stopping to impersonate account: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } + + fn set_code(&self, address: Address, code: Vec) -> RpcResult<()> { + self.set_code(address, code) + .map_err(|err| { + tracing::error!("failed setting code: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .into_boxed_future() + } +} diff --git a/.test-node-subtree/src/node/in_memory.rs b/.test-node-subtree/src/node/in_memory.rs new file mode 100644 index 00000000..cef482c8 --- /dev/null +++ b/.test-node-subtree/src/node/in_memory.rs @@ -0,0 +1,1919 @@ +//! In-memory node, that supports forking other networks. +use crate::{ + bootloader_debug::{BootloaderDebug, BootloaderDebugTracer}, + console_log::ConsoleLogHandler, + deps::{storage_view::StorageView, InMemoryStorage}, + filters::EthFilters, + fork::{ForkDetails, ForkSource, ForkStorage}, + formatter, + node::storage_logs::print_storage_logs_details, + observability::Observability, + system_contracts::{self, SystemContracts}, + utils::{ + adjust_l1_gas_price_for_tx, bytecode_to_factory_dep, create_debug_output, to_human_size, + }, +}; +use clap::Parser; +use colored::Colorize; +use core::fmt::Display; +use indexmap::IndexMap; +use once_cell::sync::OnceCell; +use std::{ + cmp::{self}, + collections::{HashMap, HashSet}, + str::FromStr, + sync::{Arc, RwLock}, +}; + +use multivm::{ + interface::{ + ExecutionResult, L1BatchEnv, L2BlockEnv, SystemEnv, TxExecutionMode, VmExecutionMode, + VmExecutionResultAndLogs, VmInterface, + }, + vm_latest::L2Block, +}; +use multivm::{ + tracers::CallTracer, + vm_latest::HistoryDisabled, + vm_latest::{ + constants::{BLOCK_GAS_LIMIT, BLOCK_OVERHEAD_PUBDATA, MAX_PUBDATA_PER_BLOCK}, + utils::{ + fee::derive_base_fee_and_gas_per_pubdata, + l2_blocks::load_last_l2_block, + overhead::{derive_overhead, OverheadCoefficients}, + }, + ToTracerPointer, TracerPointer, Vm, + }, +}; +use zksync_basic_types::{ + web3::signing::keccak256, AccountTreeId, Address, Bytes, L1BatchNumber, MiniblockNumber, H160, + H256, U256, U64, +}; +use zksync_contracts::BaseSystemContracts; +use zksync_core::api_server::web3::backend_jsonrpc::error::into_jsrpc_error; +use zksync_state::{ReadStorage, StoragePtr, WriteStorage}; +use zksync_types::{ + api::{Block, DebugCall, Log, TransactionReceipt, TransactionVariant}, + block::{unpack_block_info, MiniblockHasher}, + fee::Fee, + get_nonce_key, + l2::L2Tx, + l2::TransactionType, + utils::{decompose_full_nonce, nonces_to_full_nonce, storage_key_for_eth_balance}, + vm_trace::Call, + PackedEthSignature, StorageKey, StorageLogQueryType, StorageValue, Transaction, + ACCOUNT_CODE_STORAGE_ADDRESS, EIP_712_TX_TYPE, MAX_GAS_PER_PUBDATA_BYTE, MAX_L2_TX_GAS_LIMIT, + SYSTEM_CONTEXT_ADDRESS, SYSTEM_CONTEXT_BLOCK_INFO_POSITION, +}; +use zksync_utils::{ + bytecode::{compress_bytecode, hash_bytecode}, + h256_to_account_address, h256_to_u256, u256_to_h256, +}; +use zksync_web3_decl::error::Web3Error; + +/// Max possible size of an ABI encoded tx (in bytes). +pub const MAX_TX_SIZE: usize = 1_000_000; +/// Timestamp of the first block (if not running in fork mode). +pub const NON_FORK_FIRST_BLOCK_TIMESTAMP: u64 = 1_000; +/// Network ID we use for the test node. +pub const TEST_NODE_NETWORK_ID: u32 = 260; +/// L1 Gas Price. +pub const L1_GAS_PRICE: u64 = 50_000_000_000; +/// L2 Gas Price (0.25 gwei). +pub const L2_GAS_PRICE: u64 = 250_000_000; +/// L1 Gas Price Scale Factor for gas estimation. +pub const ESTIMATE_GAS_L1_GAS_PRICE_SCALE_FACTOR: f64 = 1.2; +/// The max possible number of gas that `eth_estimateGas` is allowed to overestimate. +pub const ESTIMATE_GAS_PUBLISH_BYTE_OVERHEAD: u32 = 100; +/// Acceptable gas overestimation limit. +pub const ESTIMATE_GAS_ACCEPTABLE_OVERESTIMATION: u32 = 1_000; +/// The factor by which to scale the gasLimit. +pub const ESTIMATE_GAS_SCALE_FACTOR: f32 = 1.3; +/// The maximum number of previous blocks to store the state for. +pub const MAX_PREVIOUS_STATES: u16 = 128; +/// The zks protocol version. +pub const PROTOCOL_VERSION: &str = "zks/1"; + +pub fn compute_hash(block_number: u64, tx_hash: H256) -> H256 { + let digest = [&block_number.to_be_bytes()[..], tx_hash.as_bytes()].concat(); + H256(keccak256(&digest)) +} + +pub fn create_empty_block( + block_number: u64, + timestamp: u64, + batch: u32, + parent_block_hash: Option, +) -> Block { + let hash = compute_hash(block_number, H256::zero()); + let parent_hash = parent_block_hash.unwrap_or(if block_number == 0 { + H256::zero() + } else { + compute_hash(block_number - 1, H256::zero()) + }); + Block { + hash, + parent_hash, + number: U64::from(block_number), + timestamp: U256::from(timestamp), + l1_batch_number: Some(U64::from(batch)), + transactions: vec![], + gas_used: U256::from(0), + gas_limit: U256::from(BLOCK_GAS_LIMIT), + ..Default::default() + } +} + +/// Information about the executed transaction. +#[derive(Debug, Clone)] +pub struct TxExecutionInfo { + pub tx: L2Tx, + // Batch number where transaction was executed. + pub batch_number: u32, + pub miniblock_number: u64, + pub result: VmExecutionResultAndLogs, +} + +#[derive(Debug, Default, clap::Parser, Clone, clap::ValueEnum, PartialEq, Eq)] +pub enum ShowCalls { + #[default] + None, + User, + System, + All, +} + +impl FromStr for ShowCalls { + type Err = String; + + fn from_str(s: &str) -> Result { + match s.to_lowercase().as_ref() { + "none" => Ok(ShowCalls::None), + "user" => Ok(ShowCalls::User), + "system" => Ok(ShowCalls::System), + "all" => Ok(ShowCalls::All), + _ => Err(format!( + "Unknown ShowCalls value {} - expected one of none|user|system|all.", + s + )), + } + } +} + +impl Display for ShowCalls { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> Result<(), std::fmt::Error> { + write!(f, "{:?}", self) + } +} + +#[derive(Debug, Default, Parser, Clone, clap::ValueEnum, PartialEq, Eq)] +pub enum ShowStorageLogs { + #[default] + None, + Read, + Write, + Paid, + All, +} + +impl FromStr for ShowStorageLogs { + type Err = String; + + fn from_str(s: &str) -> Result { + match s.to_lowercase().as_ref() { + "none" => Ok(ShowStorageLogs::None), + "read" => Ok(ShowStorageLogs::Read), + "write" => Ok(ShowStorageLogs::Write), + "paid" => Ok(ShowStorageLogs::Paid), + "all" => Ok(ShowStorageLogs::All), + _ => Err(format!( + "Unknown ShowStorageLogs value {} - expected one of none|read|write|paid|all.", + s + )), + } + } +} + +impl Display for ShowStorageLogs { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> Result<(), std::fmt::Error> { + write!(f, "{:?}", self) + } +} + +#[derive(Debug, Default, Parser, Clone, clap::ValueEnum, PartialEq, Eq)] +pub enum ShowVMDetails { + #[default] + None, + All, +} + +impl FromStr for ShowVMDetails { + type Err = String; + + fn from_str(s: &str) -> Result { + match s.to_lowercase().as_ref() { + "none" => Ok(ShowVMDetails::None), + "all" => Ok(ShowVMDetails::All), + _ => Err(format!( + "Unknown ShowVMDetails value {} - expected one of none|all.", + s + )), + } + } +} + +impl Display for ShowVMDetails { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> Result<(), std::fmt::Error> { + write!(f, "{:?}", self) + } +} + +#[derive(Debug, Default, Parser, Clone, clap::ValueEnum, PartialEq, Eq)] +pub enum ShowGasDetails { + #[default] + None, + All, +} + +impl FromStr for ShowGasDetails { + type Err = String; + + fn from_str(s: &str) -> Result { + match s.to_lowercase().as_ref() { + "none" => Ok(ShowGasDetails::None), + "all" => Ok(ShowGasDetails::All), + _ => Err(format!( + "Unknown ShowGasDetails value {} - expected one of none|all.", + s + )), + } + } +} + +impl Display for ShowGasDetails { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> Result<(), std::fmt::Error> { + write!(f, "{:?}", self) + } +} + +#[derive(Debug, Clone)] +pub struct TransactionResult { + pub info: TxExecutionInfo, + pub receipt: TransactionReceipt, + pub debug: DebugCall, +} + +impl TransactionResult { + /// Returns the debug information for the transaction. + /// If `only_top` is true - will only return the top level call. + pub fn debug_info(&self, only_top: bool) -> DebugCall { + let calls = if only_top { + vec![] + } else { + self.debug.calls.clone() + }; + DebugCall { + calls, + ..self.debug.clone() + } + } +} + +/// Helper struct for InMemoryNode. +/// S - is the Source of the Fork. +#[derive(Clone)] +pub struct InMemoryNodeInner { + /// The latest timestamp that was already generated. + /// Next block will be current_timestamp + 1 + pub current_timestamp: u64, + /// The latest batch number that was already generated. + /// Next block will be current_batch + 1 + pub current_batch: u32, + /// The latest miniblock number that was already generated. + /// Next transaction will go to the block current_miniblock + 1 + pub current_miniblock: u64, + /// The latest miniblock hash. + pub current_miniblock_hash: H256, + pub l1_gas_price: u64, + // Map from transaction to details about the exeuction + pub tx_results: HashMap, + // Map from block hash to information about the block. + pub blocks: HashMap>, + // Map from block number to a block hash. + pub block_hashes: HashMap, + // Map from filter_id to the eth filter + pub filters: EthFilters, + // Underlying storage + pub fork_storage: ForkStorage, + // Debug level information. + pub show_calls: ShowCalls, + // Displays storage logs. + pub show_storage_logs: ShowStorageLogs, + // Displays VM details. + pub show_vm_details: ShowVMDetails, + // Gas details information. + pub show_gas_details: ShowGasDetails, + // If true - will contact openchain to resolve the ABI to function names. + pub resolve_hashes: bool, + pub console_log_handler: ConsoleLogHandler, + pub system_contracts: SystemContracts, + pub impersonated_accounts: HashSet
, + pub rich_accounts: HashSet, + /// Keeps track of historical states indexed via block hash. Limited to [MAX_PREVIOUS_STATES]. + pub previous_states: IndexMap>, + /// An optional handle to the observability stack + pub observability: Option, +} + +type L2TxResult = ( + HashMap, + VmExecutionResultAndLogs, + Vec, + Block, + HashMap>, + BlockContext, +); + +impl InMemoryNodeInner { + /// Create [L1BatchEnv] to be used in the VM. + /// + /// We compute l1/l2 block details from storage to support fork testing, where the storage + /// can be updated mid execution and no longer matches with the initial node's state. + /// The L1 & L2 timestamps are also compared with node's timestamp to ensure it always increases monotonically. + pub fn create_l1_batch_env( + &self, + storage: StoragePtr, + ) -> (L1BatchEnv, BlockContext) { + let (last_l1_block_num, last_l1_block_ts) = load_last_l1_batch(storage.clone()) + .map(|(num, ts)| (num as u32, ts)) + .unwrap_or_else(|| (self.current_batch, self.current_timestamp)); + let last_l2_block = load_last_l2_block(storage.clone()).unwrap_or_else(|| L2Block { + number: self.current_miniblock as u32, + hash: MiniblockHasher::legacy_hash(MiniblockNumber(self.current_miniblock as u32)), + timestamp: self.current_timestamp, + }); + let latest_timestamp = std::cmp::max( + std::cmp::max(last_l1_block_ts, last_l2_block.timestamp), + self.current_timestamp, + ); + + let block_ctx = BlockContext::from_current( + last_l1_block_num, + last_l2_block.number as u64, + latest_timestamp, + ) + .new_batch(); + + let batch_env = L1BatchEnv { + // TODO: set the previous batch hash properly (take from fork, when forking, and from local storage, when this is not the first block). + previous_batch_hash: None, + number: L1BatchNumber::from(block_ctx.batch), + timestamp: block_ctx.timestamp, + l1_gas_price: self.l1_gas_price, + fair_l2_gas_price: L2_GAS_PRICE, + fee_account: H160::zero(), + enforced_base_fee: None, + first_l2_block: L2BlockEnv { + // the 'current_miniblock' contains the block that was already produced. + // So the next one should be one higher. + number: block_ctx.miniblock as u32, + timestamp: block_ctx.timestamp, + prev_block_hash: last_l2_block.hash, + // This is only used during zksyncEra block timestamp/number transition. + // In case of starting a new network, it doesn't matter. + // In theory , when forking mainnet, we should match this value + // to the value that was set in the node at that time - but AFAIK + // we don't have any API for this - so this might result in slightly + // incorrect replays of transacions during the migration period, that + // depend on block number or timestamp. + max_virtual_blocks_to_create: 1, + }, + }; + + (batch_env, block_ctx) + } + + pub fn create_system_env( + &self, + base_system_contracts: BaseSystemContracts, + execution_mode: TxExecutionMode, + ) -> SystemEnv { + SystemEnv { + zk_porter_available: false, + // TODO: when forking, we could consider taking the protocol version id from the fork itself. + version: zksync_types::ProtocolVersionId::latest(), + base_system_smart_contracts: base_system_contracts, + gas_limit: BLOCK_GAS_LIMIT, + execution_mode, + default_validation_computational_gas_limit: BLOCK_GAS_LIMIT, + chain_id: self.fork_storage.chain_id, + } + } + + /// Estimates the gas required for a given call request. + /// + /// # Arguments + /// + /// * `req` - A `CallRequest` struct representing the call request to estimate gas for. + /// + /// # Returns + /// + /// A `Result` with a `Fee` representing the estimated gas related data. + pub fn estimate_gas_impl( + &self, + req: zksync_types::transaction_request::CallRequest, + ) -> jsonrpc_core::Result { + let mut request_with_gas_per_pubdata_overridden = req; + + if let Some(ref mut eip712_meta) = request_with_gas_per_pubdata_overridden.eip712_meta { + if eip712_meta.gas_per_pubdata == U256::zero() { + eip712_meta.gas_per_pubdata = MAX_GAS_PER_PUBDATA_BYTE.into(); + } + } + + let is_eip712 = request_with_gas_per_pubdata_overridden + .eip712_meta + .is_some(); + + let mut l2_tx = + match L2Tx::from_request(request_with_gas_per_pubdata_overridden.into(), MAX_TX_SIZE) { + Ok(tx) => tx, + Err(e) => { + let error = Web3Error::SerializationError(e); + return Err(into_jsrpc_error(error)); + } + }; + + let tx: Transaction = l2_tx.clone().into(); + let fair_l2_gas_price = L2_GAS_PRICE; + + // Calculate Adjusted L1 Price + let l1_gas_price = { + let current_l1_gas_price = + ((self.l1_gas_price as f64) * ESTIMATE_GAS_L1_GAS_PRICE_SCALE_FACTOR) as u64; + + // In order for execution to pass smoothly, we need to ensure that block's required gasPerPubdata will be + // <= to the one in the transaction itself. + adjust_l1_gas_price_for_tx( + current_l1_gas_price, + L2_GAS_PRICE, + tx.gas_per_pubdata_byte_limit(), + ) + }; + + let (base_fee, gas_per_pubdata_byte) = + derive_base_fee_and_gas_per_pubdata(l1_gas_price, fair_l2_gas_price); + + // Properly format signature + if l2_tx.common_data.signature.is_empty() { + l2_tx.common_data.signature = vec![0u8; 65]; + l2_tx.common_data.signature[64] = 27; + } + + // The user may not include the proper transaction type during the estimation of + // the gas fee. However, it is needed for the bootloader checks to pass properly. + if is_eip712 { + l2_tx.common_data.transaction_type = TransactionType::EIP712Transaction; + } + + l2_tx.common_data.fee.gas_per_pubdata_limit = MAX_GAS_PER_PUBDATA_BYTE.into(); + l2_tx.common_data.fee.max_fee_per_gas = base_fee.into(); + l2_tx.common_data.fee.max_priority_fee_per_gas = base_fee.into(); + + let mut storage_view = StorageView::new(&self.fork_storage); + + // Calculate gas_for_bytecodes_pubdata + let pubdata_for_factory_deps = l2_tx + .execute + .factory_deps + .as_deref() + .unwrap_or_default() + .iter() + .map(|bytecode| { + if storage_view.is_bytecode_known(&hash_bytecode(bytecode)) { + return 0; + } + + let length = if let Ok(compressed) = compress_bytecode(bytecode) { + compressed.len() + } else { + bytecode.len() + }; + length as u32 + ESTIMATE_GAS_PUBLISH_BYTE_OVERHEAD + }) + .sum::(); + + if pubdata_for_factory_deps > MAX_PUBDATA_PER_BLOCK { + return Err(into_jsrpc_error(Web3Error::SubmitTransactionError( + "exceeds limit for published pubdata".into(), + Default::default(), + ))); + } + + let gas_for_bytecodes_pubdata: u32 = + pubdata_for_factory_deps * (gas_per_pubdata_byte as u32); + + let storage = storage_view.into_rc_ptr(); + + let execution_mode = TxExecutionMode::EstimateFee; + let (mut batch_env, _) = self.create_l1_batch_env(storage.clone()); + batch_env.l1_gas_price = l1_gas_price; + let impersonating = self + .impersonated_accounts + .contains(&l2_tx.common_data.initiator_address); + let system_env = self.create_system_env( + self.system_contracts + .contracts_for_fee_estimate(impersonating) + .clone(), + execution_mode, + ); + + // We are using binary search to find the minimal values of gas_limit under which the transaction succeeds + let mut lower_bound = 0; + let mut upper_bound = MAX_L2_TX_GAS_LIMIT as u32; + let mut attempt_count = 1; + + tracing::trace!("Starting gas estimation loop"); + while lower_bound + ESTIMATE_GAS_ACCEPTABLE_OVERESTIMATION < upper_bound { + let mid = (lower_bound + upper_bound) / 2; + tracing::trace!( + "Attempt {} (lower_bound: {}, upper_bound: {}, mid: {})", + attempt_count, + lower_bound, + upper_bound, + mid + ); + let try_gas_limit = gas_for_bytecodes_pubdata + mid; + + let estimate_gas_result = InMemoryNodeInner::estimate_gas_step( + l2_tx.clone(), + gas_per_pubdata_byte, + try_gas_limit, + l1_gas_price, + batch_env.clone(), + system_env.clone(), + &self.fork_storage, + ); + + if estimate_gas_result.result.is_failed() { + tracing::trace!("Attempt {} FAILED", attempt_count); + lower_bound = mid + 1; + } else { + tracing::trace!("Attempt {} SUCCEEDED", attempt_count); + upper_bound = mid; + } + attempt_count += 1; + } + + tracing::trace!("Gas Estimation Values:"); + tracing::trace!(" Final upper_bound: {}", upper_bound); + tracing::trace!(" ESTIMATE_GAS_SCALE_FACTOR: {}", ESTIMATE_GAS_SCALE_FACTOR); + tracing::trace!(" MAX_L2_TX_GAS_LIMIT: {}", MAX_L2_TX_GAS_LIMIT); + let tx_body_gas_limit = cmp::min( + MAX_L2_TX_GAS_LIMIT as u32, + (upper_bound as f32 * ESTIMATE_GAS_SCALE_FACTOR) as u32, + ); + let suggested_gas_limit = tx_body_gas_limit + gas_for_bytecodes_pubdata; + + let estimate_gas_result = InMemoryNodeInner::estimate_gas_step( + l2_tx.clone(), + gas_per_pubdata_byte, + suggested_gas_limit, + l1_gas_price, + batch_env, + system_env, + &self.fork_storage, + ); + + let coefficients = OverheadCoefficients::from_tx_type(EIP_712_TX_TYPE); + let overhead: u32 = derive_overhead( + suggested_gas_limit, + gas_per_pubdata_byte as u32, + tx.encoding_len(), + coefficients, + ); + + match estimate_gas_result.result { + ExecutionResult::Revert { output } => { + tracing::info!("{}", format!("Unable to estimate gas for the request with our suggested gas limit of {}. The transaction is most likely unexecutable. Breakdown of estimation:", suggested_gas_limit + overhead).red()); + tracing::info!( + "{}", + format!( + "\tEstimated transaction body gas cost: {}", + tx_body_gas_limit + ) + .red() + ); + tracing::info!( + "{}", + format!("\tGas for pubdata: {}", gas_for_bytecodes_pubdata).red() + ); + tracing::info!("{}", format!("\tOverhead: {}", overhead).red()); + let message = output.to_string(); + let pretty_message = format!( + "execution reverted{}{}", + if message.is_empty() { "" } else { ": " }, + message + ); + let data = output.encoded_data(); + tracing::info!("{}", pretty_message.on_red()); + Err(into_jsrpc_error(Web3Error::SubmitTransactionError( + pretty_message, + data, + ))) + } + ExecutionResult::Halt { reason } => { + tracing::info!("{}", format!("Unable to estimate gas for the request with our suggested gas limit of {}. The transaction is most likely unexecutable. Breakdown of estimation:", suggested_gas_limit + overhead).red()); + tracing::info!( + "{}", + format!( + "\tEstimated transaction body gas cost: {}", + tx_body_gas_limit + ) + .red() + ); + tracing::info!( + "{}", + format!("\tGas for pubdata: {}", gas_for_bytecodes_pubdata).red() + ); + tracing::info!("{}", format!("\tOverhead: {}", overhead).red()); + let message = reason.to_string(); + let pretty_message = format!( + "execution reverted{}{}", + if message.is_empty() { "" } else { ": " }, + message + ); + + tracing::info!("{}", pretty_message.on_red()); + Err(into_jsrpc_error(Web3Error::SubmitTransactionError( + pretty_message, + vec![], + ))) + } + ExecutionResult::Success { .. } => { + let full_gas_limit = match tx_body_gas_limit + .overflowing_add(gas_for_bytecodes_pubdata + overhead) + { + (value, false) => value, + (_, true) => { + tracing::info!("{}", "Overflow when calculating gas estimation. We've exceeded the block gas limit by summing the following values:".red()); + tracing::info!( + "{}", + format!( + "\tEstimated transaction body gas cost: {}", + tx_body_gas_limit + ) + .red() + ); + tracing::info!( + "{}", + format!("\tGas for pubdata: {}", gas_for_bytecodes_pubdata).red() + ); + tracing::info!("{}", format!("\tOverhead: {}", overhead).red()); + return Err(into_jsrpc_error(Web3Error::SubmitTransactionError( + "exceeds block gas limit".into(), + Default::default(), + ))); + } + }; + + tracing::trace!("Gas Estimation Results"); + tracing::trace!(" tx_body_gas_limit: {}", tx_body_gas_limit); + tracing::trace!(" gas_for_bytecodes_pubdata: {}", gas_for_bytecodes_pubdata); + tracing::trace!(" overhead: {}", overhead); + tracing::trace!(" full_gas_limit: {}", full_gas_limit); + let fee = Fee { + max_fee_per_gas: base_fee.into(), + max_priority_fee_per_gas: 0u32.into(), + gas_limit: full_gas_limit.into(), + gas_per_pubdata_limit: gas_per_pubdata_byte.into(), + }; + Ok(fee) + } + } + } + + /// Runs fee estimation against a sandbox vm with the given gas_limit. + #[allow(clippy::too_many_arguments)] + fn estimate_gas_step( + mut l2_tx: L2Tx, + gas_per_pubdata_byte: u64, + tx_gas_limit: u32, + l1_gas_price: u64, + mut batch_env: L1BatchEnv, + system_env: SystemEnv, + fork_storage: &ForkStorage, + ) -> VmExecutionResultAndLogs { + let tx: Transaction = l2_tx.clone().into(); + let l1_gas_price = + adjust_l1_gas_price_for_tx(l1_gas_price, L2_GAS_PRICE, tx.gas_per_pubdata_byte_limit()); + + let coefficients = OverheadCoefficients::from_tx_type(EIP_712_TX_TYPE); + // Set gas_limit for transaction + let gas_limit_with_overhead = tx_gas_limit + + derive_overhead( + tx_gas_limit, + gas_per_pubdata_byte as u32, + tx.encoding_len(), + coefficients, + ); + l2_tx.common_data.fee.gas_limit = gas_limit_with_overhead.into(); + + let storage = StorageView::new(fork_storage).into_rc_ptr(); + + // The nonce needs to be updated + let nonce = l2_tx.nonce(); + let nonce_key = get_nonce_key(&l2_tx.initiator_account()); + let full_nonce = storage.borrow_mut().read_value(&nonce_key); + let (_, deployment_nonce) = decompose_full_nonce(h256_to_u256(full_nonce)); + let enforced_full_nonce = nonces_to_full_nonce(U256::from(nonce.0), deployment_nonce); + storage + .borrow_mut() + .set_value(nonce_key, u256_to_h256(enforced_full_nonce)); + + // We need to explicitly put enough balance into the account of the users + let payer = l2_tx.payer(); + let balance_key = storage_key_for_eth_balance(&payer); + let mut current_balance = h256_to_u256(storage.borrow_mut().read_value(&balance_key)); + let added_balance = l2_tx.common_data.fee.gas_limit * l2_tx.common_data.fee.max_fee_per_gas; + current_balance += added_balance; + storage + .borrow_mut() + .set_value(balance_key, u256_to_h256(current_balance)); + + batch_env.l1_gas_price = l1_gas_price; + + let mut vm: Vm<_, HistoryDisabled> = Vm::new(batch_env, system_env, storage.clone()); + + let tx: Transaction = l2_tx.into(); + vm.push_transaction(tx); + + vm.execute(VmExecutionMode::OneTx) + } + + /// Sets the `impersonated_account` field of the node. + /// This field is used to override the `tx.initiator_account` field of the transaction in the `run_l2_tx` method. + pub fn set_impersonated_account(&mut self, address: Address) -> bool { + self.impersonated_accounts.insert(address) + } + + /// Clears the `impersonated_account` field of the node. + pub fn stop_impersonating_account(&mut self, address: Address) -> bool { + self.impersonated_accounts.remove(&address) + } + + /// Archives the current state for later queries. + pub fn archive_state(&mut self) -> Result<(), String> { + if self.previous_states.len() > MAX_PREVIOUS_STATES as usize { + if let Some(entry) = self.previous_states.shift_remove_index(0) { + tracing::debug!("removing archived state for previous block {:#x}", entry.0); + } + } + tracing::debug!( + "archiving state for {:#x} #{}", + self.current_miniblock_hash, + self.current_miniblock + ); + self.previous_states.insert( + self.current_miniblock_hash, + self.fork_storage + .inner + .read() + .map_err(|err| err.to_string())? + .raw_storage + .state + .clone(), + ); + + Ok(()) + } + + /// Creates a [Snapshot] of the current state of the node. + pub fn snapshot(&self) -> Result { + let storage = self + .fork_storage + .inner + .read() + .map_err(|err| format!("failed acquiring read lock on storage: {:?}", err))?; + + Ok(Snapshot { + current_timestamp: self.current_timestamp, + current_batch: self.current_batch, + current_miniblock: self.current_miniblock, + current_miniblock_hash: self.current_miniblock_hash, + l1_gas_price: self.l1_gas_price, + tx_results: self.tx_results.clone(), + blocks: self.blocks.clone(), + block_hashes: self.block_hashes.clone(), + filters: self.filters.clone(), + impersonated_accounts: self.impersonated_accounts.clone(), + rich_accounts: self.rich_accounts.clone(), + previous_states: self.previous_states.clone(), + raw_storage: storage.raw_storage.clone(), + value_read_cache: storage.value_read_cache.clone(), + factory_dep_cache: storage.factory_dep_cache.clone(), + }) + } + + /// Restores a previously created [Snapshot] of the node. + pub fn restore_snapshot(&mut self, snapshot: Snapshot) -> Result<(), String> { + let mut storage = self + .fork_storage + .inner + .write() + .map_err(|err| format!("failed acquiring write lock on storage: {:?}", err))?; + + self.current_timestamp = snapshot.current_timestamp; + self.current_batch = snapshot.current_batch; + self.current_miniblock = snapshot.current_miniblock; + self.current_miniblock_hash = snapshot.current_miniblock_hash; + self.l1_gas_price = snapshot.l1_gas_price; + self.tx_results = snapshot.tx_results; + self.blocks = snapshot.blocks; + self.block_hashes = snapshot.block_hashes; + self.filters = snapshot.filters; + self.impersonated_accounts = snapshot.impersonated_accounts; + self.rich_accounts = snapshot.rich_accounts; + self.previous_states = snapshot.previous_states; + storage.raw_storage = snapshot.raw_storage; + storage.value_read_cache = snapshot.value_read_cache; + storage.factory_dep_cache = snapshot.factory_dep_cache; + + Ok(()) + } +} + +/// Creates a restorable snapshot for the [InMemoryNodeInner]. The snapshot contains all the necessary +/// data required to restore the [InMemoryNodeInner] state to a previous point in time. +#[derive(Debug, Clone)] +pub struct Snapshot { + pub(crate) current_timestamp: u64, + pub(crate) current_batch: u32, + pub(crate) current_miniblock: u64, + pub(crate) current_miniblock_hash: H256, + pub(crate) l1_gas_price: u64, + pub(crate) tx_results: HashMap, + pub(crate) blocks: HashMap>, + pub(crate) block_hashes: HashMap, + pub(crate) filters: EthFilters, + pub(crate) impersonated_accounts: HashSet
, + pub(crate) rich_accounts: HashSet, + pub(crate) previous_states: IndexMap>, + pub(crate) raw_storage: InMemoryStorage, + pub(crate) value_read_cache: HashMap, + pub(crate) factory_dep_cache: HashMap>>, +} + +/// Defines the configuration parameters for the [InMemoryNode]. +#[derive(Default, Debug, Clone)] +pub struct InMemoryNodeConfig { + pub show_calls: ShowCalls, + pub show_storage_logs: ShowStorageLogs, + pub show_vm_details: ShowVMDetails, + pub show_gas_details: ShowGasDetails, + pub resolve_hashes: bool, + pub system_contracts_options: system_contracts::Options, +} + +/// In-memory node, that can be used for local & unit testing. +/// It also supports the option of forking testnet/mainnet. +/// All contents are removed when object is destroyed. +#[derive(Clone)] +pub struct InMemoryNode { + /// A thread safe reference to the [InMemoryNodeInner]. + inner: Arc>>, + /// List of snapshots of the [InMemoryNodeInner]. This is bounded at runtime by [MAX_SNAPSHOTS]. + pub(crate) snapshots: Arc>>, +} + +fn contract_address_from_tx_result(execution_result: &VmExecutionResultAndLogs) -> Option { + for query in execution_result.logs.storage_logs.iter().rev() { + if query.log_type == StorageLogQueryType::InitialWrite + && query.log_query.address == ACCOUNT_CODE_STORAGE_ADDRESS + { + return Some(h256_to_account_address(&u256_to_h256(query.log_query.key))); + } + } + None +} + +impl Default for InMemoryNode { + fn default() -> Self { + InMemoryNode::new(None, None, InMemoryNodeConfig::default()) + } +} + +impl InMemoryNode { + pub fn new( + fork: Option>, + observability: Option, + config: InMemoryNodeConfig, + ) -> Self { + let inner = if let Some(f) = &fork { + let mut block_hashes = HashMap::::new(); + block_hashes.insert(f.l2_block.number.as_u64(), f.l2_block.hash); + let mut blocks = HashMap::>::new(); + blocks.insert(f.l2_block.hash, f.l2_block.clone()); + + InMemoryNodeInner { + current_timestamp: f.block_timestamp, + current_batch: f.l1_block.0, + current_miniblock: f.l2_miniblock, + current_miniblock_hash: f.l2_miniblock_hash, + l1_gas_price: f.l1_gas_price, + tx_results: Default::default(), + blocks, + block_hashes, + filters: Default::default(), + fork_storage: ForkStorage::new(fork, &config.system_contracts_options), + show_calls: config.show_calls, + show_storage_logs: config.show_storage_logs, + show_vm_details: config.show_vm_details, + show_gas_details: config.show_gas_details, + resolve_hashes: config.resolve_hashes, + console_log_handler: ConsoleLogHandler::default(), + system_contracts: SystemContracts::from_options(&config.system_contracts_options), + impersonated_accounts: Default::default(), + rich_accounts: HashSet::new(), + previous_states: Default::default(), + observability, + } + } else { + let mut block_hashes = HashMap::::new(); + let block_hash = compute_hash(0, H256::zero()); + block_hashes.insert(0, block_hash); + let mut blocks = HashMap::>::new(); + blocks.insert( + block_hash, + create_empty_block(0, NON_FORK_FIRST_BLOCK_TIMESTAMP, 0, None), + ); + + InMemoryNodeInner { + current_timestamp: NON_FORK_FIRST_BLOCK_TIMESTAMP, + current_batch: 0, + current_miniblock: 0, + current_miniblock_hash: block_hash, + l1_gas_price: L1_GAS_PRICE, + tx_results: Default::default(), + blocks, + block_hashes, + filters: Default::default(), + fork_storage: ForkStorage::new(fork, &config.system_contracts_options), + show_calls: config.show_calls, + show_storage_logs: config.show_storage_logs, + show_vm_details: config.show_vm_details, + show_gas_details: config.show_gas_details, + resolve_hashes: config.resolve_hashes, + console_log_handler: ConsoleLogHandler::default(), + system_contracts: SystemContracts::from_options(&config.system_contracts_options), + impersonated_accounts: Default::default(), + rich_accounts: HashSet::new(), + previous_states: Default::default(), + observability, + } + }; + + InMemoryNode { + inner: Arc::new(RwLock::new(inner)), + snapshots: Default::default(), + } + } + + pub fn get_inner(&self) -> Arc>> { + self.inner.clone() + } + + /// Applies multiple transactions - but still one per L1 batch. + pub fn apply_txs(&self, txs: Vec) -> Result<(), String> { + tracing::info!("Running {:?} transactions (one per batch)", txs.len()); + + for tx in txs { + self.run_l2_tx(tx, TxExecutionMode::VerifyExecute)?; + } + + Ok(()) + } + + /// Adds a lot of tokens to a given account. + pub fn set_rich_account(&self, address: H160) { + let key = storage_key_for_eth_balance(&address); + + let mut inner = match self.inner.write() { + Ok(guard) => guard, + Err(e) => { + tracing::info!("Failed to acquire write lock: {}", e); + return; + } + }; + + let keys = { + let mut storage_view = StorageView::new(&inner.fork_storage); + storage_view.set_value(key, u256_to_h256(U256::from(10u128.pow(30)))); + storage_view.modified_storage_keys().clone() + }; + + for (key, value) in keys.iter() { + inner.fork_storage.set_value(*key, *value); + } + inner.rich_accounts.insert(address); + } + + /// Runs L2 'eth call' method - that doesn't commit to a block. + pub fn run_l2_call(&self, mut l2_tx: L2Tx) -> Result { + let execution_mode = TxExecutionMode::EthCall; + + let inner = self + .inner + .write() + .map_err(|e| format!("Failed to acquire write lock: {}", e))?; + + let storage = StorageView::new(&inner.fork_storage).into_rc_ptr(); + + let bootloader_code = inner.system_contracts.contracts_for_l2_call(); + + // init vm + + let (batch_env, _) = inner.create_l1_batch_env(storage.clone()); + let system_env = inner.create_system_env(bootloader_code.clone(), execution_mode); + + let mut vm: Vm<_, HistoryDisabled> = Vm::new(batch_env, system_env, storage.clone()); + + // We must inject *some* signature (otherwise bootloader code fails to generate hash). + if l2_tx.common_data.signature.is_empty() { + l2_tx.common_data.signature = PackedEthSignature::default().serialize_packed().into(); + } + + let tx: Transaction = l2_tx.into(); + vm.push_transaction(tx); + + let call_tracer_result = Arc::new(OnceCell::default()); + + let custom_tracer = CallTracer::new(call_tracer_result.clone()).into_tracer_pointer(); + + let tx_result = vm.inspect(custom_tracer.into(), VmExecutionMode::OneTx); + + let call_traces = Arc::try_unwrap(call_tracer_result) + .unwrap() + .take() + .unwrap_or_default(); + + match &tx_result.result { + ExecutionResult::Success { output } => { + tracing::info!("Call: {}", "SUCCESS".green()); + let output_bytes = zksync_basic_types::Bytes::from(output.clone()); + tracing::info!("Output: {}", serde_json::to_string(&output_bytes).unwrap()); + } + ExecutionResult::Revert { output } => { + tracing::info!("Call: {}: {}", "FAILED".red(), output); + } + ExecutionResult::Halt { reason } => { + tracing::info!("Call: {} {}", "HALTED".red(), reason) + } + }; + + tracing::info!("=== Console Logs: "); + for call in &call_traces { + inner.console_log_handler.handle_call_recursive(call); + } + + tracing::info!("=== Call traces:"); + for call in &call_traces { + formatter::print_call(call, 0, &inner.show_calls, inner.resolve_hashes); + } + + Ok(tx_result) + } + + fn display_detailed_gas_info( + &self, + bootloader_debug_result: Option<&eyre::Result>, + spent_on_pubdata: u32, + ) -> eyre::Result<(), String> { + if let Some(bootloader_result) = bootloader_debug_result { + let bootloader_debug = bootloader_result.clone()?; + + tracing::info!("┌─────────────────────────┐"); + tracing::info!("│ GAS DETAILS │"); + tracing::info!("└─────────────────────────┘"); + + // Total amount of gas (should match tx.gas_limit). + let total_gas_limit = bootloader_debug + .total_gas_limit_from_user + .saturating_sub(bootloader_debug.reserved_gas); + + let intrinsic_gas = total_gas_limit - bootloader_debug.gas_limit_after_intrinsic; + let gas_for_validation = + bootloader_debug.gas_limit_after_intrinsic - bootloader_debug.gas_after_validation; + + let gas_spent_on_compute = bootloader_debug.gas_spent_on_execution + - bootloader_debug.gas_spent_on_bytecode_preparation; + + let gas_used = intrinsic_gas + + gas_for_validation + + bootloader_debug.gas_spent_on_bytecode_preparation + + gas_spent_on_compute; + + tracing::info!( + "Gas - Limit: {} | Used: {} | Refunded: {}", + to_human_size(total_gas_limit), + to_human_size(gas_used), + to_human_size(bootloader_debug.refund_by_operator) + ); + + if bootloader_debug.total_gas_limit_from_user != total_gas_limit { + tracing::info!( + "{}", + format!( + " WARNING: user actually provided more gas {}, but system had a lower max limit.", + to_human_size(bootloader_debug.total_gas_limit_from_user) + ) + .yellow() + ); + } + if bootloader_debug.refund_computed != bootloader_debug.refund_by_operator { + tracing::info!( + "{}", + format!( + " WARNING: Refund by VM: {}, but operator refunded more: {}", + to_human_size(bootloader_debug.refund_computed), + to_human_size(bootloader_debug.refund_by_operator) + ) + .yellow() + ); + } + + if bootloader_debug.refund_computed + gas_used != total_gas_limit { + tracing::info!( + "{}", + format!( + " WARNING: Gas totals don't match. {} != {} , delta: {}", + to_human_size(bootloader_debug.refund_computed + gas_used), + to_human_size(total_gas_limit), + to_human_size( + total_gas_limit.abs_diff(bootloader_debug.refund_computed + gas_used) + ) + ) + .yellow() + ); + } + + let bytes_published = spent_on_pubdata / bootloader_debug.gas_per_pubdata.as_u32(); + + tracing::info!( + "During execution published {} bytes to L1, @{} each - in total {} gas", + to_human_size(bytes_published.into()), + to_human_size(bootloader_debug.gas_per_pubdata), + to_human_size(spent_on_pubdata.into()) + ); + + tracing::info!("Out of {} gas used, we spent:", to_human_size(gas_used)); + tracing::info!( + " {:>15} gas ({:>2}%) for transaction setup", + to_human_size(intrinsic_gas), + to_human_size(intrinsic_gas * 100 / gas_used) + ); + tracing::info!( + " {:>15} gas ({:>2}%) for bytecode preparation (decompression etc)", + to_human_size(bootloader_debug.gas_spent_on_bytecode_preparation), + to_human_size(bootloader_debug.gas_spent_on_bytecode_preparation * 100 / gas_used) + ); + tracing::info!( + " {:>15} gas ({:>2}%) for account validation", + to_human_size(gas_for_validation), + to_human_size(gas_for_validation * 100 / gas_used) + ); + tracing::info!( + " {:>15} gas ({:>2}%) for computations (opcodes)", + to_human_size(gas_spent_on_compute), + to_human_size(gas_spent_on_compute * 100 / gas_used) + ); + + tracing::info!(""); + tracing::info!(""); + tracing::info!( + "{}", + "=== Transaction setup cost breakdown ===".to_owned().bold(), + ); + + tracing::info!("Total cost: {}", to_human_size(intrinsic_gas).bold()); + tracing::info!( + " {:>15} gas ({:>2}%) fixed cost", + to_human_size(bootloader_debug.intrinsic_overhead), + to_human_size(bootloader_debug.intrinsic_overhead * 100 / intrinsic_gas) + ); + tracing::info!( + " {:>15} gas ({:>2}%) operator cost", + to_human_size(bootloader_debug.operator_overhead), + to_human_size(bootloader_debug.operator_overhead * 100 / intrinsic_gas) + ); + + tracing::info!(""); + tracing::info!( + " FYI: operator could have charged up to: {}, so you got {}% discount", + to_human_size(bootloader_debug.required_overhead), + to_human_size( + (bootloader_debug.required_overhead - bootloader_debug.operator_overhead) * 100 + / bootloader_debug.required_overhead + ) + ); + + let publish_block_l1_bytes = BLOCK_OVERHEAD_PUBDATA; + tracing::info!( + "Publishing full block costs the operator up to: {}, where {} is due to {} bytes published to L1", + to_human_size(bootloader_debug.total_overhead_for_block), + to_human_size(bootloader_debug.gas_per_pubdata * publish_block_l1_bytes), + to_human_size(publish_block_l1_bytes.into()) + ); + tracing::info!("Your transaction has contributed to filling up the block in the following way (we take the max contribution as the cost):"); + tracing::info!( + " Circuits overhead:{:>15} ({}% of the full block: {})", + to_human_size(bootloader_debug.overhead_for_circuits), + to_human_size( + bootloader_debug.overhead_for_circuits * 100 + / bootloader_debug.total_overhead_for_block + ), + to_human_size(bootloader_debug.total_overhead_for_block) + ); + tracing::info!( + " Length overhead: {:>15}", + to_human_size(bootloader_debug.overhead_for_length) + ); + tracing::info!( + " Slot overhead: {:>15}", + to_human_size(bootloader_debug.overhead_for_slot) + ); + Ok(()) + } else { + Err("Booloader tracer didn't finish.".to_owned()) + } + } + + // Validates L2 transaction + fn validate_tx(&self, tx: &L2Tx) -> Result<(), String> { + let max_gas = U256::from(u32::MAX); + if tx.common_data.fee.gas_limit > max_gas + || tx.common_data.fee.gas_per_pubdata_limit > max_gas + { + return Err("exceeds block gas limit".into()); + } + + if tx.common_data.fee.max_fee_per_gas < L2_GAS_PRICE.into() { + tracing::info!( + "Submitted Tx is Unexecutable {:?} because of MaxFeePerGasTooLow {}", + tx.hash(), + tx.common_data.fee.max_fee_per_gas + ); + return Err("block base fee higher than max fee per gas".into()); + } + + if tx.common_data.fee.max_fee_per_gas < tx.common_data.fee.max_priority_fee_per_gas { + tracing::info!( + "Submitted Tx is Unexecutable {:?} because of MaxPriorityFeeGreaterThanMaxFee {}", + tx.hash(), + tx.common_data.fee.max_fee_per_gas + ); + return Err("max priority fee per gas higher than max fee per gas".into()); + } + Ok(()) + } + + /// Executes the given L2 transaction and returns all the VM logs. + /// The bootloader can be omitted via specifying the `execute_bootloader` boolean. + /// This causes the VM to produce 1 L2 block per L1 block, instead of the usual 2 blocks per L1 block. + /// + /// **NOTE** + /// + /// This function must only rely on data populated initially via [ForkDetails]: + /// * [InMemoryNodeInner::current_timestamp] + /// * [InMemoryNodeInner::current_batch] + /// * [InMemoryNodeInner::current_miniblock] + /// * [InMemoryNodeInner::current_miniblock_hash] + /// * [InMemoryNodeInner::l1_gas_price] + /// + /// And must _NEVER_ rely on data updated in [InMemoryNodeInner] during previous runs: + /// (if used, they must never panic and/or have meaningful defaults) + /// * [InMemoryNodeInner::block_hashes] + /// * [InMemoryNodeInner::blocks] + /// * [InMemoryNodeInner::tx_results] + /// + /// This is because external users of the library may call this function to perform an isolated + /// VM operation (optionally without bootloader execution) with an external storage and get the results back. + /// So any data populated in [Self::run_l2_tx] will not be available for the next invocation. + pub fn run_l2_tx_raw( + &self, + l2_tx: L2Tx, + execution_mode: TxExecutionMode, + mut tracers: Vec< + TracerPointer>, multivm::vm_latest::HistoryDisabled>, + >, + execute_bootloader: bool, + ) -> Result { + let inner = self + .inner + .write() + .map_err(|e| format!("Failed to acquire write lock: {}", e))?; + + let storage = StorageView::new(inner.fork_storage.clone()).into_rc_ptr(); + + let (batch_env, block_ctx) = inner.create_l1_batch_env(storage.clone()); + + let bootloader_code = { + if inner + .impersonated_accounts + .contains(&l2_tx.common_data.initiator_address) + { + tracing::info!( + "🕵️ Executing tx from impersonated account {:?}", + l2_tx.common_data.initiator_address + ); + inner.system_contracts.contracts(execution_mode, true) + } else { + inner.system_contracts.contracts(execution_mode, false) + } + }; + let system_env = inner.create_system_env(bootloader_code.clone(), execution_mode); + + let mut vm: Vm<_, HistoryDisabled> = + Vm::new(batch_env.clone(), system_env, storage.clone()); + + let tx: Transaction = l2_tx.clone().into(); + + vm.push_transaction(tx.clone()); + + let call_tracer_result = Arc::new(OnceCell::default()); + let bootloader_debug_result = Arc::new(OnceCell::default()); + + tracers.push(CallTracer::new(call_tracer_result.clone()).into_tracer_pointer()); + tracers.push( + BootloaderDebugTracer { + result: bootloader_debug_result.clone(), + } + .into_tracer_pointer(), + ); + + let tx_result = vm.inspect(tracers.into(), VmExecutionMode::OneTx); + + let call_traces = call_tracer_result.get().unwrap(); + + let spent_on_pubdata = + tx_result.statistics.gas_used - tx_result.statistics.computational_gas_used; + + tracing::info!("┌─────────────────────────┐"); + tracing::info!("│ TRANSACTION SUMMARY │"); + tracing::info!("└─────────────────────────┘"); + + match &tx_result.result { + ExecutionResult::Success { .. } => tracing::info!("Transaction: {}", "SUCCESS".green()), + ExecutionResult::Revert { .. } => tracing::info!("Transaction: {}", "FAILED".red()), + ExecutionResult::Halt { .. } => tracing::info!("Transaction: {}", "HALTED".red()), + } + + tracing::info!("Initiator: {:?}", tx.initiator_account()); + tracing::info!("Payer: {:?}", tx.payer()); + tracing::info!( + "Gas - Limit: {} | Used: {} | Refunded: {}", + to_human_size(tx.gas_limit()), + to_human_size(tx.gas_limit() - tx_result.refunds.gas_refunded), + to_human_size(tx_result.refunds.gas_refunded.into()) + ); + + match inner.show_gas_details { + ShowGasDetails::None => tracing::info!( + "Use --show-gas-details flag or call config_setShowGasDetails to display more info" + ), + ShowGasDetails::All => { + if self + .display_detailed_gas_info(bootloader_debug_result.get(), spent_on_pubdata) + .is_err() + { + tracing::info!( + "{}", + "!!! FAILED TO GET DETAILED GAS INFO !!!".to_owned().red() + ); + } + } + } + + if inner.show_storage_logs != ShowStorageLogs::None { + print_storage_logs_details(&inner.show_storage_logs, &tx_result); + } + + if inner.show_vm_details != ShowVMDetails::None { + formatter::print_vm_details(&tx_result); + } + + tracing::info!(""); + tracing::info!("==== Console logs: "); + for call in call_traces { + inner.console_log_handler.handle_call_recursive(call); + } + tracing::info!(""); + let call_traces_count = if !call_traces.is_empty() { + // All calls/sub-calls are stored within the first call trace + call_traces[0].calls.len() + } else { + 0 + }; + tracing::info!( + "==== {} Use --show-calls flag or call config_setShowCalls to display more info.", + format!("{:?} call traces. ", call_traces_count).bold() + ); + + if inner.show_calls != ShowCalls::None { + for call in call_traces { + formatter::print_call(call, 0, &inner.show_calls, inner.resolve_hashes); + } + } + tracing::info!(""); + tracing::info!( + "==== {}", + format!("{} events", tx_result.logs.events.len()).bold() + ); + for event in &tx_result.logs.events { + formatter::print_event(event, inner.resolve_hashes); + } + + // The computed block hash here will be different than that in production. + let hash = compute_hash(block_ctx.miniblock, l2_tx.hash()); + + let mut transaction = zksync_types::api::Transaction::from(l2_tx); + transaction.block_hash = Some(inner.current_miniblock_hash); + transaction.block_number = Some(U64::from(inner.current_miniblock)); + + let parent_block_hash = inner + .block_hashes + .get(&(block_ctx.miniblock - 1)) + .cloned() + .unwrap_or_default(); + + let block = Block { + hash, + parent_hash: parent_block_hash, + number: U64::from(block_ctx.miniblock), + timestamp: U256::from(batch_env.timestamp), + l1_batch_number: Some(U64::from(batch_env.number.0)), + transactions: vec![TransactionVariant::Full(transaction)], + gas_used: U256::from(tx_result.statistics.gas_used), + gas_limit: U256::from(BLOCK_GAS_LIMIT), + ..Default::default() + }; + + let bytecodes: HashMap> = vm + .get_last_tx_compressed_bytecodes() + .iter() + .map(|b| bytecode_to_factory_dep(b.original.clone())) + .collect(); + if execute_bootloader { + vm.execute(VmExecutionMode::Bootloader); + } + + let modified_keys = storage.borrow().modified_storage_keys().clone(); + + Ok(( + modified_keys, + tx_result, + call_traces.clone(), + block, + bytecodes, + block_ctx, + )) + } + + /// Runs L2 transaction and commits it to a new block. + pub fn run_l2_tx(&self, l2_tx: L2Tx, execution_mode: TxExecutionMode) -> Result<(), String> { + let tx_hash = l2_tx.hash(); + + tracing::info!(""); + tracing::info!("Validating {}", format!("{:?}", tx_hash).bold()); + + match self.validate_tx(&l2_tx) { + Ok(_) => (), + Err(e) => { + return Err(e); + } + }; + + tracing::info!("Executing {}", format!("{:?}", tx_hash).bold()); + + { + let mut inner = self + .inner + .write() + .map_err(|e| format!("Failed to acquire write lock: {}", e))?; + inner.filters.notify_new_pending_transaction(tx_hash); + } + + let (keys, result, call_traces, block, bytecodes, block_ctx) = + self.run_l2_tx_raw(l2_tx.clone(), execution_mode, vec![], true)?; + + if let ExecutionResult::Halt { reason } = result.result { + // Halt means that something went really bad with the transaction execution (in most cases invalid signature, + // but it could also be bootloader panic etc). + // In such case, we should not persist the VM data, and we should pretend that transaction never existed. + return Err(format!("Transaction HALT: {}", reason)); + } + // Write all the mutated keys (storage slots). + let mut inner = self + .inner + .write() + .map_err(|e| format!("Failed to acquire write lock: {}", e))?; + for (key, value) in keys.iter() { + inner.fork_storage.set_value(*key, *value); + } + + // Write all the factory deps. + for (hash, code) in bytecodes.iter() { + inner.fork_storage.store_factory_dep( + u256_to_h256(*hash), + code.iter() + .flat_map(|entry| { + let mut bytes = vec![0u8; 32]; + entry.to_big_endian(&mut bytes); + bytes.to_vec() + }) + .collect(), + ) + } + + for (log_idx, event) in result.logs.events.iter().enumerate() { + inner.filters.notify_new_log( + &Log { + address: event.address, + topics: event.indexed_topics.clone(), + data: Bytes(event.value.clone()), + block_hash: Some(block.hash), + block_number: Some(block.number), + l1_batch_number: block.l1_batch_number, + transaction_hash: Some(tx_hash), + transaction_index: Some(U64::zero()), + log_index: Some(U256::from(log_idx)), + transaction_log_index: Some(U256::from(log_idx)), + log_type: None, + removed: Some(false), + }, + block.number, + ); + } + let tx_receipt = TransactionReceipt { + transaction_hash: tx_hash, + transaction_index: U64::from(0), + block_hash: Some(block.hash), + block_number: Some(block.number), + l1_batch_tx_index: None, + l1_batch_number: block.l1_batch_number, + from: l2_tx.initiator_account(), + to: Some(l2_tx.recipient_account()), + root: Some(H256::zero()), + cumulative_gas_used: Default::default(), + gas_used: Some(l2_tx.common_data.fee.gas_limit - result.refunds.gas_refunded), + contract_address: contract_address_from_tx_result(&result), + logs: result + .logs + .events + .iter() + .enumerate() + .map(|(log_idx, log)| Log { + address: log.address, + topics: log.indexed_topics.clone(), + data: Bytes(log.value.clone()), + block_hash: Some(block.hash), + block_number: Some(block.number), + l1_batch_number: block.l1_batch_number, + transaction_hash: Some(tx_hash), + transaction_index: Some(U64::zero()), + log_index: Some(U256::from(log_idx)), + transaction_log_index: Some(U256::from(log_idx)), + log_type: None, + removed: Some(false), + }) + .collect(), + l2_to_l1_logs: vec![], + status: Some(if result.result.is_failed() { + U64::from(0) + } else { + U64::from(1) + }), + effective_gas_price: Some(L2_GAS_PRICE.into()), + ..Default::default() + }; + let debug = create_debug_output(&l2_tx, &result, call_traces).expect("create debug output"); // OK to unwrap here as Halt is handled above + inner.tx_results.insert( + tx_hash, + TransactionResult { + info: TxExecutionInfo { + tx: l2_tx, + batch_number: block.l1_batch_number.unwrap_or_default().as_u32(), + miniblock_number: block.number.as_u64(), + result, + }, + receipt: tx_receipt, + debug, + }, + ); + + // With the introduction of 'l2 blocks' (and virtual blocks), + // we are adding one l2 block at the end of each batch (to handle things like remaining events etc). + // You can look at insert_fictive_l2_block function in VM to see how this fake block is inserted. + let block_ctx = block_ctx.new_block(); + let parent_block_hash = block.hash; + let empty_block_at_end_of_batch = create_empty_block( + block_ctx.miniblock, + block_ctx.timestamp, + block_ctx.batch, + Some(parent_block_hash), + ); + + inner.current_batch = inner.current_batch.saturating_add(1); + + for (i, block) in vec![block, empty_block_at_end_of_batch] + .into_iter() + .enumerate() + { + // archive current state before we produce new batch/blocks + if let Err(err) = inner.archive_state() { + tracing::error!( + "failed archiving state for block {}: {}", + inner.current_miniblock, + err + ); + } + + inner.current_miniblock = inner.current_miniblock.saturating_add(1); + inner.current_timestamp = inner.current_timestamp.saturating_add(1); + + let actual_l1_batch_number = block + .l1_batch_number + .expect("block must have a l1_batch_number"); + if actual_l1_batch_number.as_u32() != inner.current_batch { + panic!( + "expected next block to have batch_number {}, got {}", + inner.current_batch, + actual_l1_batch_number.as_u32() + ); + } + + if block.number.as_u64() != inner.current_miniblock { + panic!( + "expected next block to have miniblock {}, got {} | {i}", + inner.current_miniblock, + block.number.as_u64() + ); + } + + if block.timestamp.as_u64() != inner.current_timestamp { + panic!( + "expected next block to have timestamp {}, got {} | {i}", + inner.current_timestamp, + block.timestamp.as_u64() + ); + } + + let block_hash = block.hash; + inner.current_miniblock_hash = block_hash; + inner.block_hashes.insert(block.number.as_u64(), block.hash); + inner.blocks.insert(block.hash, block); + inner.filters.notify_new_block(block_hash); + } + + Ok(()) + } +} + +/// Keeps track of a block's batch number, miniblock number and timestamp. +/// Useful for keeping track of the current context when creating multiple blocks. +#[derive(Debug, Clone, Default)] +pub struct BlockContext { + pub batch: u32, + pub miniblock: u64, + pub timestamp: u64, +} + +impl BlockContext { + /// Create the current instance that represents the latest block. + pub fn from_current(batch: u32, miniblock: u64, timestamp: u64) -> Self { + Self { + batch, + miniblock, + timestamp, + } + } + + /// Create the next batch instance that has all parameters incremented by `1`. + pub fn new_batch(&self) -> Self { + Self { + batch: self.batch.saturating_add(1), + miniblock: self.miniblock.saturating_add(1), + timestamp: self.timestamp.saturating_add(1), + } + } + + /// Create the next batch instance that uses the same batch number, and has all other parameters incremented by `1`. + pub fn new_block(&self) -> BlockContext { + Self { + batch: self.batch, + miniblock: self.miniblock.saturating_add(1), + timestamp: self.timestamp.saturating_add(1), + } + } +} + +#[cfg(test)] +mod tests { + use ethabi::{Token, Uint}; + use zksync_basic_types::Nonce; + use zksync_types::utils::deployed_address_create; + + use super::*; + use crate::{ + http_fork_source::HttpForkSource, node::InMemoryNode, system_contracts::Options, testing, + }; + + #[tokio::test] + async fn test_run_l2_tx_validates_tx_gas_limit_too_high() { + let node = InMemoryNode::::default(); + let tx = testing::TransactionBuilder::new() + .set_gas_limit(U256::from(u32::MAX) + 1) + .build(); + node.set_rich_account(tx.common_data.initiator_address); + + let result = node.run_l2_tx(tx, TxExecutionMode::VerifyExecute); + + assert_eq!(result.err(), Some("exceeds block gas limit".into())); + } + + #[tokio::test] + async fn test_run_l2_tx_validates_tx_max_fee_per_gas_too_low() { + let node = InMemoryNode::::default(); + let tx = testing::TransactionBuilder::new() + .set_max_fee_per_gas(U256::from(250_000_000 - 1)) + .build(); + node.set_rich_account(tx.common_data.initiator_address); + + let result = node.run_l2_tx(tx, TxExecutionMode::VerifyExecute); + + assert_eq!( + result.err(), + Some("block base fee higher than max fee per gas".into()) + ); + } + + #[tokio::test] + async fn test_run_l2_tx_validates_tx_max_priority_fee_per_gas_higher_than_max_fee_per_gas() { + let node = InMemoryNode::::default(); + let tx = testing::TransactionBuilder::new() + .set_max_priority_fee_per_gas(U256::from(250_000_000 + 1)) + .build(); + node.set_rich_account(tx.common_data.initiator_address); + + let result = node.run_l2_tx(tx, TxExecutionMode::VerifyExecute); + + assert_eq!( + result.err(), + Some("max priority fee per gas higher than max fee per gas".into()) + ); + } + + #[tokio::test] + async fn test_create_empty_block_creates_genesis_block_with_hash_and_zero_parent_hash() { + let first_block = create_empty_block::(0, 1000, 1, None); + + assert_eq!(first_block.hash, compute_hash(0, H256::zero())); + assert_eq!(first_block.parent_hash, H256::zero()); + } + + #[tokio::test] + async fn test_create_empty_block_creates_block_with_parent_hash_link_to_prev_block() { + let first_block = create_empty_block::(0, 1000, 1, None); + let second_block = create_empty_block::(1, 1000, 1, None); + + assert_eq!(second_block.parent_hash, first_block.hash); + } + + #[tokio::test] + async fn test_create_empty_block_creates_block_with_parent_hash_link_to_provided_parent_hash() { + let first_block = create_empty_block::( + 0, + 1000, + 1, + Some(compute_hash(123, H256::zero())), + ); + let second_block = + create_empty_block::(1, 1000, 1, Some(first_block.hash)); + + assert_eq!(first_block.parent_hash, compute_hash(123, H256::zero())); + assert_eq!(second_block.parent_hash, first_block.hash); + } + + #[tokio::test] + async fn test_run_l2_tx_raw_does_not_panic_on_external_storage_call() { + // Perform a transaction to get storage to an intermediate state + let node = InMemoryNode::::default(); + let tx = testing::TransactionBuilder::new().build(); + node.set_rich_account(tx.common_data.initiator_address); + node.run_l2_tx(tx, TxExecutionMode::VerifyExecute).unwrap(); + let external_storage = node.inner.read().unwrap().fork_storage.clone(); + + // Execute next transaction using a fresh in-memory node and the external fork storage + let mock_db = testing::ExternalStorage { + raw_storage: external_storage.inner.read().unwrap().raw_storage.clone(), + }; + let node = InMemoryNode::new( + Some(ForkDetails { + fork_source: &mock_db, + l1_block: L1BatchNumber(1), + l2_block: Block::default(), + l2_miniblock: 2, + l2_miniblock_hash: Default::default(), + block_timestamp: 1002, + overwrite_chain_id: None, + l1_gas_price: 1000, + }), + None, + Default::default(), + ); + + node.run_l2_tx_raw( + testing::TransactionBuilder::new().build(), + TxExecutionMode::VerifyExecute, + vec![], + true, + ) + .expect("transaction must pass with external storage"); + } + + #[tokio::test] + async fn test_transact_returns_data_in_built_in_without_security_mode() { + let node = InMemoryNode::::new( + None, + None, + InMemoryNodeConfig { + system_contracts_options: Options::BuiltInWithoutSecurity, + ..Default::default() + }, + ); + + let private_key = H256::repeat_byte(0xef); + let from_account = zksync_types::PackedEthSignature::address_from_private_key(&private_key) + .expect("failed generating address"); + node.set_rich_account(from_account); + + let deployed_address = deployed_address_create(from_account, U256::zero()); + testing::deploy_contract( + &node, + H256::repeat_byte(0x1), + private_key, + hex::decode(testing::STORAGE_CONTRACT_BYTECODE).unwrap(), + None, + Nonce(0), + ); + + let mut tx = L2Tx::new_signed( + deployed_address, + hex::decode("bbf55335").unwrap(), // keccak selector for "transact_retrieve1()" + Nonce(1), + Fee { + gas_limit: U256::from(815563), + max_fee_per_gas: U256::from(250_000_000), + max_priority_fee_per_gas: U256::from(250_000_000), + gas_per_pubdata_limit: U256::from(20000), + }, + U256::from(0), + zksync_basic_types::L2ChainId::from(260), + &private_key, + None, + Default::default(), + ) + .expect("failed signing tx"); + tx.common_data.transaction_type = TransactionType::LegacyTransaction; + tx.set_input(vec![], H256::repeat_byte(0x2)); + let (_, result, ..) = node + .run_l2_tx_raw(tx, TxExecutionMode::VerifyExecute, vec![], true) + .expect("failed tx"); + + match result.result { + ExecutionResult::Success { output } => { + let actual = testing::decode_tx_result(&output, ethabi::ParamType::Uint(256)); + let expected = Token::Uint(Uint::from(1024u64)); + assert_eq!(expected, actual, "invalid result"); + } + _ => panic!("invalid result {:?}", result.result), + } + } +} + +pub fn load_last_l1_batch(storage: StoragePtr) -> Option<(u64, u64)> { + // Get block number and timestamp + let current_l1_batch_info_key = StorageKey::new( + AccountTreeId::new(SYSTEM_CONTEXT_ADDRESS), + SYSTEM_CONTEXT_BLOCK_INFO_POSITION, + ); + let mut storage_ptr = storage.borrow_mut(); + let current_l1_batch_info = storage_ptr.read_value(¤t_l1_batch_info_key); + let (batch_number, batch_timestamp) = unpack_block_info(h256_to_u256(current_l1_batch_info)); + let block_number = batch_number as u32; + if block_number == 0 { + // The block does not exist yet + return None; + } + Some((batch_number, batch_timestamp)) +} diff --git a/.test-node-subtree/src/node/in_memory_ext.rs b/.test-node-subtree/src/node/in_memory_ext.rs new file mode 100644 index 00000000..90e5395b --- /dev/null +++ b/.test-node-subtree/src/node/in_memory_ext.rs @@ -0,0 +1,901 @@ +use anyhow::anyhow; +use zksync_basic_types::{Address, U256, U64}; +use zksync_state::ReadStorage; +use zksync_types::{ + get_code_key, get_nonce_key, + utils::{decompose_full_nonce, nonces_to_full_nonce, storage_key_for_eth_balance}, +}; +use zksync_utils::{h256_to_u256, u256_to_h256}; + +use crate::{ + fork::ForkSource, + node::InMemoryNode, + utils::{self, bytecode_to_factory_dep}, +}; + +type Result = anyhow::Result; + +/// The maximum number of [Snapshot]s to store. Each snapshot represents the node state +/// and can be used to revert the node to an earlier point in time. +const MAX_SNAPSHOTS: u8 = 100; + +impl InMemoryNode { + /// Increase the current timestamp for the node + /// + /// # Parameters + /// - `time_delta`: The number of seconds to increase time by + /// + /// # Returns + /// The applied time delta to `current_timestamp` value for the InMemoryNodeInner. + pub fn increase_time(&self, time_delta_seconds: u64) -> Result { + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .map(|mut writer| { + if time_delta_seconds == 0 { + return time_delta_seconds; + } + + let time_delta = time_delta_seconds.saturating_mul(1000); + writer.current_timestamp = writer.current_timestamp.saturating_add(time_delta); + time_delta_seconds + }) + } + + /// Set the current timestamp for the node. The timestamp must be in future. + /// + /// # Parameters + /// - `timestamp`: The timestamp to set the time to + /// + /// # Returns + /// The new timestamp value for the InMemoryNodeInner. + pub fn set_next_block_timestamp(&self, timestamp: u64) -> Result { + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .and_then(|mut writer| { + if timestamp < writer.current_timestamp { + Err(anyhow!( + "timestamp ({}) must be greater than current timestamp ({})", + timestamp, + writer.current_timestamp + )) + } else { + writer.current_timestamp = timestamp; + Ok(timestamp) + } + }) + } + + /// Set the current timestamp for the node. + /// Warning: This will allow you to move backwards in time, which may cause new blocks to appear to be + /// mined before old blocks. This will result in an invalid state. + /// + /// # Parameters + /// - `time`: The timestamp to set the time to + /// + /// # Returns + /// The difference between the `current_timestamp` and the new timestamp for the InMemoryNodeInner. + pub fn set_time(&self, time: u64) -> Result { + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .map(|mut writer| { + let time_diff = (time as i128).saturating_sub(writer.current_timestamp as i128); + writer.current_timestamp = time; + time_diff + }) + } + + /// Force a single block to be mined. + /// + /// Will mine an empty block (containing zero transactions) + /// + /// # Returns + /// The string "0x0". + pub fn mine_block(&self) -> Result { + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .map(|mut writer| { + utils::mine_empty_blocks(&mut writer, 1, 1000); + tracing::info!("👷 Mined block #{}", writer.current_miniblock); + "0x0".to_string() + }) + } + + /// Snapshot the state of the blockchain at the current block. Takes no parameters. Returns the id of the snapshot + /// that was created. A snapshot can only be reverted once. After a successful evm_revert, the same snapshot id cannot + /// be used again. Consider creating a new snapshot after each evm_revert if you need to revert to the same + /// point multiple times. + /// + /// # Returns + /// The `U64` identifier for this snapshot. + pub fn snapshot(&self) -> Result { + let snapshots = self.snapshots.clone(); + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .and_then(|writer| { + // validate max snapshots + snapshots + .read() + .map_err(|err| anyhow!("failed acquiring read lock for snapshot: {:?}", err)) + .and_then(|snapshots| { + if snapshots.len() >= MAX_SNAPSHOTS as usize { + return Err(anyhow!( + "maximum number of '{}' snapshots exceeded", + MAX_SNAPSHOTS + )); + } + + Ok(()) + })?; + + // snapshot the node + let snapshot = writer.snapshot().map_err(|err| anyhow!("{}", err))?; + snapshots + .write() + .map(|mut snapshots| { + snapshots.push(snapshot); + tracing::info!("Created snapshot '{}'", snapshots.len()); + snapshots.len() + }) + .map_err(|err| anyhow!("failed storing snapshot: {:?}", err)) + .map(U64::from) + }) + } + + /// Revert the state of the blockchain to a previous snapshot. Takes a single parameter, + /// which is the snapshot id to revert to. This deletes the given snapshot, as well as any snapshots + /// taken after (e.g.: reverting to id 0x1 will delete snapshots with ids 0x1, 0x2, etc.) + /// + /// # Parameters + /// - `snapshot_id`: The snapshot id to revert. + /// + /// # Returns + /// `true` if a snapshot was reverted, otherwise `false`. + pub fn revert_snapshot(&self, snapshot_id: U64) -> Result { + let snapshots = self.snapshots.clone(); + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .and_then(|mut writer| { + let mut snapshots = snapshots.write().map_err(|err| { + anyhow!("failed acquiring read lock for snapshots: {:?}", err) + })?; + let snapshot_id_index = snapshot_id.as_usize().saturating_sub(1); + if snapshot_id_index >= snapshots.len() { + return Err(anyhow!("no snapshot exists for the id '{}'", snapshot_id)); + } + + // remove all snapshots following the index and use the first snapshot for restore + let selected_snapshot = snapshots + .drain(snapshot_id_index..) + .next() + .expect("unexpected failure, value must exist"); + + tracing::info!("Reverting node to snapshot '{snapshot_id:?}'"); + writer + .restore_snapshot(selected_snapshot) + .map(|_| { + tracing::info!("Reverting node to snapshot '{snapshot_id:?}'"); + true + }) + .map_err(|err| anyhow!("{}", err)) + }) + } + + pub fn set_balance(&self, address: Address, balance: U256) -> Result { + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .map(|mut writer| { + let balance_key = storage_key_for_eth_balance(&address); + writer + .fork_storage + .set_value(balance_key, u256_to_h256(balance)); + tracing::info!( + "👷 Balance for address {:?} has been manually set to {} Wei", + address, + balance + ); + true + }) + } + + pub fn set_nonce(&self, address: Address, nonce: U256) -> Result { + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .and_then(|mut writer| { + let nonce_key = get_nonce_key(&address); + let full_nonce = writer.fork_storage.read_value(&nonce_key); + let (mut account_nonce, mut deployment_nonce) = + decompose_full_nonce(h256_to_u256(full_nonce)); + if account_nonce >= nonce { + return Err(anyhow!( + "Account Nonce is already set to a higher value ({}, requested {})", + account_nonce, + nonce + )); + } + account_nonce = nonce; + if deployment_nonce >= nonce { + return Err(anyhow!( + "Deployment Nonce is already set to a higher value ({}, requested {})", + deployment_nonce, + nonce + )); + } + deployment_nonce = nonce; + let enforced_full_nonce = nonces_to_full_nonce(account_nonce, deployment_nonce); + tracing::info!( + "👷 Nonces for address {:?} have been set to {}", + address, + nonce + ); + writer + .fork_storage + .set_value(nonce_key, u256_to_h256(enforced_full_nonce)); + Ok(true) + }) + } + + pub fn mine_blocks(&self, num_blocks: Option, interval: Option) -> Result { + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .and_then(|mut writer| { + let num_blocks = num_blocks.unwrap_or_else(|| U64::from(1)); + let interval_ms = interval + .unwrap_or_else(|| U64::from(1)) + .saturating_mul(1_000.into()); + if num_blocks.is_zero() { + return Err(anyhow!( + "Number of blocks must be greater than 0".to_string(), + )); + } + utils::mine_empty_blocks(&mut writer, num_blocks.as_u64(), interval_ms.as_u64()); + tracing::info!("👷 Mined {} blocks", num_blocks); + + Ok(true) + }) + } + + pub fn impersonate_account(&self, address: Address) -> Result { + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .map(|mut writer| { + if writer.set_impersonated_account(address) { + tracing::info!("🕵️ Account {:?} has been impersonated", address); + true + } else { + tracing::info!("🕵️ Account {:?} was already impersonated", address); + false + } + }) + } + + pub fn stop_impersonating_account(&self, address: Address) -> Result { + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .map(|mut writer| { + if writer.stop_impersonating_account(address) { + tracing::info!("🕵️ Stopped impersonating account {:?}", address); + true + } else { + tracing::info!( + "🕵️ Account {:?} was not impersonated, nothing to stop", + address + ); + false + } + }) + } + + pub fn set_code(&self, address: Address, code: Vec) -> Result<()> { + self.get_inner() + .write() + .map_err(|err| anyhow!("failed acquiring lock: {:?}", err)) + .map(|mut writer| { + let code_key = get_code_key(&address); + tracing::info!("set code for address {address:#x}"); + let (hash, code) = bytecode_to_factory_dep(code); + let hash = u256_to_h256(hash); + writer.fork_storage.store_factory_dep( + hash, + code.iter() + .flat_map(|entry| { + let mut bytes = vec![0u8; 32]; + entry.to_big_endian(&mut bytes); + bytes.to_vec() + }) + .collect(), + ); + writer.fork_storage.set_value(code_key, hash); + }) + } +} + +#[cfg(test)] +mod tests { + use super::*; + use crate::{http_fork_source::HttpForkSource, node::InMemoryNode}; + use std::str::FromStr; + use zksync_basic_types::{Nonce, H256}; + use zksync_core::api_server::web3::backend_jsonrpc::namespaces::eth::EthNamespaceT; + use zksync_types::{api::BlockNumber, fee::Fee, l2::L2Tx, PackedEthSignature}; + + #[tokio::test] + async fn test_set_balance() { + let address = Address::from_str("0x36615Cf349d7F6344891B1e7CA7C72883F5dc049").unwrap(); + let node = InMemoryNode::::default(); + + let balance_before = node.get_balance(address, None).await.unwrap(); + + let result = node.set_balance(address, U256::from(1337)).unwrap(); + assert!(result); + + let balance_after = node.get_balance(address, None).await.unwrap(); + assert_eq!(balance_after, U256::from(1337)); + assert_ne!(balance_before, balance_after); + } + + #[tokio::test] + async fn test_set_nonce() { + let address = Address::from_str("0x36615Cf349d7F6344891B1e7CA7C72883F5dc049").unwrap(); + let node = InMemoryNode::::default(); + + let nonce_before = node.get_transaction_count(address, None).await.unwrap(); + + let result = node.set_nonce(address, U256::from(1337)).unwrap(); + assert!(result); + + let nonce_after = node.get_transaction_count(address, None).await.unwrap(); + assert_eq!(nonce_after, U256::from(1337)); + assert_ne!(nonce_before, nonce_after); + + // setting nonce lower than the current one should fail + let result = node.set_nonce(address, U256::from(1336)); + assert!(result.is_err()); + } + + #[tokio::test] + async fn test_mine_blocks_default() { + let node = InMemoryNode::::default(); + + let start_block = node + .get_block_by_number(zksync_types::api::BlockNumber::Latest, false) + .await + .unwrap() + .expect("block exists"); + + // test with defaults + let result = node.mine_blocks(None, None).expect("mine_blocks"); + assert!(result); + + let current_block = node + .get_block_by_number(zksync_types::api::BlockNumber::Latest, false) + .await + .unwrap() + .expect("block exists"); + + assert_eq!(start_block.number + 1, current_block.number); + assert_eq!(start_block.timestamp + 1, current_block.timestamp); + let result = node.mine_blocks(None, None).expect("mine_blocks"); + assert!(result); + + let current_block = node + .get_block_by_number(zksync_types::api::BlockNumber::Latest, false) + .await + .unwrap() + .expect("block exists"); + + assert_eq!(start_block.number + 2, current_block.number); + assert_eq!(start_block.timestamp + 2, current_block.timestamp); + } + + #[tokio::test] + async fn test_mine_blocks() { + let node = InMemoryNode::::default(); + + let start_block = node + .get_block_by_number(zksync_types::api::BlockNumber::Latest, false) + .await + .unwrap() + .expect("block exists"); + + let num_blocks = 5; + let interval = 3; + let start_timestamp = start_block.timestamp + 1; + + let result = node + .mine_blocks(Some(U64::from(num_blocks)), Some(U64::from(interval))) + .expect("mine blocks"); + assert!(result); + + for i in 0..num_blocks { + let current_block = node + .get_block_by_number(BlockNumber::Number(start_block.number + i + 1), false) + .await + .unwrap() + .expect("block exists"); + assert_eq!(start_block.number + i + 1, current_block.number); + assert_eq!( + start_timestamp + i * interval * 1_000, + current_block.timestamp + ); + } + } + + #[tokio::test] + async fn test_impersonate_account() { + let node = InMemoryNode::::default(); + let to_impersonate = + Address::from_str("0xd8da6bf26964af9d7eed9e03e53415d37aa96045").unwrap(); + + // give impersonated account some balance + let result = node.set_balance(to_impersonate, U256::exp10(18)).unwrap(); + assert!(result); + + // construct a tx + let mut tx = L2Tx::new( + Address::random(), + vec![], + Nonce(0), + Fee { + gas_limit: U256::from(1_000_000), + max_fee_per_gas: U256::from(250_000_000), + max_priority_fee_per_gas: U256::from(250_000_000), + gas_per_pubdata_limit: U256::from(20000), + }, + to_impersonate, + U256::one(), + None, + Default::default(), + ); + tx.set_input(vec![], H256::random()); + if tx.common_data.signature.is_empty() { + tx.common_data.signature = PackedEthSignature::default().serialize_packed().into(); + } + + // try to execute the tx- should fail without signature + assert!(node.apply_txs(vec![tx.clone()]).is_err()); + + // impersonate the account + let result = node + .impersonate_account(to_impersonate) + .expect("impersonate_account"); + + // result should be true + assert!(result); + + // impersonating the same account again should return false + let result = node + .impersonate_account(to_impersonate) + .expect("impersonate_account"); + assert!(!result); + + // execution should now succeed + assert!(node.apply_txs(vec![tx.clone()]).is_ok()); + + // stop impersonating the account + let result = node + .stop_impersonating_account(to_impersonate) + .expect("stop_impersonating_account"); + + // result should be true + assert!(result); + + // stop impersonating the same account again should return false + let result = node + .stop_impersonating_account(to_impersonate) + .expect("stop_impersonating_account"); + assert!(!result); + + // execution should now fail again + assert!(node.apply_txs(vec![tx]).is_err()); + } + + #[tokio::test] + async fn test_set_code() { + let address = Address::repeat_byte(0x1); + let node = InMemoryNode::::default(); + let new_code = vec![0x1u8; 32]; + + let code_before = node + .get_code(address, None) + .await + .expect("failed getting code") + .0; + assert_eq!(Vec::::default(), code_before); + + node.set_code(address, new_code.clone()) + .expect("failed setting code"); + + let code_after = node + .get_code(address, None) + .await + .expect("failed getting code") + .0; + assert_eq!(new_code, code_after); + } + + #[tokio::test] + async fn test_increase_time_zero_value() { + let node = InMemoryNode::::default(); + + let increase_value_seconds = 0u64; + let timestamp_before = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + let expected_response = increase_value_seconds; + + let actual_response = node + .increase_time(increase_value_seconds) + .expect("failed increasing timestamp"); + let timestamp_after = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + + assert_eq!(expected_response, actual_response, "erroneous response"); + assert_eq!( + increase_value_seconds.saturating_mul(1000u64), + timestamp_after.saturating_sub(timestamp_before), + "timestamp did not increase by the specified amount", + ); + } + + #[tokio::test] + async fn test_increase_time_max_value() { + let node = InMemoryNode::::default(); + + let increase_value_seconds = u64::MAX; + let timestamp_before = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + assert_ne!(0, timestamp_before, "initial timestamp must be non zero",); + let expected_response = increase_value_seconds; + + let actual_response = node + .increase_time(increase_value_seconds) + .expect("failed increasing timestamp"); + let timestamp_after = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + + assert_eq!(expected_response, actual_response, "erroneous response"); + assert_eq!( + u64::MAX, + timestamp_after, + "timestamp did not saturate upon increase", + ); + } + + #[tokio::test] + async fn test_increase_time() { + let node = InMemoryNode::::default(); + + let increase_value_seconds = 100u64; + let timestamp_before = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + let expected_response = increase_value_seconds; + + let actual_response = node + .increase_time(increase_value_seconds) + .expect("failed increasing timestamp"); + let timestamp_after = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + + assert_eq!(expected_response, actual_response, "erroneous response"); + assert_eq!( + increase_value_seconds.saturating_mul(1000u64), + timestamp_after.saturating_sub(timestamp_before), + "timestamp did not increase by the specified amount", + ); + } + + #[tokio::test] + async fn test_set_next_block_timestamp_future() { + let node = InMemoryNode::::default(); + + let new_timestamp = 10_000u64; + let timestamp_before = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + assert_ne!( + timestamp_before, new_timestamp, + "timestamps must be different" + ); + let expected_response = new_timestamp; + + let actual_response = node + .set_next_block_timestamp(new_timestamp) + .expect("failed setting timestamp"); + let timestamp_after = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + + assert_eq!(expected_response, actual_response, "erroneous response"); + assert_eq!( + new_timestamp, timestamp_after, + "timestamp was not set correctly", + ); + } + + #[tokio::test] + async fn test_set_next_block_timestamp_past_fails() { + let node = InMemoryNode::::default(); + + let timestamp_before = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + + let new_timestamp = timestamp_before + 500; + node.set_next_block_timestamp(new_timestamp) + .expect("failed setting timestamp"); + + let result = node.set_next_block_timestamp(timestamp_before); + + assert!(result.is_err(), "expected an error for timestamp in past"); + } + + #[tokio::test] + async fn test_set_next_block_timestamp_same_value() { + let node = InMemoryNode::::default(); + + let new_timestamp = 1000u64; + let timestamp_before = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + assert_eq!(timestamp_before, new_timestamp, "timestamps must be same"); + let expected_response = new_timestamp; + + let actual_response = node + .set_next_block_timestamp(new_timestamp) + .expect("failed setting timestamp"); + let timestamp_after = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + + assert_eq!(expected_response, actual_response, "erroneous response"); + assert_eq!( + timestamp_before, timestamp_after, + "timestamp must not change", + ); + } + + #[tokio::test] + async fn test_set_time_future() { + let node = InMemoryNode::::default(); + + let new_time = 10_000u64; + let timestamp_before = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + assert_ne!(timestamp_before, new_time, "timestamps must be different"); + let expected_response = 9000; + + let actual_response = node.set_time(new_time).expect("failed setting timestamp"); + let timestamp_after = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + + assert_eq!(expected_response, actual_response, "erroneous response"); + assert_eq!(new_time, timestamp_after, "timestamp was not set correctly",); + } + + #[tokio::test] + async fn test_set_time_past() { + let node = InMemoryNode::::default(); + + let new_time = 10u64; + let timestamp_before = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + assert_ne!(timestamp_before, new_time, "timestamps must be different"); + let expected_response = -990; + + let actual_response = node.set_time(new_time).expect("failed setting timestamp"); + let timestamp_after = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + + assert_eq!(expected_response, actual_response, "erroneous response"); + assert_eq!(new_time, timestamp_after, "timestamp was not set correctly",); + } + + #[tokio::test] + async fn test_set_time_same_value() { + let node = InMemoryNode::::default(); + + let new_time = 1000u64; + let timestamp_before = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + assert_eq!(timestamp_before, new_time, "timestamps must be same"); + let expected_response = 0; + + let actual_response = node.set_time(new_time).expect("failed setting timestamp"); + let timestamp_after = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .expect("failed reading timestamp"); + + assert_eq!(expected_response, actual_response, "erroneous response"); + assert_eq!( + timestamp_before, timestamp_after, + "timestamp must not change", + ); + } + + #[tokio::test] + async fn test_set_time_edges() { + let node = InMemoryNode::::default(); + + for new_time in [0, u64::MAX] { + let timestamp_before = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .unwrap_or_else(|_| panic!("case {}: failed reading timestamp", new_time)); + assert_ne!( + timestamp_before, new_time, + "case {new_time}: timestamps must be different" + ); + let expected_response = (new_time as i128).saturating_sub(timestamp_before as i128); + + let actual_response = node.set_time(new_time).expect("failed setting timestamp"); + let timestamp_after = node + .get_inner() + .read() + .map(|inner| inner.current_timestamp) + .unwrap_or_else(|_| panic!("case {}: failed reading timestamp", new_time)); + + assert_eq!( + expected_response, actual_response, + "case {new_time}: erroneous response" + ); + assert_eq!( + new_time, timestamp_after, + "case {new_time}: timestamp was not set correctly", + ); + } + } + + #[tokio::test] + async fn test_mine_block() { + let node = InMemoryNode::::default(); + + let start_block = node + .get_block_by_number(zksync_types::api::BlockNumber::Latest, false) + .await + .unwrap() + .expect("block exists"); + let result = node.mine_block().expect("mine_block"); + assert_eq!(&result, "0x0"); + + let current_block = node + .get_block_by_number(zksync_types::api::BlockNumber::Latest, false) + .await + .unwrap() + .expect("block exists"); + + assert_eq!(start_block.number + 1, current_block.number); + assert_eq!(start_block.timestamp + 1, current_block.timestamp); + + let result = node.mine_block().expect("mine_block"); + assert_eq!(&result, "0x0"); + + let current_block = node + .get_block_by_number(zksync_types::api::BlockNumber::Latest, false) + .await + .unwrap() + .expect("block exists"); + + assert_eq!(start_block.number + 2, current_block.number); + assert_eq!(start_block.timestamp + 2, current_block.timestamp); + } + + #[tokio::test] + async fn test_evm_snapshot_creates_incrementing_ids() { + let node = InMemoryNode::::default(); + + let snapshot_id_1 = node.snapshot().expect("failed creating snapshot 1"); + let snapshot_id_2 = node.snapshot().expect("failed creating snapshot 2"); + + assert_eq!(snapshot_id_1, U64::from(1)); + assert_eq!(snapshot_id_2, U64::from(2)); + } + + #[tokio::test] + async fn test_evm_revert_snapshot_restores_state() { + let node = InMemoryNode::::default(); + + let initial_block = node + .get_block_number() + .await + .expect("failed fetching block number"); + let snapshot_id = node.snapshot().expect("failed creating snapshot"); + node.mine_block().expect("mine_block"); + let current_block = node + .get_block_number() + .await + .expect("failed fetching block number"); + assert_eq!(current_block, initial_block + 1); + + let reverted = node + .revert_snapshot(snapshot_id) + .expect("failed reverting snapshot"); + assert!(reverted); + + let restored_block = node + .get_block_number() + .await + .expect("failed fetching block number"); + assert_eq!(restored_block, initial_block); + } + + #[tokio::test] + async fn test_evm_revert_snapshot_removes_all_snapshots_following_the_reverted_one() { + let node = InMemoryNode::::default(); + + let _snapshot_id_1 = node.snapshot().expect("failed creating snapshot"); + let snapshot_id_2 = node.snapshot().expect("failed creating snapshot"); + let _snapshot_id_3 = node.snapshot().expect("failed creating snapshot"); + assert_eq!(3, node.snapshots.read().unwrap().len()); + + let reverted = node + .revert_snapshot(snapshot_id_2) + .expect("failed reverting snapshot"); + assert!(reverted); + + assert_eq!(1, node.snapshots.read().unwrap().len()); + } + + #[tokio::test] + async fn test_evm_revert_snapshot_fails_for_invalid_snapshot_id() { + let node = InMemoryNode::::default(); + + let result = node.revert_snapshot(U64::from(100)); + assert!(result.is_err()); + } +} diff --git a/.test-node-subtree/src/node/mod.rs b/.test-node-subtree/src/node/mod.rs new file mode 100644 index 00000000..eef4206f --- /dev/null +++ b/.test-node-subtree/src/node/mod.rs @@ -0,0 +1,15 @@ +//! In-memory node, that supports forking other networks. + +mod config; +mod debug; +mod eth; +mod evm; +mod hardhat; +mod in_memory; +mod in_memory_ext; +mod net; +mod storage_logs; +mod web3; +mod zks; + +pub use in_memory::*; diff --git a/.test-node-subtree/src/node/net.rs b/.test-node-subtree/src/node/net.rs new file mode 100644 index 00000000..e61d60f9 --- /dev/null +++ b/.test-node-subtree/src/node/net.rs @@ -0,0 +1,23 @@ +use zksync_basic_types::U256; + +use crate::{ + fork::ForkSource, + namespaces::{NetNamespaceT, Result}, + node::{InMemoryNode, TEST_NODE_NETWORK_ID}, +}; + +impl NetNamespaceT + for InMemoryNode +{ + fn net_version(&self) -> Result { + Ok(TEST_NODE_NETWORK_ID.to_string()) + } + + fn net_peer_count(&self) -> Result { + Ok(U256::from(0)) + } + + fn net_listening(&self) -> Result { + Ok(false) + } +} diff --git a/.test-node-subtree/src/node/storage_logs.rs b/.test-node-subtree/src/node/storage_logs.rs new file mode 100644 index 00000000..2662da66 --- /dev/null +++ b/.test-node-subtree/src/node/storage_logs.rs @@ -0,0 +1,116 @@ +use std::collections::HashMap; + +use crate::formatter::{self, PubdataBytesInfo}; + +use super::ShowStorageLogs; +use multivm::vm_latest::VmExecutionResultAndLogs; +use zksync_basic_types::AccountTreeId; +use zksync_types::{ + utils::storage_key_for_eth_balance, + writes::{ + compression::compress_with_best_strategy, BYTES_PER_DERIVED_KEY, + BYTES_PER_ENUMERATION_INDEX, + }, + StorageKey, StorageLogQuery, StorageLogQueryType, BOOTLOADER_ADDRESS, SYSTEM_CONTEXT_ADDRESS, +}; +use zksync_utils::u256_to_h256; + +fn is_storage_key_free(key: &StorageKey) -> bool { + key.address() == &SYSTEM_CONTEXT_ADDRESS + || *key == storage_key_for_eth_balance(&BOOTLOADER_ADDRESS) +} + +fn compute_and_update_pubdata_cost( + cost_paid: &mut HashMap, + log_query: &StorageLogQuery, +) -> PubdataBytesInfo { + let storage_key = StorageKey::new( + AccountTreeId::new(log_query.log_query.address), + u256_to_h256(log_query.log_query.key), + ); + + if is_storage_key_free(&storage_key) { + PubdataBytesInfo::FreeSlot + } else { + // how many bytes it takes after compression. + let compressed_value_size = compress_with_best_strategy( + log_query.log_query.read_value, + log_query.log_query.written_value, + ) + .len() as u32; + + let final_pubdata_cost = if log_query.log_type == StorageLogQueryType::InitialWrite { + (BYTES_PER_DERIVED_KEY as u32) + compressed_value_size + } else { + (BYTES_PER_ENUMERATION_INDEX as u32) + compressed_value_size + }; + + let result = match cost_paid.get(&storage_key).copied() { + Some(already_paid) => { + let to_pay = final_pubdata_cost.saturating_sub(already_paid); + if to_pay > 0 { + PubdataBytesInfo::AdditionalPayment(to_pay, final_pubdata_cost) + } else { + PubdataBytesInfo::PaidAlready + } + } + None => PubdataBytesInfo::Paid(final_pubdata_cost), + }; + cost_paid.insert(storage_key, final_pubdata_cost); + result + } +} + +pub fn print_storage_logs_details( + show_storage_logs: &ShowStorageLogs, + result: &VmExecutionResultAndLogs, +) { + tracing::info!(""); + tracing::info!("┌──────────────────┐"); + tracing::info!("│ STORAGE LOGS │"); + tracing::info!("└──────────────────┘"); + + let mut cost_paid = HashMap::::default(); + + for log_query in &result.logs.storage_logs { + let pubdata_bytes_info = if matches!( + log_query.log_type, + StorageLogQueryType::RepeatedWrite | StorageLogQueryType::InitialWrite + ) { + Some(compute_and_update_pubdata_cost(&mut cost_paid, log_query)) + } else { + None + }; + + match show_storage_logs { + ShowStorageLogs::Write => { + if matches!( + log_query.log_type, + StorageLogQueryType::RepeatedWrite | StorageLogQueryType::InitialWrite + ) { + formatter::print_logs(log_query, pubdata_bytes_info); + } + } + ShowStorageLogs::Paid => { + // Show only the logs that incur any cost. + if pubdata_bytes_info + .as_ref() + .map(|x| x.does_cost()) + .unwrap_or_default() + { + formatter::print_logs(log_query, pubdata_bytes_info); + } + } + ShowStorageLogs::Read => { + if log_query.log_type == StorageLogQueryType::Read { + formatter::print_logs(log_query, pubdata_bytes_info); + } + } + ShowStorageLogs::All => { + formatter::print_logs(log_query, pubdata_bytes_info); + } + + _ => {} + } + } +} diff --git a/.test-node-subtree/src/node/web3.rs b/.test-node-subtree/src/node/web3.rs new file mode 100644 index 00000000..1b7402d5 --- /dev/null +++ b/.test-node-subtree/src/node/web3.rs @@ -0,0 +1,13 @@ +use crate::{ + fork::ForkSource, + namespaces::{Result, Web3NamespaceT}, + node::InMemoryNode, +}; + +impl Web3NamespaceT + for InMemoryNode +{ + fn web3_client_version(&self) -> Result { + Ok("zkSync/v2.0".to_string()) + } +} diff --git a/.test-node-subtree/src/node/zks.rs b/.test-node-subtree/src/node/zks.rs new file mode 100644 index 00000000..4c3834c4 --- /dev/null +++ b/.test-node-subtree/src/node/zks.rs @@ -0,0 +1,1168 @@ +use std::collections::HashMap; + +use bigdecimal::BigDecimal; +use colored::Colorize; +use futures::FutureExt; +use zksync_basic_types::{AccountTreeId, Address, L1BatchNumber, MiniblockNumber, H256, U256}; +use zksync_core::api_server::web3::backend_jsonrpc::error::{internal_error, into_jsrpc_error}; +use zksync_state::ReadStorage; +use zksync_types::{ + api::{ + BlockDetails, BlockDetailsBase, BlockStatus, BridgeAddresses, Proof, ProtocolVersion, + TransactionDetails, TransactionStatus, TransactionVariant, + }, + fee::Fee, + utils::storage_key_for_standard_token_balance, + ExecuteTransactionCommon, ProtocolVersionId, Transaction, L2_ETH_TOKEN_ADDRESS, +}; +use zksync_utils::h256_to_u256; +use zksync_web3_decl::error::Web3Error; + +use crate::{ + fork::ForkSource, + namespaces::{RpcResult, ZksNamespaceT}, + node::{InMemoryNode, TransactionResult, L2_GAS_PRICE}, + utils::{not_implemented, utc_datetime_from_epoch_ms, IntoBoxedFuture}, +}; + +impl ZksNamespaceT + for InMemoryNode +{ + /// Estimates the gas fee data required for a given call request. + /// + /// # Arguments + /// + /// * `req` - A `CallRequest` struct representing the call request to estimate gas for. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a `Fee` representing the estimated gas data required. + fn estimate_fee(&self, req: zksync_types::transaction_request::CallRequest) -> RpcResult { + self.get_inner() + .read() + .map_err(|err| { + tracing::error!("failed acquiring lock: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + }) + .and_then(|reader| reader.estimate_gas_impl(req)) + .into_boxed_future() + } + + /// Returns data of transactions in a block. + /// + /// # Arguments + /// + /// * `block` - Block number + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a `Vec` of `Transaction`s representing the transactions in the block. + fn get_raw_block_transactions( + &self, + block_number: MiniblockNumber, + ) -> RpcResult> { + let inner = self.get_inner().clone(); + Box::pin(async move { + let reader = inner + .read() + .map_err(|_err| into_jsrpc_error(Web3Error::InternalError))?; + + let maybe_transactions = reader + .block_hashes + .get(&(block_number.0 as u64)) + .and_then(|hash| reader.blocks.get(hash)) + .map(|block| { + block + .transactions + .iter() + .map(|tx| match tx { + TransactionVariant::Full(tx) => &tx.hash, + TransactionVariant::Hash(hash) => hash, + }) + .flat_map(|tx_hash| { + reader.tx_results.get(tx_hash).map( + |TransactionResult { info, .. }| Transaction { + common_data: ExecuteTransactionCommon::L2( + info.tx.common_data.clone(), + ), + execute: info.tx.execute.clone(), + received_timestamp_ms: info.tx.received_timestamp_ms, + raw_bytes: info.tx.raw_bytes.clone(), + }, + ) + }) + .collect() + }); + + let transactions = match maybe_transactions { + Some(txns) => Ok(txns), + None => { + let fork_storage_read = reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage"); + + match fork_storage_read.fork.as_ref() { + Some(fork) => fork + .fork_source + .get_raw_block_transactions(block_number) + .map_err(|e| internal_error("get_raw_block_transactions", e)), + None => Ok(vec![]), + } + } + } + .map_err(into_jsrpc_error)?; + + Ok(transactions) + }) + } + + fn get_proof( + &self, + _address: Address, + _keys: Vec, + _l1_batch_number: L1BatchNumber, + ) -> RpcResult { + not_implemented("zks_getProof") + } + + fn estimate_gas_l1_to_l2( + &self, + _req: zksync_types::transaction_request::CallRequest, + ) -> RpcResult { + not_implemented("zks_estimateGasL1ToL2") + } + + fn get_main_contract(&self) -> RpcResult { + not_implemented("zks_getMainContract") + } + + fn get_testnet_paymaster(&self) -> RpcResult> { + not_implemented("zks_getTestnetPaymaster") + } + + fn get_bridge_contracts(&self) -> RpcResult { + let inner = self.get_inner().clone(); + Box::pin(async move { + let reader = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let result = match reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + { + Some(fork) => fork.fork_source.get_bridge_contracts().map_err(|err| { + tracing::error!("failed fetching bridge contracts from the fork: {:?}", err); + into_jsrpc_error(Web3Error::InternalError) + })?, + None => BridgeAddresses { + l1_erc20_default_bridge: Default::default(), + l2_erc20_default_bridge: Default::default(), + l1_weth_bridge: Default::default(), + l2_weth_bridge: Default::default(), + }, + }; + + Ok(result) + }) + } + + fn l1_chain_id(&self) -> RpcResult { + not_implemented("zks_L1ChainId") + } + + fn get_confirmed_tokens( + &self, + from: u32, + limit: u8, + ) -> jsonrpc_core::BoxFuture>> { + let inner = self.get_inner().clone(); + Box::pin(async move { + let reader = inner + .read() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let fork_storage_read = reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage"); + + match fork_storage_read.fork.as_ref() { + Some(fork) => Ok(fork + .fork_source + .get_confirmed_tokens(from, limit) + .map_err(|_e| into_jsrpc_error(Web3Error::InternalError))?), + None => Ok(vec![zksync_web3_decl::types::Token { + l1_address: Address::zero(), + l2_address: L2_ETH_TOKEN_ADDRESS, + name: "Ether".to_string(), + symbol: "ETH".to_string(), + decimals: 18, + }]), + } + }) + } + + fn get_token_price(&self, token_address: zksync_basic_types::Address) -> RpcResult { + match format!("{:?}", token_address).to_lowercase().as_str() { + "0x0000000000000000000000000000000000000000" => { + // ETH + Ok(1_500.into()).into_boxed_future() + } + "0x40609141db628beee3bfab8034fc2d8278d0cc78" => { + // LINK + Ok(1.into()).into_boxed_future() + } + "0x0bfce1d53451b4a8175dd94e6e029f7d8a701e9c" => { + // wBTC + Ok(1.into()).into_boxed_future() + } + "0x0faf6df7054946141266420b43783387a78d82a9" => { + // USDC + Ok(1.into()).into_boxed_future() + } + "0x3e7676937a7e96cfb7616f255b9ad9ff47363d4b" => { + // DAI + Ok(1.into()).into_boxed_future() + } + address => { + tracing::error!( + "{}", + format!("Token price requested for unknown address {:?}", address).red() + ); + futures::future::err(into_jsrpc_error(Web3Error::InternalError)).boxed() + } + } + } + + /// Get all known balances for a given account. + /// + /// # Arguments + /// + /// * `address` - The user address with balances to check. + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with a (Token, Balance) map where account has non-zero value. + fn get_all_account_balances( + &self, + address: zksync_basic_types::Address, + ) -> jsonrpc_core::BoxFuture< + jsonrpc_core::Result>, + > { + let inner = self.get_inner().clone(); + Box::pin({ + self.get_confirmed_tokens(0, 100) + .then(move |tokens| async move { + let tokens = + tokens.map_err(|_err| into_jsrpc_error(Web3Error::InternalError))?; + + let mut writer = inner + .write() + .map_err(|_err| into_jsrpc_error(Web3Error::InternalError))?; + + let mut balances = HashMap::new(); + for token in tokens { + let balance_key = storage_key_for_standard_token_balance( + AccountTreeId::new(token.l2_address), + &address, + ); + + let balance = writer.fork_storage.read_value(&balance_key); + if !balance.is_zero() { + balances.insert(token.l2_address, h256_to_u256(balance)); + } + } + + Ok(balances) + }) + }) + } + + fn get_l2_to_l1_msg_proof( + &self, + _block: zksync_basic_types::MiniblockNumber, + _sender: zksync_basic_types::Address, + _msg: zksync_basic_types::H256, + _l2_log_position: Option, + ) -> RpcResult> { + not_implemented("zks_getL2ToL1MsgProof") + } + + fn get_l2_to_l1_log_proof( + &self, + _tx_hash: zksync_basic_types::H256, + _index: Option, + ) -> RpcResult> { + not_implemented("zks_getL2ToL1LogProof") + } + + fn get_l1_batch_number(&self) -> RpcResult { + not_implemented("zks_L1BatchNumber") + } + + /// Get block details. + /// + /// # Arguments + /// + /// * `blockNumber` - `u32` miniblock number + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with an `Option` representing details of the block (if found). + fn get_block_details( + &self, + block_number: zksync_basic_types::MiniblockNumber, + ) -> RpcResult> { + let inner = self.get_inner().clone(); + Box::pin(async move { + let reader = inner + .read() + .map_err(|_err| into_jsrpc_error(Web3Error::InternalError))?; + + let maybe_block = reader + .block_hashes + .get(&(block_number.0 as u64)) + .and_then(|hash| reader.blocks.get(hash)) + .map(|block| BlockDetails { + number: MiniblockNumber(block.number.as_u32()), + l1_batch_number: L1BatchNumber( + block.l1_batch_number.unwrap_or_default().as_u32(), + ), + base: BlockDetailsBase { + timestamp: block.timestamp.as_u64(), + l1_tx_count: 1, + l2_tx_count: block.transactions.len(), + root_hash: Some(block.hash), + status: BlockStatus::Verified, + commit_tx_hash: None, + committed_at: None, + prove_tx_hash: None, + proven_at: None, + execute_tx_hash: None, + executed_at: None, + l1_gas_price: 0, + l2_fair_gas_price: L2_GAS_PRICE, + base_system_contracts_hashes: reader + .system_contracts + .baseline_contracts + .hashes(), + }, + operator_address: Address::zero(), + protocol_version: Some(ProtocolVersionId::latest()), + }) + .or_else(|| { + reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_block_details(block_number) + .ok() + .flatten() + }) + }); + + Ok(maybe_block) + }) + } + + fn get_miniblock_range( + &self, + _batch: zksync_basic_types::L1BatchNumber, + ) -> jsonrpc_core::BoxFuture< + jsonrpc_core::Result>, + > { + not_implemented("zks_getL1BatchBlockRange") + } + + /// Get transaction details. + /// + /// # Arguments + /// + /// * `transactionHash` - `H256` hash of the transaction + /// + /// # Returns + /// + /// A `BoxFuture` containing a `Result` with an `Option` representing details of the transaction (if found). + fn get_transaction_details( + &self, + hash: zksync_basic_types::H256, + ) -> RpcResult> { + let inner = self.get_inner().clone(); + Box::pin(async move { + let reader = inner + .read() + .map_err(|_err| into_jsrpc_error(Web3Error::InternalError))?; + + let maybe_result = { + reader + .tx_results + .get(&hash) + .map(|TransactionResult { info, receipt, .. }| { + TransactionDetails { + is_l1_originated: false, + status: TransactionStatus::Included, + // if these are not set, fee is effectively 0 + fee: receipt.effective_gas_price.unwrap_or_default() + * receipt.gas_used.unwrap_or_default(), + gas_per_pubdata: info.tx.common_data.fee.gas_per_pubdata_limit, + initiator_address: info.tx.initiator_account(), + received_at: utc_datetime_from_epoch_ms(info.tx.received_timestamp_ms), + eth_commit_tx_hash: None, + eth_prove_tx_hash: None, + eth_execute_tx_hash: None, + } + }) + .or_else(|| { + reader + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| { + fork.fork_source + .get_transaction_details(hash) + .ok() + .flatten() + }) + }) + }; + + Ok(maybe_result) + }) + } + + /// Retrieves details for a given L1 batch. + /// + /// This method is intended to handle queries related to L1 batch details. However, as of the current implementation, + /// L1 communication is not supported. Instead of an error or no method found, this method intentionally returns + /// `{"jsonrpc":"2.0","result":null,"id":1}` to ensure compatibility with block explorer integration. + /// + /// # Parameters + /// + /// * `_batch`: The batch number of type `zksync_basic_types::L1BatchNumber` for which the details are to be fetched. + /// + /// # Returns + /// + /// A boxed future resolving to a `jsonrpc_core::Result` containing an `Option` of `zksync_types::api::L1BatchDetails`. + /// Given the current implementation, this will always be `None`. + fn get_l1_batch_details( + &self, + _batch: zksync_basic_types::L1BatchNumber, + ) -> RpcResult> { + Box::pin(async { Ok(None) }) + } + + /// Returns bytecode of a transaction given by its hash. + /// + /// # Parameters + /// + /// * `hash`: Hash address. + /// + /// # Returns + /// + /// A boxed future resolving to a `jsonrpc_core::Result` containing an `Option` of bytes. + fn get_bytecode_by_hash(&self, hash: zksync_basic_types::H256) -> RpcResult>> { + let inner = self.get_inner().clone(); + Box::pin(async move { + let mut writer = inner + .write() + .map_err(|_| into_jsrpc_error(Web3Error::InternalError))?; + + let maybe_bytecode = writer.fork_storage.load_factory_dep(hash).or_else(|| { + writer + .fork_storage + .inner + .read() + .expect("failed reading fork storage") + .fork + .as_ref() + .and_then(|fork| fork.fork_source.get_bytecode_by_hash(hash).ok().flatten()) + }); + + Ok(maybe_bytecode) + }) + } + + fn get_l1_gas_price(&self) -> RpcResult { + not_implemented("zks_getL1GasPrice") + } + + fn get_protocol_version(&self, _version_id: Option) -> RpcResult> { + not_implemented("zks_getProtocolVersion") + } +} + +#[cfg(test)] +mod tests { + use std::str::FromStr; + + use crate::cache::CacheConfig; + use crate::fork::ForkDetails; + use crate::testing; + use crate::testing::{ForkBlockConfig, MockServer}; + use crate::{http_fork_source::HttpForkSource, node::InMemoryNode}; + + use super::*; + use zksync_basic_types::{Address, H160, H256}; + use zksync_types::api::{self, Block, TransactionReceipt, TransactionVariant}; + use zksync_types::transaction_request::CallRequest; + use zksync_utils::u256_to_h256; + + #[tokio::test] + async fn test_estimate_fee() { + let node = InMemoryNode::::default(); + + let mock_request = CallRequest { + from: Some( + "0xa61464658afeaf65cccaafd3a512b69a83b77618" + .parse() + .unwrap(), + ), + to: Some( + "0x36615cf349d7f6344891b1e7ca7c72883f5dc049" + .parse() + .unwrap(), + ), + gas: Some(U256::from(0)), + gas_price: Some(U256::from(0)), + max_fee_per_gas: None, + max_priority_fee_per_gas: None, + value: Some(U256::from(0)), + data: Some(vec![0, 0].into()), + nonce: Some(U256::from(0)), + transaction_type: None, + access_list: None, + eip712_meta: None, + }; + + let result = node.estimate_fee(mock_request).await.unwrap(); + + assert_eq!(result.gas_limit, U256::from(746532)); + assert_eq!(result.max_fee_per_gas, U256::from(250000000)); + assert_eq!(result.max_priority_fee_per_gas, U256::from(0)); + assert_eq!(result.gas_per_pubdata_limit, U256::from(4080)); + } + + #[tokio::test] + async fn test_get_token_price_given_eth_should_return_price() { + // Arrange + let node = InMemoryNode::::default(); + + let mock_address = Address::from_str("0x0000000000000000000000000000000000000000") + .expect("Failed to parse address"); + + // Act + let result = node.get_token_price(mock_address).await.unwrap(); + + // Assert + assert_eq!(result, BigDecimal::from(1_500)); + } + + #[tokio::test] + async fn test_get_token_price_given_capitalized_link_address_should_return_price() { + // Arrange + let node = InMemoryNode::::default(); + + let mock_address = Address::from_str("0x40609141Db628BeEE3BfAB8034Fc2D8278D0Cc78") + .expect("Failed to parse address"); + + // Act + let result = node.get_token_price(mock_address).await.unwrap(); + + // Assert + assert_eq!(result, BigDecimal::from(1)); + } + + #[tokio::test] + async fn test_get_token_price_given_unknown_address_should_return_error() { + // Arrange + let node = InMemoryNode::::default(); + + let mock_address = Address::from_str("0x0000000000000000000000000000000000000042") + .expect("Failed to parse address"); + + // Act + let result = node.get_token_price(mock_address).await; + + // Assert + assert!(result.is_err()); + } + + #[tokio::test] + async fn test_get_transaction_details_local() { + // Arrange + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + writer.tx_results.insert( + H256::repeat_byte(0x1), + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![], + gas_used: Some(U256::from(10_000)), + effective_gas_price: Some(U256::from(1_000_000_000)), + ..Default::default() + }, + debug: testing::default_tx_debug_info(), + }, + ); + } + let result = node + .get_transaction_details(H256::repeat_byte(0x1)) + .await + .expect("get transaction details") + .expect("transaction details"); + + // Assert + assert!(matches!(result.status, TransactionStatus::Included)); + assert_eq!(result.fee, U256::from(10_000_000_000_000u64)); + } + + #[tokio::test] + async fn test_get_transaction_details_fork() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let input_tx_hash = H256::repeat_byte(0x02); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getTransactionDetails", + "params": [ + format!("{:#x}", input_tx_hash), + ], + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": { + "isL1Originated": false, + "status": "included", + "fee": "0x74293f087500", + "gasPerPubdata": "0x4e20", + "initiatorAddress": "0x63ab285cd87a189f345fed7dd4e33780393e01f0", + "receivedAt": "2023-10-12T15:45:53.094Z", + "ethCommitTxHash": null, + "ethProveTxHash": null, + "ethExecuteTxHash": null + }, + "id": 0 + }), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let result = node + .get_transaction_details(input_tx_hash) + .await + .expect("get transaction details") + .expect("transaction details"); + + assert!(matches!(result.status, TransactionStatus::Included)); + assert_eq!(result.fee, U256::from(127_720_500_000_000u64)); + } + + #[tokio::test] + async fn test_get_block_details_local() { + // Arrange + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + let block = Block::::default(); + writer.blocks.insert(H256::repeat_byte(0x1), block); + writer.block_hashes.insert(0, H256::repeat_byte(0x1)); + } + let result = node + .get_block_details(MiniblockNumber(0)) + .await + .expect("get block details") + .expect("block details"); + + // Assert + assert!(matches!(result.number, MiniblockNumber(0))); + assert_eq!(result.l1_batch_number, L1BatchNumber(0)); + assert_eq!(result.base.timestamp, 0); + } + + #[tokio::test] + async fn test_get_block_details_fork() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let miniblock = MiniblockNumber::from(16474138); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getBlockDetails", + "params": [ + miniblock.0, + ], + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": { + "number": 16474138, + "l1BatchNumber": 270435, + "timestamp": 1697405098, + "l1TxCount": 0, + "l2TxCount": 1, + "rootHash": "0xd9e60f9a684fd7fc16e87ae923341a6e4af24f286e76612efdfc2d55f3f4d064", + "status": "sealed", + "commitTxHash": null, + "committedAt": null, + "proveTxHash": null, + "provenAt": null, + "executeTxHash": null, + "executedAt": null, + "l1GasPrice": 6156252068u64, + "l2FairGasPrice": 250000000u64, + "baseSystemContractsHashes": { + "bootloader": "0x0100089b8a2f2e6a20ba28f02c9e0ed0c13d702932364561a0ea61621f65f0a8", + "default_aa": "0x0100067d16a5485875b4249040bf421f53e869337fe118ec747cf40a4c777e5f" + }, + "operatorAddress": "0xa9232040bf0e0aea2578a5b2243f2916dbfc0a69", + "protocolVersion": "Version15" + }, + "id": 0 + }), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let result = node + .get_block_details(miniblock) + .await + .expect("get block details") + .expect("block details"); + + assert!(matches!(result.number, MiniblockNumber(16474138))); + assert_eq!(result.l1_batch_number, L1BatchNumber(270435)); + assert_eq!(result.base.timestamp, 1697405098); + } + + #[tokio::test] + async fn test_get_bridge_contracts_uses_default_values_if_local() { + // Arrange + let node = InMemoryNode::::default(); + let expected_bridge_addresses = BridgeAddresses { + l1_erc20_default_bridge: Default::default(), + l2_erc20_default_bridge: Default::default(), + l1_weth_bridge: Default::default(), + l2_weth_bridge: Default::default(), + }; + + let actual_bridge_addresses = node + .get_bridge_contracts() + .await + .expect("get bridge addresses"); + + // Assert + testing::assert_bridge_addresses_eq(&expected_bridge_addresses, &actual_bridge_addresses) + } + + #[tokio::test] + async fn test_get_bridge_contracts_uses_fork() { + // Arrange + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let input_bridge_addresses = BridgeAddresses { + l1_erc20_default_bridge: H160::repeat_byte(0x1), + l2_erc20_default_bridge: H160::repeat_byte(0x2), + l1_weth_bridge: Some(H160::repeat_byte(0x3)), + l2_weth_bridge: Some(H160::repeat_byte(0x4)), + }; + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getBridgeContracts", + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": { + "l1Erc20DefaultBridge": format!("{:#x}", input_bridge_addresses.l1_erc20_default_bridge), + "l2Erc20DefaultBridge": format!("{:#x}", input_bridge_addresses.l2_erc20_default_bridge), + "l1WethBridge": format!("{:#x}", input_bridge_addresses.l1_weth_bridge.unwrap()), + "l2WethBridge": format!("{:#x}", input_bridge_addresses.l2_weth_bridge.unwrap()) + }, + "id": 0 + }), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual_bridge_addresses = node + .get_bridge_contracts() + .await + .expect("get bridge addresses"); + + // Assert + testing::assert_bridge_addresses_eq(&input_bridge_addresses, &actual_bridge_addresses) + } + + #[tokio::test] + async fn test_get_bytecode_by_hash_returns_local_value_if_available() { + // Arrange + let node = InMemoryNode::::default(); + let input_hash = H256::repeat_byte(0x1); + let input_bytecode = vec![0x1]; + node.get_inner() + .write() + .unwrap() + .fork_storage + .store_factory_dep(input_hash, input_bytecode.clone()); + + let actual = node + .get_bytecode_by_hash(input_hash) + .await + .expect("failed fetching bytecode") + .expect("no bytecode was found"); + + // Assert + assert_eq!(input_bytecode, actual); + } + + #[tokio::test] + async fn test_get_bytecode_by_hash_uses_fork_if_value_unavailable() { + // Arrange + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let input_hash = H256::repeat_byte(0x1); + let input_bytecode = vec![0x1]; + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getBytecodeByHash", + "params": [ + format!("{:#x}", input_hash) + ], + }), + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "result": input_bytecode, + }), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let actual = node + .get_bytecode_by_hash(input_hash) + .await + .expect("failed fetching bytecode") + .expect("no bytecode was found"); + + // Assert + assert_eq!(input_bytecode, actual); + } + + #[tokio::test] + async fn test_get_raw_block_transactions_local() { + // Arrange + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + { + let mut writer = inner.write().unwrap(); + let mut block = Block::::default(); + let txn = api::Transaction::default(); + writer.tx_results.insert( + txn.hash, + TransactionResult { + info: testing::default_tx_execution_info(), + receipt: TransactionReceipt { + logs: vec![], + gas_used: Some(U256::from(10_000)), + effective_gas_price: Some(U256::from(1_000_000_000)), + ..Default::default() + }, + debug: testing::default_tx_debug_info(), + }, + ); + block.transactions.push(TransactionVariant::Full(txn)); + writer.blocks.insert(H256::repeat_byte(0x1), block); + writer.block_hashes.insert(0, H256::repeat_byte(0x1)); + } + + let txns = node + .get_raw_block_transactions(MiniblockNumber(0)) + .await + .expect("get transaction details"); + + // Assert + assert_eq!(txns.len(), 1); + } + + #[tokio::test] + async fn test_get_raw_block_transactions_fork() { + let mock_server = MockServer::run_with_config(ForkBlockConfig { + number: 10, + transaction_count: 0, + hash: H256::repeat_byte(0xab), + }); + let miniblock = MiniblockNumber::from(16474138); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getRawBlockTransactions", + "params": [miniblock.0] + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": [ + { + "common_data": { + "L2": { + "nonce": 86, + "fee": { + "gas_limit": "0xcc626", + "max_fee_per_gas": "0x141dd760", + "max_priority_fee_per_gas": "0x0", + "gas_per_pubdata_limit": "0x4e20" + }, + "initiatorAddress": "0x840bd73f903ba7dbb501be8326fe521dadcae1a5", + "signature": [ + 135, + 163, + 2, + 78, + 118, + 14, + 209 + ], + "transactionType": "EIP1559Transaction", + "input": { + "hash": "0xc1f625f55d186ad0b439054adfe3317ae703c5f588f4fa1896215e8810a141e0", + "data": [ + 2, + 249, + 1, + 110, + 130 + ] + }, + "paymasterParams": { + "paymaster": "0x0000000000000000000000000000000000000000", + "paymasterInput": [] + } + } + }, + "execute": { + "contractAddress": "0xbe7d1fd1f6748bbdefc4fbacafbb11c6fc506d1d", + "calldata": "0x38ed173900000000000000000000000000000000000000000000000000000000002c34cc00000000000000000000000000000000000000000000000000000000002c9a2500000000000000000000000000000000000000000000000000000000000000a0000000000000000000000000840bd73f903ba7dbb501be8326fe521dadcae1a500000000000000000000000000000000000000000000000000000000652c5d1900000000000000000000000000000000000000000000000000000000000000020000000000000000000000008e86e46278518efc1c5ced245cba2c7e3ef115570000000000000000000000003355df6d4c9c3035724fd0e3914de96a5a83aaf4", + "value": "0x0", + "factoryDeps": null + }, + "received_timestamp_ms": 1697405097873u64, + "raw_bytes": "0x02f9016e820144568084141dd760830cc62694be7d1fd1f6748bbdefc4fbacafbb11c6fc506d1d80b9010438ed173900000000000000000000000000000000000000000000000000000000002c34cc00000000000000000000000000000000000000000000000000000000002c9a2500000000000000000000000000000000000000000000000000000000000000a0000000000000000000000000840bd73f903ba7dbb501be8326fe521dadcae1a500000000000000000000000000000000000000000000000000000000652c5d1900000000000000000000000000000000000000000000000000000000000000020000000000000000000000008e86e46278518efc1c5ced245cba2c7e3ef115570000000000000000000000003355df6d4c9c3035724fd0e3914de96a5a83aaf4c080a087a3024e760ed14134ef541608bf308e083c899a89dba3c02bf3040f07c8b91b9fc3a7eeb6b3b8b36bb03ea4352415e7815dda4954f4898d255bd7660736285e" + } + ], + "id": 0 + }), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), None, CacheConfig::None).await), + None, + Default::default(), + ); + + let txns = node + .get_raw_block_transactions(miniblock) + .await + .expect("get transaction details"); + assert_eq!(txns.len(), 1); + } + + #[tokio::test] + async fn test_get_all_account_balances_empty() { + let node = InMemoryNode::::default(); + let balances = node + .get_all_account_balances(Address::zero()) + .await + .expect("get balances"); + assert!(balances.is_empty()); + } + + #[tokio::test] + async fn test_get_confirmed_tokens_eth() { + let node = InMemoryNode::::default(); + let balances = node + .get_confirmed_tokens(0, 100) + .await + .expect("get balances"); + assert_eq!(balances.len(), 1); + assert_eq!(&balances[0].name, "Ether"); + } + + #[tokio::test] + async fn test_get_all_account_balances_forked() { + let cbeth_address = Address::from_str("0x75af292c1c9a37b3ea2e6041168b4e48875b9ed5") + .expect("failed to parse address"); + let mock_server = testing::MockServer::run(); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getBlockDetails", + "params": [1] + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": { + "baseSystemContractsHashes": { + "bootloader": "0x010008a5c30072f79f8e04f90b31f34e554279957e7e2bf85d3e9c7c1e0f834d", + "default_aa": "0x01000663d7941c097ba2631096508cf9ec7769ddd40e081fd81b0d04dc07ea0e" + }, + "commitTxHash": null, + "committedAt": null, + "executeTxHash": null, + "executedAt": null, + "l1BatchNumber": 0, + "l1GasPrice": 0, + "l1TxCount": 1, + "l2FairGasPrice": 250000000, + "l2TxCount": 0, + "number": 0, + "operatorAddress": "0x0000000000000000000000000000000000000000", + "protocolVersion": "Version16", + "proveTxHash": null, + "provenAt": null, + "rootHash": "0xdaa77426c30c02a43d9fba4e841a6556c524d47030762eb14dc4af897e605d9b", + "status": "verified", + "timestamp": 1000 + }, + "id": 0 + }), + ); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 1, + "method": "eth_getBlockByHash", + "params": ["0xdaa77426c30c02a43d9fba4e841a6556c524d47030762eb14dc4af897e605d9b", true] + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": { + "baseFeePerGas": "0x0", + "difficulty": "0x0", + "extraData": "0x", + "gasLimit": "0xffffffff", + "gasUsed": "0x0", + "hash": "0xdaa77426c30c02a43d9fba4e841a6556c524d47030762eb14dc4af897e605d9b", + "l1BatchNumber": "0x0", + "l1BatchTimestamp": null, + "logsBloom": "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "miner": "0x0000000000000000000000000000000000000000", + "mixHash": "0x0000000000000000000000000000000000000000000000000000000000000000", + "nonce": "0x0000000000000000", + "number": "0x0", + "parentHash": "0x0000000000000000000000000000000000000000000000000000000000000000", + "receiptsRoot": "0x0000000000000000000000000000000000000000000000000000000000000000", + "sealFields": [], + "sha3Uncles": "0x0000000000000000000000000000000000000000000000000000000000000000", + "size": "0x0", + "stateRoot": "0x0000000000000000000000000000000000000000000000000000000000000000", + "timestamp": "0x3e8", + "totalDifficulty": "0x0", + "transactions": [], + "transactionsRoot": "0x0000000000000000000000000000000000000000000000000000000000000000", + "uncles": [] + }, + "id": 1 + }), + ); + mock_server.expect( + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "zks_getConfirmedTokens", + "params": [0, 100] + }), + serde_json::json!({ + "jsonrpc": "2.0", + "result": [ + { + "decimals": 18, + "l1Address": "0xbe9895146f7af43049ca1c1ae358b0541ea49704", + "l2Address": "0x75af292c1c9a37b3ea2e6041168b4e48875b9ed5", + "name": "Coinbase Wrapped Staked ETH", + "symbol": "cbETH" + } + ], + "id": 0 + }), + ); + + let node = InMemoryNode::::new( + Some(ForkDetails::from_network(&mock_server.url(), Some(1), CacheConfig::None).await), + None, + Default::default(), + ); + { + let inner = node.get_inner(); + let writer = inner.write().unwrap(); + let mut fork = writer.fork_storage.inner.write().unwrap(); + fork.raw_storage.set_value( + storage_key_for_standard_token_balance( + AccountTreeId::new(cbeth_address), + &Address::repeat_byte(0x1), + ), + u256_to_h256(U256::from(1337)), + ); + } + + let balances = node + .get_all_account_balances(Address::repeat_byte(0x1)) + .await + .expect("get balances"); + assert_eq!(balances.get(&cbeth_address).unwrap(), &U256::from(1337)); + } +} diff --git a/.test-node-subtree/src/observability.rs b/.test-node-subtree/src/observability.rs new file mode 100644 index 00000000..ec3039b6 --- /dev/null +++ b/.test-node-subtree/src/observability.rs @@ -0,0 +1,144 @@ +use core::fmt; +use std::{fs::File, sync::Mutex}; + +use clap::ValueEnum; +use serde::{Deserialize, Serialize}; +use tracing_subscriber::{ + filter::LevelFilter, layer::SubscriberExt, reload, util::SubscriberInitExt, EnvFilter, Registry, +}; + +/// Log filter level for the node. +#[derive(Debug, Clone, ValueEnum, Serialize, Deserialize)] +#[serde(rename_all = "lowercase")] +pub enum LogLevel { + Trace, + Debug, + Info, + Warn, + Error, +} + +impl fmt::Display for LogLevel { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + match *self { + LogLevel::Trace => f.pad("TRACE"), + LogLevel::Debug => f.pad("DEBUG"), + LogLevel::Info => f.pad("INFO"), + LogLevel::Warn => f.pad("WARN"), + LogLevel::Error => f.pad("ERROR"), + } + } +} + +impl From for LevelFilter { + fn from(value: LogLevel) -> Self { + match value { + LogLevel::Trace => LevelFilter::TRACE, + LogLevel::Debug => LevelFilter::DEBUG, + LogLevel::Info => LevelFilter::INFO, + LogLevel::Warn => LevelFilter::WARN, + LogLevel::Error => LevelFilter::ERROR, + } + } +} + +/// A sharable reference to the observability stack. +#[derive(Debug, Default, Clone)] +pub struct Observability { + binary_name: String, + reload_handle: Option>, +} + +impl Observability { + /// Initialize the tracing subscriber. + pub fn init( + binary_name: String, + log_level_filter: LevelFilter, + log_file: File, + ) -> Result { + let filter = Self::parse_filter(&format!( + "{}={}", + binary_name, + format!("{log_level_filter}").to_lowercase() + ))?; + let (filter, reload_handle) = reload::Layer::new(filter); + + let timer_format = + time::format_description::parse("[hour]:[minute]:[second]").expect("Cataplum"); + let time_offset = time::UtcOffset::current_local_offset().unwrap_or(time::UtcOffset::UTC); + let timer = tracing_subscriber::fmt::time::OffsetTime::new(time_offset, timer_format); + + tracing_subscriber::registry() + .with(filter) + .with( + tracing_subscriber::fmt::layer().event_format( + tracing_subscriber::fmt::format() + .compact() + .with_timer(timer.clone()) + .with_target(false), + ), + ) + .with( + tracing_subscriber::fmt::layer() + .event_format( + tracing_subscriber::fmt::format() + .compact() + .with_timer(timer.clone()) + .with_target(false), + ) + .with_writer(Mutex::new(log_file)) + .with_ansi(false), + ) + .init(); + + Ok(Self { + binary_name, + reload_handle: Some(reload_handle), + }) + } + + /// Set the log level for the binary. + pub fn set_log_level(&self, level: LogLevel) -> Result<(), anyhow::Error> { + let level = LevelFilter::from(level); + let new_filter = Self::parse_filter(&format!( + "{}={}", + self.binary_name, + format!("{level}").to_lowercase() + ))?; + + if let Some(handle) = &self.reload_handle { + handle.modify(|filter| *filter = new_filter)?; + } + + Ok(()) + } + + /// Sets advanced logging directive. + /// Example: + /// * "my_crate=debug" + /// * "my_crate::module=trace" + /// * "my_crate=debug,other_crate=warn" + pub fn set_logging(&self, directive: &str) -> Result<(), anyhow::Error> { + let new_filter = Self::parse_filter(directive)?; + + if let Some(handle) = &self.reload_handle { + handle.modify(|filter| *filter = new_filter)?; + } + + Ok(()) + } + + /// Parses a directive and builds an [EnvFilter] from it. + /// Example: + /// * "my_crate=debug" + /// * "my_crate::module=trace" + /// * "my_crate=debug,other_crate=warn" + fn parse_filter(directive: &str) -> Result { + let mut filter = EnvFilter::from_default_env(); + for directive in directive.split(',') { + filter = filter.add_directive(directive.parse()?); + } + + Ok(filter) + } +} diff --git a/.test-node-subtree/src/resolver.rs b/.test-node-subtree/src/resolver.rs new file mode 100644 index 00000000..db4372e7 --- /dev/null +++ b/.test-node-subtree/src/resolver.rs @@ -0,0 +1,251 @@ +//! Resolving the selectors (both method & event) with external database. +use lazy_static::lazy_static; +use reqwest::header::{HeaderMap, HeaderName, HeaderValue}; +use serde::Deserialize; +use std::iter::FromIterator; +use std::{ + collections::HashMap, + sync::{ + atomic::{AtomicBool, AtomicUsize, Ordering}, + Arc, + }, + time::Duration, +}; +use tokio::sync::RwLock; +use tracing::warn; + +static SELECTOR_DATABASE_URL: &str = "https://sig.eth.samczsun.com/api/v1/signatures"; + +/// The standard request timeout for API requests +const REQ_TIMEOUT: Duration = Duration::from_secs(15); + +/// How many request can time out before we decide this is a spurious connection +const MAX_TIMEDOUT_REQ: usize = 4usize; + +/// A client that can request API data from `https://sig.eth.samczsun.com/api` +#[derive(Debug, Clone)] +pub struct SignEthClient { + inner: reqwest::Client, + /// Whether the connection is spurious, or API is down + spurious_connection: Arc, + /// How many requests timed out + timedout_requests: Arc, + /// Max allowed request that can time out + max_timedout_requests: usize, +} + +#[derive(Deserialize)] +pub struct KnownAbi { + abi: String, + name: String, +} + +lazy_static! { + static ref KNOWN_SIGNATURES: HashMap = { + let json_value = serde_json::from_slice(include_bytes!("data/abi_map.json")).unwrap(); + let pairs: Vec = serde_json::from_value(json_value).unwrap(); + + pairs + .into_iter() + .map(|entry| (entry.abi, entry.name)) + .collect() + }; + static ref CACHE: RwLock>> = RwLock::new(HashMap::new()); +} + +impl SignEthClient { + /// Creates a new client with default settings + pub fn new() -> reqwest::Result { + let inner = reqwest::Client::builder() + .default_headers(HeaderMap::from_iter([( + HeaderName::from_static("user-agent"), + HeaderValue::from_static("zksync"), + )])) + .timeout(REQ_TIMEOUT) + .build()?; + Ok(Self { + inner, + spurious_connection: Arc::new(Default::default()), + timedout_requests: Arc::new(Default::default()), + max_timedout_requests: MAX_TIMEDOUT_REQ, + }) + } + + async fn get_text(&self, url: &str) -> reqwest::Result { + self.inner + .get(url) + .send() + .await + .map_err(|err| { + self.on_reqwest_err(&err); + err + })? + .text() + .await + .map_err(|err| { + self.on_reqwest_err(&err); + err + }) + } + + fn on_reqwest_err(&self, err: &reqwest::Error) { + fn is_connectivity_err(err: &reqwest::Error) -> bool { + if err.is_timeout() || err.is_connect() { + return true; + } + // Error HTTP codes (5xx) are considered connectivity issues and will prompt retry + if let Some(status) = err.status() { + let code = status.as_u16(); + if (500..600).contains(&code) { + return true; + } + } + false + } + + if is_connectivity_err(err) { + warn!("spurious network detected for sig.eth.samczsun.com"); + let previous = self.timedout_requests.fetch_add(1, Ordering::SeqCst); + if previous >= self.max_timedout_requests { + self.set_spurious(); + } + } + } + + /// Returns whether the connection was marked as spurious + fn is_spurious(&self) -> bool { + self.spurious_connection.load(Ordering::Relaxed) + } + + /// Marks the connection as spurious + fn set_spurious(&self) { + self.spurious_connection.store(true, Ordering::Relaxed) + } + + fn ensure_not_spurious(&self) -> eyre::Result<()> { + if self.is_spurious() { + eyre::bail!("Spurious connection detected") + } + Ok(()) + } + + /// Decodes the given function or event selector using sig.eth.samczsun.com + pub async fn decode_selector( + &self, + selector: &str, + selector_type: SelectorType, + ) -> eyre::Result> { + // exit early if spurious connection + self.ensure_not_spurious()?; + + #[derive(Deserialize)] + struct Decoded { + name: String, + filtered: bool, + } + + #[derive(Deserialize)] + struct ApiResult { + event: HashMap>, + function: HashMap>, + } + + #[derive(Deserialize)] + struct ApiResponse { + ok: bool, + result: ApiResult, + } + + // using samczsun signature database over 4byte + // see https://github.com/foundry-rs/foundry/issues/1672 + let url = match selector_type { + SelectorType::Function => format!("{SELECTOR_DATABASE_URL}?function={selector}"), + SelectorType::Event => format!("{SELECTOR_DATABASE_URL}?event={selector}"), + }; + + let res = self.get_text(&url).await?; + let api_response = match serde_json::from_str::(&res) { + Ok(inner) => inner, + Err(err) => { + eyre::bail!("Could not decode response:\n {res}.\nError: {err}") + } + }; + + if !api_response.ok { + eyre::bail!("Failed to decode:\n {res}") + } + + let decoded = match selector_type { + SelectorType::Function => api_response.result.function, + SelectorType::Event => api_response.result.event, + }; + + Ok(decoded + .get(selector) + .ok_or(eyre::eyre!("No signature found"))? + .iter() + .filter(|d| !d.filtered) + .map(|d| d.name.clone()) + .collect::>() + .first() + .cloned()) + } + + /// Fetches a function signature given the selector using sig.eth.samczsun.com + pub async fn decode_function_selector(&self, selector: &str) -> eyre::Result> { + let prefixed_selector = format!("0x{}", selector.strip_prefix("0x").unwrap_or(selector)); + if prefixed_selector.len() != 10 { + eyre::bail!("Invalid selector: expected 8 characters (excluding 0x prefix), got {} characters (including 0x prefix).", prefixed_selector.len()) + } + + if let Some(r) = KNOWN_SIGNATURES.get(&prefixed_selector) { + return Ok(Some(r.clone())); + } + + self.decode_selector(&prefixed_selector[..10], SelectorType::Function) + .await + } +} + +#[derive(Clone, Copy)] +pub enum SelectorType { + Function, + Event, +} +/// Fetches a function signature given the selector using sig.eth.samczsun.com +pub async fn decode_function_selector(selector: &str) -> eyre::Result> { + { + let cache = CACHE.read().await; + if let Some(result) = cache.get(selector) { + return Ok(result.clone()); + } + } + let result = SignEthClient::new()? + .decode_function_selector(selector) + .await; + if let Ok(result) = &result { + let mut cache = CACHE.write().await; + cache.insert(selector.to_string(), result.clone()); + } + result +} + +pub async fn decode_event_selector(selector: &str) -> eyre::Result> { + { + let cache = CACHE.read().await; + if let Some(result) = cache.get(selector) { + return Ok(result.clone()); + } + } + if let Some(r) = KNOWN_SIGNATURES.get(selector) { + return Ok(Some(r.clone())); + } + let result = SignEthClient::new()? + .decode_selector(selector, SelectorType::Event) + .await; + if let Ok(result) = &result { + let mut cache = CACHE.write().await; + cache.insert(selector.to_string(), result.clone()); + } + result +} diff --git a/.test-node-subtree/src/system_contracts.rs b/.test-node-subtree/src/system_contracts.rs new file mode 100644 index 00000000..b1409727 --- /dev/null +++ b/.test-node-subtree/src/system_contracts.rs @@ -0,0 +1,193 @@ +use multivm::interface::TxExecutionMode; +use zksync_contracts::{ + read_playground_batch_bootloader_bytecode, read_proved_batch_bootloader_bytecode, + read_sys_contract_bytecode, read_zbin_bytecode, BaseSystemContracts, ContractLanguage, + SystemContractCode, +}; +use zksync_types::system_contracts::get_system_smart_contracts; +use zksync_utils::{bytecode::hash_bytecode, bytes_to_be_words}; + +use crate::deps::system_contracts::{bytecode_from_slice, COMPILED_IN_SYSTEM_CONTRACTS}; + +#[derive(Default, Debug, Clone)] +pub enum Options { + // Use the compiled-in contracts + #[default] + BuiltIn, + // Load the contracts bytecode at runtime from ZKSYNC_HOME + Local, + // Don't verify the signatures and return transaction result on calls (used only for testing - for example Forge). + BuiltInWithoutSecurity, +} + +/// Holds the system contracts (and bootloader) that are used by the in-memory node. +#[derive(Debug, Clone)] +pub struct SystemContracts { + pub baseline_contracts: BaseSystemContracts, + pub playground_contracts: BaseSystemContracts, + pub fee_estimate_contracts: BaseSystemContracts, + pub baseline_impersonating_contracts: BaseSystemContracts, + pub fee_estimate_impersonating_contracts: BaseSystemContracts, +} + +pub fn get_deployed_contracts(options: &Options) -> Vec { + match options { + Options::BuiltIn | Options::BuiltInWithoutSecurity => COMPILED_IN_SYSTEM_CONTRACTS.clone(), + Options::Local => get_system_smart_contracts(), + } +} + +impl Default for SystemContracts { + /// Creates SystemContracts that use compiled-in contracts. + fn default() -> Self { + SystemContracts::from_options(&Options::BuiltIn) + } +} + +impl SystemContracts { + /// Creates the SystemContracts that use the complied contracts from ZKSYNC_HOME path. + /// These are loaded at binary runtime. + pub fn from_options(options: &Options) -> Self { + Self { + baseline_contracts: baseline_contracts(options), + playground_contracts: playground(options), + fee_estimate_contracts: fee_estimate_contracts(options), + baseline_impersonating_contracts: baseline_impersonating_contracts(options), + fee_estimate_impersonating_contracts: fee_estimate_impersonating_contracts(options), + } + } + pub fn contracts_for_l2_call(&self) -> &BaseSystemContracts { + self.contracts(TxExecutionMode::EthCall, false) + } + + pub fn contracts_for_fee_estimate(&self, impersonating: bool) -> &BaseSystemContracts { + self.contracts(TxExecutionMode::EstimateFee, impersonating) + } + + pub fn contracts( + &self, + execution_mode: TxExecutionMode, + impersonating: bool, + ) -> &BaseSystemContracts { + match (execution_mode, impersonating) { + // 'real' contracts, that do all the checks. + (TxExecutionMode::VerifyExecute, false) => &self.baseline_contracts, + // Ignore invalid signatures. These requests are often coming unsigned, and they keep changing the + // gas limit - so the signatures are often not matching. + (TxExecutionMode::EstimateFee, false) => &self.fee_estimate_contracts, + // Read-only call - don't check signatures, have a lower (fixed) gas limit. + (TxExecutionMode::EthCall, false) => &self.playground_contracts, + // Without account validation and sender related checks. + (TxExecutionMode::VerifyExecute, true) => &self.baseline_impersonating_contracts, + (TxExecutionMode::EstimateFee, true) => &self.fee_estimate_impersonating_contracts, + (TxExecutionMode::EthCall, true) => { + panic!("Account impersonating with eth_call is not supported") + } + } + } +} + +/// Creates BaseSystemContracts object with a specific bootloader. +fn bsc_load_with_bootloader( + bootloader_bytecode: Vec, + options: &Options, +) -> BaseSystemContracts { + let hash = hash_bytecode(&bootloader_bytecode); + + let bootloader = SystemContractCode { + code: bytes_to_be_words(bootloader_bytecode), + hash, + }; + + let bytecode = match options { + Options::BuiltIn => bytecode_from_slice( + "DefaultAccount", + include_bytes!("deps/contracts/DefaultAccount.json"), + ), + Options::Local => read_sys_contract_bytecode("", "DefaultAccount", ContractLanguage::Sol), + Options::BuiltInWithoutSecurity => bytecode_from_slice( + "DefaultAccountNoSecurity", + include_bytes!("deps/contracts/DefaultAccountNoSecurity.json"), + ), + }; + + let hash = hash_bytecode(&bytecode); + + let default_aa = SystemContractCode { + code: bytes_to_be_words(bytecode), + hash, + }; + + BaseSystemContracts { + bootloader, + default_aa, + } +} + +/// BaseSystemContracts with playground bootloader - used for handling 'eth_calls'. +pub fn playground(options: &Options) -> BaseSystemContracts { + let bootloader_bytecode = match options { + Options::BuiltIn | Options::BuiltInWithoutSecurity => { + include_bytes!("deps/contracts/playground_batch.yul.zbin").to_vec() + } + Options::Local => read_playground_batch_bootloader_bytecode(), + }; + + bsc_load_with_bootloader(bootloader_bytecode, options) +} + +/// Returns the system contracts for fee estimation. +/// +/// # Arguments +/// +/// * `use_local_contracts` - A boolean indicating whether to use local contracts or not. +/// +/// # Returns +/// +/// A `BaseSystemContracts` struct containing the system contracts used for handling 'eth_estimateGas'. +/// It sets ENSURE_RETURNED_MAGIC to 0 and BOOTLOADER_TYPE to 'playground_block' +pub fn fee_estimate_contracts(options: &Options) -> BaseSystemContracts { + let bootloader_bytecode = match options { + Options::BuiltIn | Options::BuiltInWithoutSecurity => { + include_bytes!("deps/contracts/fee_estimate.yul.zbin").to_vec() + } + Options::Local => + read_zbin_bytecode("etc/system-contracts/bootloader/build/artifacts/fee_estimate.yul/fee_estimate.yul.zbin") + }; + + bsc_load_with_bootloader(bootloader_bytecode, options) +} + +pub fn fee_estimate_impersonating_contracts(options: &Options) -> BaseSystemContracts { + let bootloader_bytecode = match options { + Options::BuiltIn | Options::BuiltInWithoutSecurity => { + include_bytes!("deps/contracts/fee_estimate_impersonating.yul.zbin").to_vec() + } + Options::Local => + // Account impersonating is not supported with the local contracts + read_zbin_bytecode("etc/system-contracts/bootloader/build/artifacts/fee_estimate.yul/fee_estimate.yul.zbin") + }; + + bsc_load_with_bootloader(bootloader_bytecode, options) +} + +pub fn baseline_contracts(options: &Options) -> BaseSystemContracts { + let bootloader_bytecode = match options { + Options::BuiltIn | Options::BuiltInWithoutSecurity => { + include_bytes!("deps/contracts/proved_batch.yul.zbin").to_vec() + } + Options::Local => read_proved_batch_bootloader_bytecode(), + }; + bsc_load_with_bootloader(bootloader_bytecode, options) +} + +pub fn baseline_impersonating_contracts(options: &Options) -> BaseSystemContracts { + let bootloader_bytecode = match options { + Options::BuiltIn | Options::BuiltInWithoutSecurity => { + include_bytes!("deps/contracts/proved_batch_impersonating.yul.zbin").to_vec() + } + // Account impersonating is not supported with the local contracts + Options::Local => read_proved_batch_bootloader_bytecode(), + }; + bsc_load_with_bootloader(bootloader_bytecode, options) +} diff --git a/.test-node-subtree/src/testing.rs b/.test-node-subtree/src/testing.rs new file mode 100644 index 00000000..bd150752 --- /dev/null +++ b/.test-node-subtree/src/testing.rs @@ -0,0 +1,1028 @@ +//! This file hold testing helpers for other unit tests. +//! +//! There is MockServer that can help simulate a forked network. +//! + +#![cfg(test)] + +use crate::deps::InMemoryStorage; +use crate::node::{InMemoryNode, TxExecutionInfo}; +use crate::{fork::ForkSource, node::compute_hash}; + +use ethabi::{ParamType, Token}; +use ethers::contract; +use httptest::{ + matchers::{eq, json_decoded, request}, + responders::json_encoded, + Expectation, Server, +}; +use itertools::Itertools; +use multivm::interface::{ExecutionResult, VmExecutionResultAndLogs}; +use std::str::FromStr; +use zksync_basic_types::{AccountTreeId, MiniblockNumber, H160, U64}; +use zksync_types::api::{BlockIdVariant, BridgeAddresses, DebugCall, DebugCallType, Log}; +use zksync_types::block::pack_block_info; +use zksync_types::StorageKey; +use zksync_types::{fee::Fee, l2::L2Tx, Address, L2ChainId, Nonce, ProtocolVersionId, H256, U256}; +use zksync_utils::u256_to_h256; + +/// Configuration for the [MockServer]'s initial block. +#[derive(Default, Debug, Clone)] +pub struct ForkBlockConfig { + pub number: u64, + pub hash: H256, + pub transaction_count: u8, +} + +/// A HTTP server that can be used to mock a fork source. +pub struct MockServer { + /// The implementation for [httptest::Server]. + pub inner: Server, +} + +impl MockServer { + /// Start the mock server. + pub fn run() -> Self { + MockServer { + inner: Server::run(), + } + } + + /// Start the mock server with pre-defined calls used to fetch the fork's state. + /// The input config can be used to set the initial block's number, hash and transactions. + pub fn run_with_config(block_config: ForkBlockConfig) -> Self { + let server = Server::run(); + + // setup initial fork calls + server.expect( + Expectation::matching(request::body(json_decoded(eq(serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "method": "eth_blockNumber", + }))))) + .respond_with(json_encoded(serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "result": format!("{:#x}", block_config.number), + }))), + ); + server.expect( + Expectation::matching(request::body(json_decoded(eq(serde_json::json!({ + "jsonrpc": "2.0", + "id": 1, + "method": "zks_getBlockDetails", + "params": [ block_config.number ], + }))))) + .respond_with(json_encoded(serde_json::json!({ + "jsonrpc": "2.0", + "id": 1, + "result": { + "number": block_config.number, + "l1BatchNumber": 1, + "timestamp": 1676461082u64, + "l1TxCount": 0, + "l2TxCount": 0, + "rootHash": format!("{:#x}", block_config.hash), + "status": "verified", + "commitTxHash": "0x9f5b07e968787514667fae74e77ecab766be42acd602c85cfdbda1dc3dd9902f", + "committedAt": "2023-02-15T11:40:39.326104Z", + "proveTxHash": "0xac8fe9fdcbeb5f1e59c41e6bd33b75d405af84e4b968cd598c2d3f59c9c925c8", + "provenAt": "2023-02-15T12:42:40.073918Z", + "executeTxHash": "0x65d50174b214b05e82936c4064023cbea5f6f8135e30b4887986b316a2178a39", + "executedAt": "2023-02-15T12:43:20.330052Z", + "l1GasPrice": 29860969933u64, + "l2FairGasPrice": 500000000u64, + "baseSystemContractsHashes": { + "bootloader": "0x0100038581be3d0e201b3cc45d151ef5cc59eb3a0f146ad44f0f72abf00b594c", + "default_aa": "0x0100038dc66b69be75ec31653c64cb931678299b9b659472772b2550b703f41c" + }, + "operatorAddress": "0xfeee860e7aae671124e9a4e61139f3a5085dfeee", + "protocolVersion": ProtocolVersionId::Version15, + }, + }))), + ); + server.expect( + Expectation::matching(request::body(json_decoded(eq(serde_json::json!({ + "jsonrpc": "2.0", + "id": 2, + "method": "eth_getBlockByHash", + "params": [format!("{:#x}", block_config.hash), true], + }))))).times(0..) + .respond_with(json_encoded(serde_json::json!({ + "jsonrpc": "2.0", + "id": 2, + "result": { + "hash": format!("{:#x}", block_config.hash), + "parentHash": "0x0000000000000000000000000000000000000000000000000000000000000000", + "sha3Uncles": "0x1dcc4de8dec75d7aab85b567b6ccd41ad312451b948a7413f0a142fd40d49347", + "miner": "0x0000000000000000000000000000000000000000", + "stateRoot": "0x0000000000000000000000000000000000000000000000000000000000000000", + "transactionsRoot": "0x0000000000000000000000000000000000000000000000000000000000000000", + "receiptsRoot": "0x0000000000000000000000000000000000000000000000000000000000000000", + "number": format!("{:#x}", block_config.number), + "l1BatchNumber": "0x6", + "gasUsed": "0x0", + "gasLimit": "0xffffffff", + "baseFeePerGas": "0x1dcd6500", + "extraData": "0x", + "logsBloom": "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "timestamp": "0x63ecc41a", + "l1BatchTimestamp": "0x63ecbd12", + "difficulty": "0x0", + "totalDifficulty": "0x0", + "sealFields": [], + "uncles": [], + "transactions": (0..block_config.transaction_count) + .map(|index| { + TransactionResponseBuilder::new() + .set_hash(H256::repeat_byte(index)) + .build_result() + }) + .collect::>(), + "size": "0x0", + "mixHash": "0x0000000000000000000000000000000000000000000000000000000000000000", + "nonce": "0x0000000000000000" + } + }))), + ); + + MockServer { inner: server } + } + + /// Retrieve the mock server's url. + pub fn url(&self) -> String { + self.inner.url("").to_string() + } + + /// Assert an exactly single call expectation with a given request and the provided response. + pub fn expect(&self, request: serde_json::Value, response: serde_json::Value) { + self.inner.expect( + Expectation::matching(request::body(json_decoded(eq(request)))) + .respond_with(json_encoded(response)), + ); + } +} + +/// A mock response builder for a block +#[derive(Default, Debug, Clone)] +pub struct BlockResponseBuilder { + hash: H256, + number: u64, +} + +impl BlockResponseBuilder { + /// Create a new instance of [BlockResponseBuilder] + pub fn new() -> Self { + Self::default() + } + + /// Sets the block hash + pub fn set_hash(&mut self, hash: H256) -> &mut Self { + self.hash = hash; + self + } + + /// Sets the block number + pub fn set_number(&mut self, number: u64) -> &mut Self { + self.number = number; + self + } + + /// Builds the block json result response + pub fn build_result(&mut self) -> serde_json::Value { + serde_json::json!({ + "hash": format!("{:#x}", self.hash), + "parentHash": "0x0000000000000000000000000000000000000000000000000000000000000000", + "sha3Uncles": "0x1dcc4de8dec75d7aab85b567b6ccd41ad312451b948a7413f0a142fd40d49347", + "miner": "0x0000000000000000000000000000000000000000", + "stateRoot": "0x0000000000000000000000000000000000000000000000000000000000000000", + "transactionsRoot": "0x0000000000000000000000000000000000000000000000000000000000000000", + "receiptsRoot": "0x0000000000000000000000000000000000000000000000000000000000000000", + "number": format!("{:#x}", self.number), + "l1BatchNumber": "0x6", + "gasUsed": "0x0", + "gasLimit": "0xffffffff", + "baseFeePerGas": "0x1dcd6500", + "extraData": "0x", + "logsBloom": "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000", + "timestamp": "0x63ecc41a", + "l1BatchTimestamp": "0x63ecbd12", + "difficulty": "0x0", + "totalDifficulty": "0x0", + "sealFields": [], + "uncles": [], + "transactions": [], + "size": "0x0", + "mixHash": "0x0000000000000000000000000000000000000000000000000000000000000000", + "nonce": "0x0000000000000000" + }) + } + + /// Builds the json response + pub fn build(&mut self) -> serde_json::Value { + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "result": self.build_result(), + }) + } +} + +/// A mock response builder for a transaction +#[derive(Default, Debug, Clone)] +pub struct TransactionResponseBuilder { + hash: H256, + block_hash: H256, + block_number: U64, +} + +impl TransactionResponseBuilder { + /// Create a new instance of [TransactionResponseBuilder] + pub fn new() -> Self { + Self::default() + } + + /// Sets the transaction hash + pub fn set_hash(&mut self, hash: H256) -> &mut Self { + self.hash = hash; + self + } + + /// Sets the block hash + pub fn set_block_hash(&mut self, hash: H256) -> &mut Self { + self.block_hash = hash; + self + } + + /// Sets the block number + pub fn set_block_number(&mut self, number: U64) -> &mut Self { + self.block_number = number; + self + } + + /// Builds the transaction json result + pub fn build_result(&mut self) -> serde_json::Value { + serde_json::json!({ + "hash": format!("{:#x}", self.hash), + "nonce": "0x0", + "blockHash": format!("{:#x}", self.block_hash), + "blockNumber": format!("{:#x}", self.block_number), + "transactionIndex": "0x0", + "from": "0x29df43f75149d0552475a6f9b2ac96e28796ed0b", + "to": "0x0000000000000000000000000000000000008006", + "value": "0x0", + "gasPrice": "0x0", + "gas": "0x44aa200", + "input": "0x3cda33510000000000000000000000000000000000000000000000000000000000000000010000553109a66f1432eb2286c54694784d1b6993bc24a168be0a49b4d0fd4500000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000000", + "type": "0xff", + "maxFeePerGas": "0x0", + "maxPriorityFeePerGas": "0x0", + "chainId": "0x104", + "l1BatchNumber": "0x1", + "l1BatchTxIndex": "0x0", + }) + } + + /// Builds the json response + pub fn build(&mut self) -> serde_json::Value { + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "result": self.build_result(), + }) + } +} + +/// A mock response builder for a transaction +#[derive(Default, Debug, Clone)] +pub struct RawTransactionsResponseBuilder { + serial_ids: Vec, +} + +impl RawTransactionsResponseBuilder { + /// Create a new instance of [RawTransactionsResponseBuilder] + pub fn new() -> Self { + Self::default() + } + + /// Inserts a new raw transaction with a serial id + pub fn add(&mut self, serial_id: u64) -> &mut Self { + self.serial_ids.push(serial_id); + self + } + + /// Builds the raw transaction json result + pub fn build_result(&mut self) -> serde_json::Value { + serde_json::json!( + self.serial_ids + .iter() + .map(|serial_id| serde_json::json!({ + "common_data": { + "L1": { + "sender": "0xcca8009f5e09f8c5db63cb0031052f9cb635af62", + "serialId": serial_id, + "deadlineBlock": 0, + "layer2TipFee": "0x0", + "fullFee": "0x0", + "maxFeePerGas": "0x0", + "gasLimit": "0x989680", + "gasPerPubdataLimit": "0x320", + "opProcessingType": "Common", + "priorityQueueType": "Deque", + "ethHash": "0x0000000000000000000000000000000000000000000000000000000000000000", + "ethBlock": 16631249u64, + "canonicalTxHash": "0xaaf9514a005ba59e29b53e1dc84d234d909c5202b44c5179f9c67d8e3cad0636", + "toMint": "0x470de4df820000", + "refundRecipient": "0xcca8009f5e09f8c5db63cb0031052f9cb635af62" + } + }, + "execute": { + "contractAddress": "0xcca8009f5e09f8c5db63cb0031052f9cb635af62", + "calldata": "0x", + "value": "0x470de4df820000", + "factoryDeps": [] + }, + "received_timestamp_ms": 1676429272816u64, + "raw_bytes": null + })) + .collect_vec() + ) + } + + /// Builds the json response + pub fn build(&mut self) -> serde_json::Value { + serde_json::json!({ + "jsonrpc": "2.0", + "id": 0, + "result": self.build_result(), + }) + } +} + +#[derive(Debug, Clone)] +pub struct TransactionBuilder { + tx_hash: H256, + from_account_private_key: H256, + gas_limit: U256, + max_fee_per_gas: U256, + max_priority_fee_per_gas: U256, +} + +impl Default for TransactionBuilder { + fn default() -> Self { + Self { + tx_hash: H256::repeat_byte(0x01), + from_account_private_key: H256::random(), + gas_limit: U256::from(1_000_000), + max_fee_per_gas: U256::from(250_000_000), + max_priority_fee_per_gas: U256::from(250_000_000), + } + } +} + +impl TransactionBuilder { + pub fn new() -> Self { + Self::default() + } + + pub fn set_hash(&mut self, hash: H256) -> &mut Self { + self.tx_hash = hash; + self + } + + pub fn set_gas_limit(&mut self, gas_limit: U256) -> &mut Self { + self.gas_limit = gas_limit; + self + } + + pub fn set_max_fee_per_gas(&mut self, max_fee_per_gas: U256) -> &mut Self { + self.max_fee_per_gas = max_fee_per_gas; + self + } + + pub fn set_max_priority_fee_per_gas(&mut self, max_priority_fee_per_gas: U256) -> &mut Self { + self.max_priority_fee_per_gas = max_priority_fee_per_gas; + self + } + + pub fn build(&mut self) -> L2Tx { + let mut tx = L2Tx::new_signed( + Address::random(), + vec![], + Nonce(0), + Fee { + gas_limit: self.gas_limit, + max_fee_per_gas: self.max_fee_per_gas, + max_priority_fee_per_gas: self.max_priority_fee_per_gas, + gas_per_pubdata_limit: U256::from(20000), + }, + U256::from(1), + L2ChainId::from(260), + &self.from_account_private_key, + None, + Default::default(), + ) + .unwrap(); + tx.set_input(vec![], self.tx_hash); + tx + } +} + +/// Applies a transaction with a given hash to the node and returns the block hash. +pub fn apply_tx( + node: &InMemoryNode, + tx_hash: H256, +) -> (H256, U64) { + let next_miniblock = node + .get_inner() + .read() + .map(|reader| reader.current_miniblock.saturating_add(1)) + .expect("failed getting current batch number"); + let produced_block_hash = compute_hash(next_miniblock, tx_hash); + + let tx = TransactionBuilder::new().set_hash(tx_hash).build(); + node.set_rich_account(tx.common_data.initiator_address); + node.apply_txs(vec![tx]).expect("failed applying tx"); + + (produced_block_hash, U64::from(next_miniblock)) +} + +/// Deploys a contract with the given bytecode. +pub fn deploy_contract( + node: &InMemoryNode, + tx_hash: H256, + private_key: H256, + bytecode: Vec, + calldata: Option>, + nonce: Nonce, +) -> H256 { + use ethers::abi::Function; + use ethers::types::Bytes; + use zksync_web3_rs::eip712; + + let next_miniblock = node + .get_inner() + .read() + .map(|reader| reader.current_miniblock.saturating_add(1)) + .expect("failed getting current batch number"); + let produced_block_hash = compute_hash(next_miniblock, tx_hash); + + let salt = [0u8; 32]; + let bytecode_hash = eip712::hash_bytecode(&bytecode).expect("invalid bytecode"); + let call_data: Bytes = calldata.unwrap_or_default().into(); + let create: Function = serde_json::from_str( + r#"{ + "inputs": [ + { + "internalType": "bytes32", + "name": "_salt", + "type": "bytes32" + }, + { + "internalType": "bytes32", + "name": "_bytecodeHash", + "type": "bytes32" + }, + { + "internalType": "bytes", + "name": "_input", + "type": "bytes" + } + ], + "name": "create", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "payable", + "type": "function" + }"#, + ) + .unwrap(); + + let data = contract::encode_function_data(&create, (salt, bytecode_hash, call_data)) + .expect("failed encoding function data"); + + let mut tx = L2Tx::new_signed( + zksync_types::CONTRACT_DEPLOYER_ADDRESS, + data.to_vec(), + nonce, + Fee { + gas_limit: U256::from(82511299), + max_fee_per_gas: U256::from(250_000_000), + max_priority_fee_per_gas: U256::from(250_000_000), + gas_per_pubdata_limit: U256::from(50000), + }, + U256::from(0), + zksync_basic_types::L2ChainId::from(260), + &private_key, + Some(vec![bytecode]), + Default::default(), + ) + .expect("failed signing tx"); + tx.set_input(vec![], tx_hash); + node.apply_txs(vec![tx]).expect("failed deploying contract"); + + produced_block_hash +} + +/// Builds transaction logs +#[derive(Debug, Default, Clone)] +pub struct LogBuilder { + block_number: U64, + address: Option, + topics: Option>, +} + +impl LogBuilder { + /// Create a new instance of [LogBuilder] + pub fn new() -> Self { + Self::default() + } + + /// Sets the log's block number + pub fn set_block(&mut self, number: U64) -> &mut Self { + self.block_number = number; + self + } + + /// Sets the log address + pub fn set_address(&mut self, address: H160) -> &mut Self { + self.address = Some(address); + self + } + + /// Sets the log topics + pub fn set_topics(&mut self, topics: Vec) -> &mut Self { + self.topics = Some(topics); + self + } + + /// Builds the [Log] object + pub fn build(&mut self) -> Log { + Log { + address: self.address.unwrap_or_default(), + topics: self.topics.clone().unwrap_or_default(), + data: Default::default(), + block_hash: Some(H256::zero()), + block_number: Some(self.block_number), + l1_batch_number: Default::default(), + transaction_hash: Default::default(), + transaction_index: Default::default(), + log_index: Default::default(), + transaction_log_index: Default::default(), + log_type: Default::default(), + removed: Some(false), + } + } +} + +/// Simple storage solidity contract that stores and retrieves two numbers +/// +/// contract Storage { +/// uint256 number1 = 1024; +/// uint256 number2 = 115792089237316195423570985008687907853269984665640564039457584007913129639935; // uint256::max +/// +/// function retrieve1() public view returns (uint256) { +/// return number1; +/// } +/// +/// function retrieve2() public view returns (uint256) { +/// return number2; +/// } +/// +/// function transact_retrieve1() public returns (uint256) { +/// return number1; +/// } +/// } +pub const STORAGE_CONTRACT_BYTECODE: &str = "0000008003000039000000400030043f0000000102200190000000150000c13d00000000020100190000000d02200198000000290000613d000000000101043b000000e0011002700000000e0210009c000000220000613d0000000f0210009c000000220000613d000000100110009c000000290000c13d0000000001000416000000000101004b000000290000c13d0000000101000039000000000101041a000000260000013d0000000001000416000000000101004b000000290000c13d0000040001000039000000000010041b000000010100008a0000000102000039000000000012041b0000002001000039000001000010044300000120000004430000000c010000410000002c0001042e0000000001000416000000000101004b000000290000c13d000000000100041a000000800010043f00000011010000410000002c0001042e00000000010000190000002d000104300000002b000004320000002c0001042e0000002d0001043000000000000000000000000000000000000000020000000000000000000000000000004000000100000000000000000000000000000000000000000000000000fffffffc00000000000000000000000000000000000000000000000000000000000000000000000000000000bbf5533500000000000000000000000000000000000000000000000000000000ae2e2cce000000000000000000000000000000000000000000000000000000002711432d0000000000000000000000000000000000000020000000800000000000000000ccac83652a1e8701e76052e8662f8e7889170c68883ae295c1c984f22be3560f"; + +/// Returns a default instance for a successful [TxExecutionInfo] +pub fn default_tx_execution_info() -> TxExecutionInfo { + TxExecutionInfo { + tx: L2Tx { + execute: zksync_types::Execute { + contract_address: Default::default(), + calldata: Default::default(), + value: Default::default(), + factory_deps: Default::default(), + }, + common_data: Default::default(), + received_timestamp_ms: Default::default(), + raw_bytes: None, + }, + batch_number: Default::default(), + miniblock_number: Default::default(), + result: VmExecutionResultAndLogs { + result: ExecutionResult::Success { output: vec![] }, + logs: Default::default(), + statistics: Default::default(), + refunds: Default::default(), + }, + } +} + +/// Returns a default instance for a successful [DebugCall] +pub fn default_tx_debug_info() -> DebugCall { + DebugCall { + r#type: DebugCallType::Call, + from: Address::zero(), + to: Address::zero(), + gas: U256::zero(), + gas_used: U256::zero(), + value: U256::zero(), + output: Default::default(), + input: Default::default(), + error: None, + revert_reason: None, + calls: vec![DebugCall { + r#type: DebugCallType::Call, + from: Address::zero(), + to: Address::zero(), + gas: U256::zero(), + gas_used: U256::zero(), + value: U256::zero(), + output: Default::default(), + input: Default::default(), + error: None, + revert_reason: None, + calls: vec![], + }], + } +} + +/// Decodes a `bytes` tx result to its concrete parameter type. +pub fn decode_tx_result(output: &[u8], param_type: ParamType) -> Token { + let result = ethabi::decode(&[ParamType::Bytes], output).expect("failed decoding output"); + if result.is_empty() { + panic!("result was empty"); + } + + let result_bytes = result[0] + .clone() + .into_bytes() + .expect("failed converting result to bytes"); + let result = ethabi::decode(&[param_type], &result_bytes).expect("failed converting output"); + if result.is_empty() { + panic!("decoded result was empty"); + } + + result[0].clone() +} + +/// Asserts that two instances of [BridgeAddresses] are equal +pub fn assert_bridge_addresses_eq( + expected_bridge_addresses: &BridgeAddresses, + actual_bridge_addresses: &BridgeAddresses, +) { + assert_eq!( + expected_bridge_addresses.l1_erc20_default_bridge, + actual_bridge_addresses.l1_erc20_default_bridge + ); + assert_eq!( + expected_bridge_addresses.l2_erc20_default_bridge, + actual_bridge_addresses.l2_erc20_default_bridge + ); + assert_eq!( + expected_bridge_addresses.l1_weth_bridge, + actual_bridge_addresses.l1_weth_bridge + ); + assert_eq!( + expected_bridge_addresses.l2_weth_bridge, + actual_bridge_addresses.l2_weth_bridge + ); +} + +/// Represents a read-only fork source that is backed by the provided [InMemoryStorage]. +#[derive(Debug, Clone)] +pub struct ExternalStorage { + pub raw_storage: InMemoryStorage, +} + +impl ForkSource for &ExternalStorage { + fn get_storage_at( + &self, + address: H160, + idx: U256, + _block: Option, + ) -> eyre::Result { + let key = StorageKey::new(AccountTreeId::new(address), u256_to_h256(idx)); + Ok(self + .raw_storage + .state + .get(&key) + .cloned() + .unwrap_or_default()) + } + + fn get_raw_block_transactions( + &self, + _block_number: MiniblockNumber, + ) -> eyre::Result> { + todo!() + } + + fn get_bytecode_by_hash(&self, hash: H256) -> eyre::Result>> { + Ok(self.raw_storage.factory_deps.get(&hash).cloned()) + } + + fn get_transaction_by_hash( + &self, + _hash: H256, + ) -> eyre::Result> { + todo!() + } + + fn get_transaction_details( + &self, + _hash: H256, + ) -> eyre::Result> { + todo!() + } + + fn get_block_by_hash( + &self, + _hash: H256, + _full_transactions: bool, + ) -> eyre::Result>> { + todo!() + } + + fn get_block_by_number( + &self, + _block_number: zksync_types::api::BlockNumber, + _full_transactions: bool, + ) -> eyre::Result>> { + todo!() + } + + fn get_block_details( + &self, + _miniblock: MiniblockNumber, + ) -> eyre::Result> { + todo!() + } + + fn get_block_transaction_count_by_hash(&self, _block_hash: H256) -> eyre::Result> { + todo!() + } + + fn get_block_transaction_count_by_number( + &self, + _block_number: zksync_types::api::BlockNumber, + ) -> eyre::Result> { + todo!() + } + + fn get_transaction_by_block_hash_and_index( + &self, + _block_hash: H256, + _index: zksync_basic_types::web3::types::Index, + ) -> eyre::Result> { + todo!() + } + + fn get_transaction_by_block_number_and_index( + &self, + _block_number: zksync_types::api::BlockNumber, + _index: zksync_basic_types::web3::types::Index, + ) -> eyre::Result> { + todo!() + } + + fn get_bridge_contracts(&self) -> eyre::Result { + todo!() + } + + fn get_confirmed_tokens( + &self, + _from: u32, + _limit: u8, + ) -> eyre::Result> { + todo!() + } +} + +mod test { + use maplit::hashmap; + use zksync_types::block::unpack_block_info; + use zksync_utils::h256_to_u256; + + use super::*; + use crate::http_fork_source::HttpForkSource; + + #[test] + fn test_block_response_builder_set_hash() { + let builder = BlockResponseBuilder::new() + .set_hash(H256::repeat_byte(0x01)) + .build(); + + let actual_value = builder + .as_object() + .and_then(|o| o.get("result").unwrap().as_object()) + .and_then(|o| o.get("hash").unwrap().as_str()) + .expect("failed retrieving value"); + + assert_eq!( + "0x0101010101010101010101010101010101010101010101010101010101010101", + actual_value + ); + } + + #[test] + fn test_block_response_builder_set_number() { + let builder = BlockResponseBuilder::new().set_number(255).build(); + + let actual_value = builder + .as_object() + .and_then(|o| o.get("result").unwrap().as_object()) + .and_then(|o| o.get("number").unwrap().as_str()) + .expect("failed retrieving value"); + + assert_eq!("0xff", actual_value); + } + + #[test] + fn test_transaction_response_builder_set_hash() { + let builder = TransactionResponseBuilder::new() + .set_hash(H256::repeat_byte(0x01)) + .build(); + + let actual_value = builder + .as_object() + .and_then(|o| o.get("result").unwrap().as_object()) + .and_then(|o| o.get("hash").unwrap().as_str()) + .expect("failed retrieving value"); + + assert_eq!( + "0x0101010101010101010101010101010101010101010101010101010101010101", + actual_value + ); + } + + #[test] + fn test_raw_transactions_response_builder_no_items() { + let builder = RawTransactionsResponseBuilder::new().build(); + + let actual_len = builder + .as_object() + .and_then(|o| o.get("result").unwrap().as_array()) + .map(|o| o.len()) + .expect("failed retrieving value"); + + assert_eq!(0, actual_len); + } + + #[test] + fn test_raw_transactions_response_builder_added_items() { + let builder = RawTransactionsResponseBuilder::new() + .add(10) + .add(11) + .build(); + + let actual_serial_ids = builder + .as_object() + .and_then(|o| o.get("result").unwrap().as_array()) + .map(|o| { + o.iter() + .map(|o| o.get("common_data").unwrap().as_object().unwrap()) + .map(|o| o.get("L1").unwrap().as_object().unwrap()) + .map(|entry| entry.get("serialId").unwrap().as_u64().unwrap()) + .collect_vec() + }) + .expect("failed retrieving value"); + + assert_eq!(vec![10, 11], actual_serial_ids); + } + + #[tokio::test] + async fn test_apply_tx() { + let node = InMemoryNode::::default(); + let (actual_block_hash, actual_block_number) = apply_tx(&node, H256::repeat_byte(0x01)); + + assert_eq!( + H256::from_str("0xd97ba6a5ab0f2d7fbfc697251321cce20bff3da2b0ddaf12c80f80f0ab270b15") + .unwrap(), + actual_block_hash, + ); + assert_eq!(U64::from(1), actual_block_number); + + assert!( + node.get_inner() + .read() + .map(|inner| inner.blocks.contains_key(&actual_block_hash)) + .unwrap(), + "block was not produced" + ); + } + + #[test] + fn test_log_builder_set_block() { + let log = LogBuilder::new().set_block(U64::from(2)).build(); + + assert_eq!(Some(U64::from(2)), log.block_number); + } + + #[test] + fn test_log_builder_set_address() { + let log = LogBuilder::new() + .set_address(H160::repeat_byte(0x1)) + .build(); + + assert_eq!(H160::repeat_byte(0x1), log.address); + } + + #[test] + fn test_log_builder_set_topics() { + let log = LogBuilder::new() + .set_topics(vec![ + H256::repeat_byte(0x1), + H256::repeat_byte(0x2), + H256::repeat_byte(0x3), + H256::repeat_byte(0x4), + ]) + .build(); + + assert_eq!( + vec![ + H256::repeat_byte(0x1), + H256::repeat_byte(0x2), + H256::repeat_byte(0x3), + H256::repeat_byte(0x4), + ], + log.topics + ); + } + + #[test] + fn test_external_storage() { + let input_batch = 1; + let input_l2_block = 2; + let input_timestamp = 3; + let input_bytecode = vec![0x4]; + let batch_key = StorageKey::new( + AccountTreeId::new(zksync_types::SYSTEM_CONTEXT_ADDRESS), + zksync_types::SYSTEM_CONTEXT_BLOCK_INFO_POSITION, + ); + let l2_block_key = StorageKey::new( + AccountTreeId::new(zksync_types::SYSTEM_CONTEXT_ADDRESS), + zksync_types::SYSTEM_CONTEXT_CURRENT_L2_BLOCK_INFO_POSITION, + ); + + let storage = &ExternalStorage { + raw_storage: InMemoryStorage { + state: hashmap! { + batch_key => u256_to_h256(U256::from(input_batch)), + l2_block_key => u256_to_h256(pack_block_info( + input_l2_block, + input_timestamp, + )) + }, + factory_deps: hashmap! { + H256::repeat_byte(0x1) => input_bytecode.clone(), + }, + }, + }; + + let actual_batch = storage + .get_storage_at( + zksync_types::SYSTEM_CONTEXT_ADDRESS, + h256_to_u256(zksync_types::SYSTEM_CONTEXT_BLOCK_INFO_POSITION), + None, + ) + .map(|value| h256_to_u256(value).as_u64()) + .expect("failed getting batch number"); + assert_eq!(input_batch, actual_batch); + + let (actual_l2_block, actual_timestamp) = storage + .get_storage_at( + zksync_types::SYSTEM_CONTEXT_ADDRESS, + h256_to_u256(zksync_types::SYSTEM_CONTEXT_CURRENT_L2_BLOCK_INFO_POSITION), + None, + ) + .map(|value| unpack_block_info(h256_to_u256(value))) + .expect("failed getting l2 block info"); + assert_eq!(input_l2_block, actual_l2_block); + assert_eq!(input_timestamp, actual_timestamp); + + let zero_missing_value = storage + .get_storage_at( + zksync_types::SYSTEM_CONTEXT_ADDRESS, + h256_to_u256(H256::repeat_byte(0x1e)), + None, + ) + .map(|value| h256_to_u256(value).as_u64()) + .expect("failed missing value"); + assert_eq!(0, zero_missing_value); + + let actual_bytecode = storage + .get_bytecode_by_hash(H256::repeat_byte(0x1)) + .ok() + .expect("failed getting bytecode") + .expect("missing bytecode"); + assert_eq!(input_bytecode, actual_bytecode); + } +} diff --git a/.test-node-subtree/src/utils.rs b/.test-node-subtree/src/utils.rs new file mode 100644 index 00000000..197ff03d --- /dev/null +++ b/.test-node-subtree/src/utils.rs @@ -0,0 +1,468 @@ +use std::collections::HashMap; +use std::convert::TryInto; +use std::pin::Pin; + +use chrono::{DateTime, Utc}; +use futures::Future; +use multivm::interface::{ExecutionResult, VmExecutionResultAndLogs, VmInterface}; +use multivm::vm_latest::HistoryDisabled; +use multivm::vm_latest::{utils::fee::derive_base_fee_and_gas_per_pubdata, Vm}; +use zksync_basic_types::{H256, U256, U64}; +use zksync_state::WriteStorage; +use zksync_types::api::{BlockNumber, DebugCall, DebugCallType}; +use zksync_types::l2::L2Tx; +use zksync_types::vm_trace::Call; +use zksync_types::CONTRACT_DEPLOYER_ADDRESS; +use zksync_utils::u256_to_h256; +use zksync_utils::{bytecode::hash_bytecode, bytes_to_be_words}; +use zksync_web3_decl::error::Web3Error; + +use crate::deps::storage_view::StorageView; +use crate::node::create_empty_block; +use crate::{fork::ForkSource, node::InMemoryNodeInner}; + +pub(crate) trait IntoBoxedFuture: Sized + Send + 'static { + fn into_boxed_future(self) -> Pin + Send>> { + Box::pin(async { self }) + } +} + +impl IntoBoxedFuture for Result +where + T: Send + 'static, + U: Send + 'static, +{ +} + +/// Adjusts the L1 gas price for a transaction based on the current pubdata price and the fair L2 gas price. +/// If the current pubdata price is small enough, returns the original L1 gas price. +/// Otherwise, calculates a new L1 gas price based on the fair L2 gas price and the transaction gas per pubdata limit. +/// +/// # Arguments +/// +/// * `l1_gas_price` - The original L1 gas price. +/// * `fair_l2_gas_price` - The fair L2 gas price. +/// * `tx_gas_per_pubdata_limit` - The transaction gas per pubdata limit. +/// +/// # Returns +/// +/// The adjusted L1 gas price. +pub fn adjust_l1_gas_price_for_tx( + l1_gas_price: u64, + fair_l2_gas_price: u64, + tx_gas_per_pubdata_limit: U256, +) -> u64 { + let (_, current_pubdata_price) = + derive_base_fee_and_gas_per_pubdata(l1_gas_price, fair_l2_gas_price); + if U256::from(current_pubdata_price) <= tx_gas_per_pubdata_limit { + // The current pubdata price is small enough + l1_gas_price + } else { + let l1_gas_price = U256::from(fair_l2_gas_price) + * (tx_gas_per_pubdata_limit - U256::from(1u32)) + / U256::from(17); + + l1_gas_price.as_u64() + } +} + +/// Takes long integers and returns them in human friendly format with "_". +/// For example: 12_334_093 +pub fn to_human_size(input: U256) -> String { + let input = format!("{:?}", input); + let tmp: Vec<_> = input + .chars() + .rev() + .enumerate() + .flat_map(|(index, val)| { + if index > 0 && index % 3 == 0 { + vec!['_', val] + } else { + vec![val] + } + }) + .collect(); + tmp.iter().rev().collect() +} + +pub fn bytecode_to_factory_dep(bytecode: Vec) -> (U256, Vec) { + let bytecode_hash = hash_bytecode(&bytecode); + let bytecode_hash = U256::from_big_endian(bytecode_hash.as_bytes()); + + let bytecode_words = bytes_to_be_words(bytecode); + + (bytecode_hash, bytecode_words) +} + +/// Creates and inserts a given number of empty blocks into the node, with a given interval between them. +/// The blocks will be empty (contain no transactions). +/// Currently this is quite slow - as we invoke the VM for each operation, in the future we might want to optimise it +/// by adding a way to set state via some system contract call. +pub fn mine_empty_blocks( + node: &mut InMemoryNodeInner, + num_blocks: u64, + interval_ms: u64, +) { + // build and insert new blocks + for i in 0..num_blocks { + // roll the vm + let (keys, bytecodes, block_ctx) = { + let storage = StorageView::new(&node.fork_storage).into_rc_ptr(); + + // system_contract.contracts_for_l2_call() will give playground contracts + // we need these to use the unsafeOverrideBlock method in SystemContext.sol + let bootloader_code = node.system_contracts.contracts_for_l2_call(); + let (batch_env, mut block_ctx) = node.create_l1_batch_env(storage.clone()); + // override the next block's timestamp to match up with interval for subsequent blocks + if i != 0 { + block_ctx.timestamp = node.current_timestamp.saturating_add(interval_ms); + } + + // init vm + let system_env = node.create_system_env( + bootloader_code.clone(), + multivm::interface::TxExecutionMode::VerifyExecute, + ); + + let mut vm: Vm<_, HistoryDisabled> = Vm::new(batch_env, system_env, storage.clone()); + + vm.execute(multivm::interface::VmExecutionMode::Bootloader); + + let bytecodes: HashMap> = vm + .get_last_tx_compressed_bytecodes() + .iter() + .map(|b| bytecode_to_factory_dep(b.original.clone())) + .collect(); + let modified_keys = storage.borrow().modified_storage_keys().clone(); + (modified_keys, bytecodes, block_ctx) + }; + + for (key, value) in keys.iter() { + node.fork_storage.set_value(*key, *value); + } + + // Write all the factory deps. + for (hash, code) in bytecodes.iter() { + node.fork_storage.store_factory_dep( + u256_to_h256(*hash), + code.iter() + .flat_map(|entry| { + let mut bytes = vec![0u8; 32]; + entry.to_big_endian(&mut bytes); + bytes.to_vec() + }) + .collect(), + ) + } + + let block = create_empty_block( + block_ctx.miniblock, + block_ctx.timestamp, + block_ctx.batch, + None, + ); + + node.block_hashes.insert(block.number.as_u64(), block.hash); + node.blocks.insert(block.hash, block); + + // leave node state ready for next interaction + node.current_batch = block_ctx.batch; + node.current_miniblock = block_ctx.miniblock; + node.current_timestamp = block_ctx.timestamp; + } +} + +/// Returns the actual [U64] block number from [BlockNumber]. +/// +/// # Arguments +/// +/// * `block_number` - [BlockNumber] for a block. +/// * `latest_block_number` - A [U64] representing the latest block number. +/// +/// # Returns +/// +/// A [U64] representing the input block number. +pub fn to_real_block_number(block_number: BlockNumber, latest_block_number: U64) -> U64 { + match block_number { + BlockNumber::Finalized + | BlockNumber::Pending + | BlockNumber::Committed + | BlockNumber::Latest => latest_block_number, + BlockNumber::Earliest => U64::zero(), + BlockNumber::Number(n) => n, + } +} + +/// Returns a [jsonrpc_core::Error] indicating that the method is not implemented. +pub fn not_implemented( + method_name: &str, +) -> jsonrpc_core::BoxFuture> { + tracing::warn!("Method {} is not implemented", method_name); + Err(jsonrpc_core::Error { + data: None, + code: jsonrpc_core::ErrorCode::MethodNotFound, + message: format!("Method {} is not implemented", method_name), + }) + .into_boxed_future() +} + +/// Creates a [DebugCall] from a [L2Tx], [VmExecutionResultAndLogs] and a list of [Call]s. +pub fn create_debug_output( + l2_tx: &L2Tx, + result: &VmExecutionResultAndLogs, + traces: Vec, +) -> Result { + let calltype = if l2_tx.recipient_account() == CONTRACT_DEPLOYER_ADDRESS { + DebugCallType::Create + } else { + DebugCallType::Call + }; + match &result.result { + ExecutionResult::Success { output } => Ok(DebugCall { + gas_used: result.statistics.gas_used.into(), + output: output.clone().into(), + r#type: calltype, + from: l2_tx.initiator_account(), + to: l2_tx.recipient_account(), + gas: l2_tx.common_data.fee.gas_limit, + value: l2_tx.execute.value, + input: l2_tx.execute.calldata().into(), + error: None, + revert_reason: None, + calls: traces.into_iter().map(Into::into).collect(), + }), + ExecutionResult::Revert { output } => Ok(DebugCall { + gas_used: result.statistics.gas_used.into(), + output: Default::default(), + r#type: calltype, + from: l2_tx.initiator_account(), + to: l2_tx.recipient_account(), + gas: l2_tx.common_data.fee.gas_limit, + value: l2_tx.execute.value, + input: l2_tx.execute.calldata().into(), + error: None, + revert_reason: Some(output.to_string()), + calls: traces.into_iter().map(Into::into).collect(), + }), + ExecutionResult::Halt { reason } => Err(Web3Error::SubmitTransactionError( + reason.to_string(), + vec![], + )), + } +} + +/// Converts a timestamp in milliseconds since epoch to a [DateTime] in UTC. +pub fn utc_datetime_from_epoch_ms(millis: u64) -> DateTime { + let secs = millis / 1000; + let nanos = (millis % 1000) * 1_000_000; + // expect() is ok- nanos can't be >2M + DateTime::::from_timestamp(secs as i64, nanos as u32).expect("valid timestamp") +} + +#[cfg(test)] +mod tests { + use zksync_basic_types::{H256, U256}; + + use crate::{http_fork_source::HttpForkSource, node::InMemoryNode, testing}; + + use super::*; + + #[test] + fn test_utc_datetime_from_epoch_ms() { + let actual = utc_datetime_from_epoch_ms(1623931200000); + assert_eq!( + DateTime::::from_naive_utc_and_offset( + chrono::NaiveDateTime::from_timestamp_opt(1623931200, 0).unwrap(), + Utc + ), + actual + ); + } + + #[test] + fn test_human_sizes() { + assert_eq!("123", to_human_size(U256::from(123u64))); + assert_eq!("1_234", to_human_size(U256::from(1234u64))); + assert_eq!("12_345", to_human_size(U256::from(12345u64))); + assert_eq!("0", to_human_size(U256::from(0))); + assert_eq!("1", to_human_size(U256::from(1))); + assert_eq!("250_000_000", to_human_size(U256::from(250000000u64))); + } + + #[test] + fn test_to_real_block_number_finalized() { + let actual = to_real_block_number(BlockNumber::Finalized, U64::from(10)); + assert_eq!(U64::from(10), actual); + } + + #[test] + fn test_to_real_block_number_pending() { + let actual = to_real_block_number(BlockNumber::Pending, U64::from(10)); + assert_eq!(U64::from(10), actual); + } + + #[test] + fn test_to_real_block_number_committed() { + let actual = to_real_block_number(BlockNumber::Committed, U64::from(10)); + assert_eq!(U64::from(10), actual); + } + + #[test] + fn test_to_real_block_number_latest() { + let actual = to_real_block_number(BlockNumber::Latest, U64::from(10)); + assert_eq!(U64::from(10), actual); + } + + #[test] + fn test_to_real_block_number_earliest() { + let actual = to_real_block_number(BlockNumber::Earliest, U64::from(10)); + assert_eq!(U64::zero(), actual); + } + + #[test] + fn test_to_real_block_number_number() { + let actual = to_real_block_number(BlockNumber::Number(U64::from(5)), U64::from(10)); + assert_eq!(U64::from(5), actual); + } + + #[test] + fn test_mine_empty_blocks_mines_the_first_block_immediately() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + + let starting_block = { + let reader = inner.read().expect("failed acquiring reader"); + reader + .block_hashes + .get(&reader.current_miniblock) + .and_then(|hash| reader.blocks.get(hash)) + .expect("failed finding block") + .clone() + }; + assert_eq!(U64::from(0), starting_block.number); + assert_eq!(Some(U64::from(0)), starting_block.l1_batch_number); + assert_eq!(U256::from(1000), starting_block.timestamp); + + { + let mut writer = inner.write().expect("failed acquiring write lock"); + mine_empty_blocks(&mut writer, 1, 1000); + } + + let reader = inner.read().expect("failed acquiring reader"); + let mined_block = reader + .block_hashes + .get(&1) + .and_then(|hash| reader.blocks.get(hash)) + .expect("failed finding block"); + assert_eq!(U64::from(1), mined_block.number); + assert_eq!(Some(U64::from(1)), mined_block.l1_batch_number); + assert_eq!(U256::from(1001), mined_block.timestamp); + } + + #[test] + fn test_mine_empty_blocks_mines_2_blocks_with_interval() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + + let starting_block = { + let reader = inner.read().expect("failed acquiring reader"); + reader + .block_hashes + .get(&reader.current_miniblock) + .and_then(|hash| reader.blocks.get(hash)) + .expect("failed finding block") + .clone() + }; + assert_eq!(U64::from(0), starting_block.number); + assert_eq!(Some(U64::from(0)), starting_block.l1_batch_number); + assert_eq!(U256::from(1000), starting_block.timestamp); + + { + let mut writer = inner.write().expect("failed acquiring write lock"); + mine_empty_blocks(&mut writer, 2, 1000); + } + + let reader = inner.read().expect("failed acquiring reader"); + let mined_block_1 = reader + .block_hashes + .get(&1) + .and_then(|hash| reader.blocks.get(hash)) + .expect("failed finding block 1"); + assert_eq!(U64::from(1), mined_block_1.number); + assert_eq!(Some(U64::from(1)), mined_block_1.l1_batch_number); + assert_eq!(U256::from(1001), mined_block_1.timestamp); + + let mined_block_2 = reader + .block_hashes + .get(&2) + .and_then(|hash| reader.blocks.get(hash)) + .expect("failed finding block 2"); + assert_eq!(U64::from(2), mined_block_2.number); + assert_eq!(Some(U64::from(2)), mined_block_2.l1_batch_number); + assert_eq!(U256::from(2001), mined_block_2.timestamp); + } + + #[test] + fn test_mine_empty_blocks_mines_2_blocks_with_interval_and_next_block_immediately() { + let node = InMemoryNode::::default(); + let inner = node.get_inner(); + + let starting_block = { + let reader = inner.read().expect("failed acquiring reader"); + reader + .block_hashes + .get(&reader.current_miniblock) + .and_then(|hash| reader.blocks.get(hash)) + .expect("failed finding block") + .clone() + }; + assert_eq!(U64::from(0), starting_block.number); + assert_eq!(Some(U64::from(0)), starting_block.l1_batch_number); + assert_eq!(U256::from(1000), starting_block.timestamp); + + { + let mut writer = inner.write().expect("failed acquiring write lock"); + mine_empty_blocks(&mut writer, 2, 1000); + } + + { + let reader = inner.read().expect("failed acquiring reader"); + let mined_block_1 = reader + .block_hashes + .get(&1) + .and_then(|hash| reader.blocks.get(hash)) + .expect("failed finding block 1"); + assert_eq!(U64::from(1), mined_block_1.number); + assert_eq!(Some(U64::from(1)), mined_block_1.l1_batch_number); + assert_eq!(U256::from(1001), mined_block_1.timestamp); + + let mined_block_2 = reader + .block_hashes + .get(&2) + .and_then(|hash| reader.blocks.get(hash)) + .expect("failed finding block 2"); + assert_eq!(U64::from(2), mined_block_2.number); + assert_eq!(Some(U64::from(2)), mined_block_2.l1_batch_number); + assert_eq!(U256::from(2001), mined_block_2.timestamp); + } + + { + testing::apply_tx(&node, H256::repeat_byte(0x1)); + let reader = inner.read().expect("failed acquiring reader"); + let tx_block_3 = reader + .block_hashes + .get(&3) + .and_then(|hash| reader.blocks.get(hash)) + .expect("failed finding block 2"); + assert_eq!(U64::from(3), tx_block_3.number); + assert_eq!(Some(U64::from(3)), tx_block_3.l1_batch_number); + assert_eq!(U256::from(2002), tx_block_3.timestamp); + } + } +} + +/// Converts `h256` value as BE into the u64 +pub fn h256_to_u64(value: H256) -> u64 { + let be_u64_bytes: [u8; 8] = value[24..].try_into().unwrap(); + u64::from_be_bytes(be_u64_bytes) +} diff --git a/.test-node-subtree/test_endpoints.http b/.test-node-subtree/test_endpoints.http new file mode 100644 index 00000000..5a2d56ff --- /dev/null +++ b/.test-node-subtree/test_endpoints.http @@ -0,0 +1,803 @@ +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_blockNumber", + "params": [] +} + +### + +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_gasPrice", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "net_version", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "net_listening", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "net_peerCount", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "config_getShowCalls", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "config_getCurrentTimestamp", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "config_setShowCalls", + "params": ["All"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "config_setShowStorageLogs", + "params": ["All"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "config_setShowVmDetails", + "params": ["All"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "config_setShowGasDetails", + "params": ["All"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "config_setResolveHashes", + "params": [true] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "debug_traceCall", + "params": [{ + "to": "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "data": "0x0000", + "from": "0xa61464658AfeAf65CccaaFD3a512b69A83B77618", + "gas": "0x0000", + "gasPrice": "0x0000", + "value": "0x0000", + "nonce": "0x0000" + }, "latest"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "debug_traceTransaction", + "params": ["0xd3a94ff697a573cb174ecce05126e952ecea6dee051526a3e389747ff86b0d99", { "tracer": "callTracer", "tracerConfig": { "onlyTopCall": true } }] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "debug_traceBlockByHash", + "params": ["0xd3a94ff697a573cb174ecce05126e952ecea6dee051526a3e389747ff86b0d99", { "tracer": "callTracer", "tracerConfig": { "onlyTopCall": true } }] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "debug_traceBlockByNumber", + "params": ["0xddd", { "tracer": "callTracer", "tracerConfig": { "onlyTopCall": true } }] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_chainId", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_estimateGas", + "params": [{ + "0x0000000000000000000000000000000000000000": true + }] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_gasPrice", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getBalance", + "params": ["0x0000000000000000000000000000000000000000", "latest"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getBlockByHash", + "params": ["0x0000000000000000000000000000000000000000000000000000000000000000", true] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getBlockByNumber", + "params": ["latest", true] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getCode", + "params": ["0x0000000000000000000000000000000000000000", "latest"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getTransactionByHash", + "params": ["0x0000000000000000000000000000000000000000000000000000000000000000"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_getTransactionCount", + "params": ["0x0000000000000000000000000000000000000000", "latest"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_sendRawTransaction", + "params": ["0x0000"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_blockNumber", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_call", + "params": [{ + "to": "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "data": "0x0000", + "from": "0xa61464658AfeAf65CccaaFD3a512b69A83B77618", + "gas": "0x0000", + "gasPrice": "0x0000", + "value": "0x0000", + "nonce": "0x0000" + }, "latest"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_syncing", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "evm_increaseTime", + "params": [10] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "evm_setNextBlockTimestamp", + "params": [1672527600] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "evm_setTime", + "params": [1672527600] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "evm_mine", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "evm_snapshot", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "evm_revert", + "params": ["0x1"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getBlockByHash", + "params": ["0x371c9871792d89fea30e6b947ca45e9798e4f577dcdddb79269a93450f52b459", true] +} + + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getBlockByNumber", + "params": ["0xc9d5bb", false] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getBlockByNumber", + "params": ["latest", false] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getBlockByNumber", + "params": ["earliest", false] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getBlockTransactionCountByHash", + "params": ["0x371c9871792d89fea30e6b947ca45e9798e4f577dcdddb79269a93450f52b459"] +} + + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getBlockTransactionCountByNumber", + "params": ["0xc9d5bb"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getBlockTransactionCountByNumber", + "params": ["latest"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getBlockTransactionCountByNumber", + "params": ["earliest"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_newBlockFilter", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_newFilter", + "params": [{"fromBlock": "earliest", "toBlock": "0xa"}] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_newPendingTransactionFilter", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_uninstallFilter", + "params": ["0x2"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getFilterChanges", + "params": ["0x1"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getStorageAt", + "params": ["0x123456789abcdef123456789abcdef1234567890", "0x0", "latest"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getTransactionByBlockHashAndIndex", + "params": ["0x123456789abcdef123456789abcdef1234567890", "0x1"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_getTransactionByBlockNumberAndIndex", + "params": ["latest", "0x1"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "eth_protocolVersion" +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "hardhat_setBalance", + "params": [ + "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "0x1337" + ] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "hardhat_setNonce", + "params": [ + "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + "0x56" + ] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "hardhat_mine", + "params": [ + "0xaa", + "0x100" + ] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "hardhat_impersonateAccount", + "params": [ + "0x364d6D0333432C3Ac016Ca832fb8594A8cE43Ca6" + ] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "hardhat_stopImpersonatingAccount", + "params": [ + "0x364d6D0333432C3Ac016Ca832fb8594A8cE43Ca6" + ] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "2", + "method": "hardhat_setCode", + "params": [ + "0x36615Cf349d7F6344891B1e7CA7C72883F5dc049", + [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] + ] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "zks_getTokenPrice", + "params": ["0x0000000000000000000000000000000000000000"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "zks_getTransactionDetails", + "params": ["0xa5d62a85561295ed58f8daad4e9442691e6da4301a859f364d28a02917d6e04d"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "zks_getBlockDetails", + "params": [16474138] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "zks_getBridgeContracts", +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "zks_getRawBlockTransactions", + "params": [16474138] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "zks_getConfirmedTokens", + "params": [0, 100] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "zks_getAllAccountBalances", + "params": ["0x36615Cf349d7F6344891B1e7CA7C72883F5dc049"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_feeHistory", + "params": ["0x1", "latest", [25, 50 , 75]] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "eth_accounts", + "params": [] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "config_setLogLevel", + "params": ["trace"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "config_setLogging", + "params": ["era_test_node=info,hyper=debug"] +} + +### +POST http://localhost:8011 +content-type: application/json + +{ + "jsonrpc": "2.0", + "id": "1", + "method": "web3_clientVersion", + "params": [] +} diff --git a/Makefile b/Makefile index 4320104c..850a2ea7 100644 --- a/Makefile +++ b/Makefile @@ -1,7 +1,7 @@ .PHONY: clean current_dir := ${CURDIR} -era_test_node_base_path := $(current_dir)/submodules/era-test-node +era_test_node_base_path := $(current_dir)/.test-node-subtree era_test_node := $(era_test_node_base_path)/target/release/era_test_node era_test_node_makefile := $(era_test_node_base_path)/Makefile precompile_dst_path := $(era_test_node_base_path)/etc/system-contracts/contracts/precompiles @@ -22,11 +22,6 @@ $(era_test_node): $(era_test_node_makefile) $(precompiles_dst): $(precompiles_source) cp precompiles/*.yul $(precompile_dst_path) && cd $(era_test_node_base_path) && make build-contracts -$(era_test_node_makefile): - mkdir -p submodules && \ - cd submodules && \ - git clone git@github.com:LambdaClass/era-test-node.git --branch lambdaclasss_precompiles - build-precompiles: $(precompiles_dst) # Node Commands diff --git a/README.md b/README.md index becde8d7..16e6dc32 100644 --- a/README.md +++ b/README.md @@ -82,3 +82,14 @@ If you want to run a specific test: ``` make test PRECOMPILE= ``` + + +### To pull changes zk sync era node LC fork on the precompiles branch + +```git subtree pull --prefix=.test-node-subtree --squash git@github.com:lambdaclass/era-test-node.git lambdaclasss_precompiles``` + +### To push changes from local node to the branch + +This should be used if for example a precompile is added or modified, and we want to push the chanes to the fork upstream + + ```git subtree push -P .test-node-subtree git@github.com:lambdaclass/era-test-node.git lambdaclasss_precompiles``` diff --git a/submodules/era-test-node b/submodules/era-test-node deleted file mode 160000 index 84b2805f..00000000 --- a/submodules/era-test-node +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 84b2805f191ea1d451bf3083f7232ce33c26567d